DLOPEN(3)

NOME
dlclose, dlerror, dlopen, dlsym - interface de programação do carregador de bibliotecas dinâmicas

SINÓPSE
#include <dlfcn.h>

void *dlopen (const char *filename, int flag);
const char *dlerror(void);
void *dlsym(void *handle, char *symbol);
int dlclose (void *handle);

Special symbols: _init, _fini.

DESCRIÇÃO
dlopen carrega uma biblioteca dinâmica do arquivo designado pela seqüencia filename e retorna um manipulador (handle) para a biblioteca. Se filename não for um caminho absoluto (não começar com '/'), o arquivo será procurado nos seguintes locais:

    Uma lista de diretórios separados por ponto-e-vírgula na variável de ambiente LD_LIBRARY_PATH.

    A lista de bibliotecas em /etc/ld.so.cache.

    /usr/lib e /lib.

Se filename for NULO, o manipulador designará o programa principal.

As referências externas da biblioteca são definidas usando as bibliotecas na lista de dependências desta biblioteca ou de quaisquer outras bibliotecas abertas com o sinalizador RTLD_GLOBAL. Se o executável foi 'linkado' com o sinalizador "-rdynamic", os símbolos globais no executável também serão usados para definir referências numa biblioteca carregada dinamicamente.

flag pode ser RTLD_LAZY, que faz que os símbolos não definidos sejam pesquisados durante a execução, ou RTLD_NOW, que faz que todos os símbolos não definidos sejam pesquisados antes que dlopen retorne, e falhe se não puder fazê-lo. A opção RTLD_GLOBAL pode ser acrescentada (com OR) a flag, o que faz com que os símbolos externos definidos na biblioteca sejam disponibilizados para as bibliotecas carregadas posteriormente.

Se a biblioteca exportar uma rotina chamada _init, este código será executado antes do retorno de dlopen. Se uma mesma biblioteca for carregada duas vezes, dlopen(), será retornado o mesmo manipulador. A biblioteca 'dl' mantém uma contagem de ligações, e a biblioteca não será dealocada até que dlclose seja chamada o mesmo número de vezes que dlopen tenha sido usada com sucesso.

Se dlopen falhar por qualquer motivo, ela retornará NULO. Uma mensagem de texto descrevendo o erro mais recente gerado pelas funções dlopen, dlsym ou dlclose pode ser obtida com dlerror(). dlerror retorna NULO se não tiver ocorrido nenhum erro desde a inicialização ou desde que ela foi chamada pela última vez. (Chamar dlerror() duas vezes seguidas sempre fará com que a segunda chamada retorne NULO). dlsym pega o manipulador de uma biblioteca e o nulo da terminação do símbolo e retorna o endereço onde este símbolo se encontra. Se o símbolo não for encontrado, dlsym retorna NULO. O modo certo de identificar um erro do dlsym é gravar o resultado de dlerror em uma variável e ver se o resultado não é NULO. Isto ocorre porque o valor do símbolo pode ser NULO. Também é necessário armazenar o resultado de dlerror em uma variável porque se dlerror for chamada novamente, ela retornará NULO.

dlclose decrementa a contagem do manipulador da biblioteca dinâmica, handle. Se esta contagem chegar a zero e não houver outra biblioteca usando símbolos desta biblioteca, ela é descarregada. Se houver uma rotina chamada _fini, ela será executada imediatamente antes de a biblioteca ser descarregada.

VALORES RETORNADOS
dlclose Em caso de sucesso, devolve 0. Caso contrário, é devolvido outro valor.

EXEMPLOS
Carregar a biblioteca de matemática e calcular o coseno de 2.0:
    #include <stdio.h>
    #include <dlfcn.h>
    int main(int argc, char **argv) {
        void *handle;
        double (*cosine)(double);
        char *error;
        handle = dlopen ("/lib/libm.so", RTLD_LAZY);
        if (!handle) {
            fputs (dlerror(), stderr);
    	exit(1);
        }
        cosine = dlsym(handle, "cos");
        if ((error = dlerror()) != NULL)  {
            fprintf (stderr, "%s\n", error);
    	exit(1);
        }
        printf ("%f\n", (*cosine)(2.0));
        dlclose(handle);
    }

Se este programa estivesse num arquivo chamado "foo.c", o programa seria compilado com o comando

    gcc -rdynamic -o foo foo.c -ldl

CRÉDITOS
A interface dlopen surgiu no Solaris. A implementação linux foi escrita por Eric Youngdale, com ajuda de Mitch D'Souza, David Engel, Hongjiu Lu, Andreas Schwab e outros. Esta manpage foi escrita por Adam Richter.

VER TAMBÉM
ld(1), ld.so(8), ldconfig(8), ldd(1), ld.so.info.

TRADUZIDO POR LDP-BR em 21/08/2000.

  Tradução:
Paulo César Mendes <drpc@ism.com.br>

  Revisão.:
André Luiz Fassone <lonely_wolf@ig.com.br>