Nota
O acesso a esta página requer autorização. Podes tentar iniciar sessão ou mudar de diretório.
O acesso a esta página requer autorização. Podes tentar mudar de diretório.
Importando chamadas de função usando
Anotar chamadas usando o __declspec(dllimport) pode torná-las mais rápidas.
__declspec(dllimport) é sempre necessário para acessar dados DLL exportados.
Importar uma função de uma DLL
O exemplo de código a seguir mostra como usar __declspec(dllimport) para importar chamadas de função de uma DLL para um aplicativo. Suponha que func1 é uma função que está em uma DLL separada do arquivo executável que contém a função principal .
Sem __declspec(dllimport), dado este código:
int main(void)
{
func1();
}
O compilador gera código com esta aparência:
call func1
e o linker traduz a chamada em algo assim:
call 0x4000000 ; The address of 'func1'.
Se func1 existir em outra DLL, o vinculador não pode resolver esse endereço diretamente porque não tem como saber qual é o endereço func1 . Em ambientes de 32 bits e 64 bits, o vinculador gera um thunk num endereço conhecido. Em um ambiente de 32 bits, o "thunk" se parece com:
0x40000000: jmp DWORD PTR __imp_func1
Aqui __imp_func1 está o endereço do slot func1 na tabela de endereços de importação do ficheiro executável. Todos esses endereços são conhecidos pelo vinculador. O carregador só precisa atualizar a tabela de endereços de importação do arquivo executável no momento do carregamento para que tudo funcione corretamente.
É por isso que usar __declspec(dllimport) é melhor: porque o linker não gera um thunk se não for necessário. Thunks tornam o código maior (em sistemas RISC, pode ser várias instruções) e podem degradar o desempenho do cache. Se você informar ao compilador que a função está em uma DLL, ele pode gerar uma chamada indireta para você.
Então agora este código:
__declspec(dllimport) void func1(void);
int main(void)
{
func1();
}
gera esta instrução:
call DWORD PTR __imp_func1
Não há thunk nem jmp instrução, então o código é menor e mais rápido. Você também pode obter o mesmo efeito ao usar a otimização de todo o programa sem __declspec(dllimport). Para obter mais informações, consulte /GL (Otimização de todo o programa).
Para chamadas de função dentro de uma DLL, você não quer ter que usar uma chamada indireta. O vinculador já sabe o endereço da função. Leva tempo e espaço extra para carregar e armazenar o endereço da função antes de uma chamada indireta. Uma chamada direta é sempre mais rápida e menor. Você só deseja usar __declspec(dllimport) ao chamar funções DLL de fora da própria DLL. Não use __declspec(dllimport) em funções dentro de uma DLL ao criar essa DLL.