Domanda

Ho un programma C in cui ottengo puntatori di funzione "dinamicamente" con il nome della funzione (cioè. Passo il nome della funzione come stringa e ottengo un puntatore alla funzione). Lo faccio già in Linux usando dlopen e dlsym e suppongo che funzionerà anche in qualsiasi altro tipo di unix dlfcn.

I problemi sono iniziati quando ho provato a portare questo programma a Windows usando MINGW. Quando provo a trovare il nome usando "getprCaddress (manegge, simbolo_name), dove" simbolo_name "è il nome della mia funzione di callback e" handle "è un manico per l'eseguibile corrente restituita da" getmodulehandle (null) ", non ottengo nulla Perché il nome di Mingw Mingling aggiunge un "_" al mio nome di simbolo.

La soluzione ovvia (prefisso un "_" al simbolo che voglio) sembra un po '"pericolosa" per la portabilità (può il compilatore aggiungere due sottoti per alcuni di essi? Non lo so), quindi chiedo:

  • Esiste un modo migliore per impedire al compilatore di managing dei miei simboli? (o un sottoinsieme di essi, solo i callback che devo trovare dinamicamente);

  • O un modo per farli trovarli anche quando li trovano?

Ho anche provato l'opzione -fno-leading-winderscore, ma ha rimosso anche il mangrezzo di tutti i simboli esterni, rendendo impossibile il programma da collegare con lo stdlib, ecc. (Inoltre, gli avvertimenti sulla documentazione sono un po 'spaventosi).

Inoltre, si prega di notare che sto usando puro C - non c'è C ++ in nessuna parte del mio codice - e tutto il mio codice vive in un singolo ".exe".

Tia

È stato utile?

Soluzione

Non sono sicuro di quale sia il tuo problema, poiché non riesco a riprodurlo con l'esempio DLL più semplice che riesco a pensare:

/* hello_dll.c */
#include <stdio.h>

__declspec(dllexport) void hello ( void )
{
    puts ( "Hello, DLL!");
}

/* hello_exe.c */
#include <windows.h>
#include <stdio.h>  

int main () {
    typedef void (*pfunc)(void);

    HANDLE hself;

    pfunc hello;

    hself = GetModuleHandle(NULL);

    hello = (pfunc)GetProcAddress(hdll, "hello");

    hello();

    return 0;
}

Questa è la riga di comando che utilizza Mingw GCC senza flag speciali e tutto funziona:

gcc src\hello_dll.c src\hello_exe.c -o bin\hello.exe
$ bin\hello.exe
Hello, DLL!
$ gcc --version
gcc (GCC) 4.5.0

Non funziona senza il __declspec(dllexport) Se stai ottenendo la funzione da te; Quando si crea una DLL con gcc -shared Non sembra essere necessario, ma sembra essere necessario se si esportano una funzione da un exe.

Altri suggerimenti

C non usa il manglini di nome. In particolare, non aggiunge alcuna informazione di tipo al nome (a differenza di C ++). Ma alcune piattaforme apportano una piccola modifica al nome come il prefisso del sottolineaggio. E a differenza di C ++, è solo una piattaforma specifica ma non specifica del compilatore.

Su tutte le piattaforme che ho visto finora, non ho visto solo nessuna modifica o il principale sottolineaggio.

Quindi ti propongo di usarne un po ' Ifdefs per derivare se la piattaforma attuale utilizza o meno un sottolineaggio.

(Windows ha un'altra piccola modifica per alcune funzioni API di Windows per distinguere l'ANSI dalla versione Unicode. Ma probabilmente non è rilevante per il tuo caso.)

Forse qualcun altro può indicare una documentazione ufficiale per il C ABI su piattaforme diverse.

Autorizzato sotto: CC-BY-SA insieme a attribuzione
Non affiliato a StackOverflow
scroll top