Newsgroup: it.comp.programmare.win32
Titolo: 100 Euro a chi mi risolve questo problema

Salve a tutti,
sono un programmatore hobbista o della domenica che dir si voglia, e sono
ormai molti giorni che combatto con questo problema senza riuscire a
risolverlo perciò adesso mi rivolgo a voi professionisti geni della
programmazione. Ho scandagliato la rete in lungo e in largo, l'ho rivoltata
come un pedalino, ho consultato libri, ma niente, nada di nada, mah .. boh,
molto probabilmente sono io una SCHIAPPA DISUMANA. 100 Euro a chi mi risolve
il problema, non stò scherzando (naturalmente solo al primo, non sono mica
milionario .... ehe, ehe).
Allora ....... io possiedo due files swedll32.lib e swedll32.dll realizzati
non da me ma da una società e quindi perfettamente funzionanti. Il problema
è che non riesco a chiamare le funzioni di questa DLL dalla mia
applicazione.
Lavoro con il Visual C++ 6.0 di Microsoft e con l'assistente ho realizzato
un applicazione MFC a documento singolo SDI. Dichiaro la funzione da
chiamare in cima al file ....Doc.h in questo modo:
extern "C" _declspec(dllimport) double swe_julday(int year, int month, int
day, double hour, int gregflag);
e poi la chiamo all'interno della classe del Documento in quest'altro modo:
double jd = swe_julday(2003,11,19,14,1);
I file swedll32.lib e swedll32.dll li ho copiati nella cartella del progetto
e la libreria swedll32.lib la dichiaro a VC++ tramita l'opzione di menu:
Project - Settings - Link
Quando compilo il programma il compilatore mi segnala quest'errore:
ProvaSwiss1Doc.obj : error LNK2001: unresolved external symbol
__imp__swe_julday
Debug/ProvaSwiss1.exe : fatal error LNK1120: 1 unresolved externals
Vi posso fornire tutto il necessario: cartella del mio progetto, vari file
sorgenti e file doc del produttore della libreria ecc. ecc.
Grazie a chi mi potrà o vorrà aiutare.
Lallo

 
Prova prima i consigli sopra.
Se "vinco" i 100 euro, dalli in beneficienza a Emergency.
-- 
Valter Minute
vmi...@inwind.it
 (the reply address of this message is invalid)

 Debug/ProvaSwiss1.exe : fatal error LNK1120: 1 unresolved externals
Verifica il prototipo della funzione come viene esportato dalla libreria.
Ad un primo tentativo, prova a dichiarare la funzione __stdcall.

 ha scritto nel messaggio 
news:3931loF...@individual.net...

forse il file .lib non è per il VC.
Prova a caricarla a runtime (puoi togliere il file .lib dal linker). Ti 
posto un mini esempio.
//----------------------------------------------------------------------------
// name è nella forma "_funzioneNellaDll"
static FARPROC getProc(HINSTANCE hI, LPCTSTR name)
{
  // prima prova con l'underscore
  FARPROC f = GetProcAddress(hI, name);
  if(!f)
    // prova senza underscore
    f = GetProcAddress(hI, name + 1);
  return f;
}
//----------------------------------------------------------------------------
extern "C"
{
  typedef void (*fzDllNoParam)();
  typedef bool (*fzDllWithParam)(uint id, LPCTSTR tetx, bool force);
}
fzDllNoParam DllNoParam;
fzDllWithParam DllWithParam;
//----------------------------------------------------------------------------
HMODULE loadLib()
{
    HMODULE h = LoadLibrary(_T("DllDaCaricare.dll"));
    while(h) {
      FARPROC f = getProc(h, _T("_primaFz"));
      if(!f)
        break;
      DllNoParam = (fzDllNoParam )f;
      f = getProc(h, _T("_secondaFz"));
      if(!f)
        break;
      DllWithParam = (fzDllWithParam )f;
      return h;
      }
    if(h)
        FreeLibrary(h);
  return 0;
}

 L'hai aggiunta alle librerie di input, immagino.
si
Lallo

 Ad un primo tentativo, prova a dichiarare la funzione __stdcall.
effettivamente sembrerebbe questa la soluzione:
extern "C" _stdcall swe_julday(int year, int month, int day, double hour,
int gregflag);
il compilatore non mi segnala più errori ... però, però, però .... questa
funzione riceve in ingresso una data e mi dovrebbe dare in uscita il numero
di giorni giuliani corrispondenti, però mi restituisce per qualsiasi data
sempre lo stesso numero errato 14368, inoltre questa funzione dovrebbe poter
ricevere come ultimo parametro le costanti simboliche SE_GREG_CAL o
SE_JUL_CAL (come specificato da file doc) ma in questo caso il compilatore
mi dice "Identificatore non dichiarato".
Altro problema: se dichiaro quest'altra funzione:
extern "C" _stdcall swe_calc_ut(double tjd_ut, int32 ipl, int32 iflag,
double *xx, char *serr);
il compilatore mi dice: error C2061: errore di sintassi : Identificatore
'int32'
Lallo


provo a risponderti domani
Lallo

 'int32'
Prova con _int32 
-- 
Luc

 
Quel @24 mi fa sospettare che si tratti di un nome "decorato" e questo 
potrebbe darti problemi se la DDL non è compilata con lo stesso 
compilatore che stai utilizzando tu.
Per ovviare al problema, come ti hanno già suggerito, puoi caricare 
dinamicamente la DLL e recuperare un puntatore con GetProcAddress (devi 
usare il nome decorato).
Buon lavoro


 'int32'
Stesso problema di prima. Ti manca la definizione del tipo int32 che 
probabilmente loro hanno definito in un header.
Intuisco però che puoi sostituirlo con DWORD.

 ha scritto nel
messaggio news:lL_Wd.628925$b5.28...@news3.tin.it...

Grazie anche a te logicMind, ora non so se posso ancora osare a chiederti
delle spiegazioni, visto che il premio è già stato vinto. Ci provo, quarda
un pò il codice seguente:
HMODULE CProvaSwiss2Doc::loadLib()
{
 HMODULE h = LoadLibrary(_T("swedll32.dll"));
    while(h) {
      FARPROC f = getProc(h, _T("_swe_julday"));
      if(!f)
        break;
      DllNoParam = (fzDllNoParam )f;
      f = getProc(h, _T("_swe_calc_ut")); // ma qui ci devo mettere il nome
di un'altra funzione DLL ?!?????
      if(!f)
        break;
      DllWithParam = (fzDllWithParam )f;
      return h;
      }
    if(h)
        FreeLibrary(h);
  return 0;
}
La funzione loadLib() una volta eseguita mi deve restituire un puntatore
alla funzione DLL caricata? così:  HMODULE pfunz = loadLib();
e come la devo chiamare?
Ciao,
Lallo


Ok, perfetto, funziona
Lallo

 Intuisco però che puoi sostituirlo con DWORD.
si, si, come mi hai spiegato prima manca una typedef, oppure come mi ha
suggerito Luc funziona anche con _int32
Bene, bene, bene sono molto contento, non ce posso credere, ho combattuto
per settimane con questo problema ..... e adesso proclamo il vincitore (and
the
winner is)  VINCENT VEGAAA!!!
A parte gli scherzi, un grazie di cuore a tutti coloro che mi hanno aiutato,
a Valter Minute, logicMind e Luc. Grazie ancora.
Vincent Vega, mandami in privato le tue coordinate bancarie, o meglio il
Bancoposta, o se vuoi ti mando un vaglia postale. Vedi un pò tu.
Ciao,
Lallo

 delle spiegazioni, visto che il premio è già stato vinto. <snip>
intanto ti serve la dichiarazione che metti in un file include
//-------------------------
extern "C"
{
   typedef double(*fzSweDll)(int year, int month, int day, double hour, int 
gregflag);
}
extern fzSweDll swe_julday;
//-------------------------
poi nel .cpp
fzSweDll swe_julday;
//-------------------------
ed il metodo diventa
//-------------------------
HMODULE CProvaSwiss2Doc::loadLib()
{
    HMODULE h = LoadLibrary(_T("swedll32.dll"));
    while(h) {
      FARPROC f = getProc(h, _T("_swe_julday"));
      if(!f)
        break;
      swe_julday = (fzSweDll )f;
    // trovata la funzione torna l'handle alla libreria per liberarla quando 
non serve più
      return h;
     }
    // se arrivi qui vuol dire che la funzione non è stata trovata, libera 
la dll e torna fallimento
    if(h)
        FreeLibrary(h);
  return 0;
}
//-------------------------
nel codice di inizio
    HMODULE pDll = loadLib();
    if(!pDll) {
        problemi con la dll e/o funzione
        esci o ....
        }
    double v = swe_julday(year, month, day, hour, gregflag);
    ....
    bla bla
     FreeLibrary(pDll);
fine 

 Bancoposta, o se vuoi ti mando un vaglia postale. Vedi un pò tu.
Allora, ABI... CAB... ;-)
Vai tranquillo, per oggi la mia giornata è già guadagnata ;)