2012-01-25 32 views
77

Ho una libreria di DLL con codice API C++ non gestito che è necessario utilizzare nell'applicazione .NET 4.0. Ma ogni metodo provo a caricare la mia dll ho un errore:Impossibile caricare DLL (Impossibile trovare il modulo HRESULT: 0x8007007E)

Unable to load DLL 'MyOwn.dll': The specified module could not be found. (Exception from HRESULT: 0x8007007E)

Ho letto e cercato soluzioni Severa ho trovato su internet. Niente funziona ..

Ho provato con metodi seguenti:

[DllImport("MyOwn.dll", CallingConvention = CallingConvention.Cdecl)] 
[return: MarshalAs((UnmanagedType.I4))] 
public static extern Int32 MyProIni(string DBname, string DBuser_pass, 
    string WorkDirectory, ref StringBuilder ErrorMessage); 

Quando ho provato dopo this article e quando ho eseguito questo esempio (dal codice scaricato) Viene eseguito senza un problema (la dll utilizzato è in la cartella bin/debug)

Ho copiato la mia DLL (insieme a tutti i file da cui dipende nella cartella bin).

Ho anche provato questo approccio, ma ho ottenuto lo stesso errore:

[DllImportAttribute(MyOwnLibDllPath, EntryPoint="TMproIni")] 
[return: MarshalAs(UnmanagedType.I4)] 
public static extern int MyproIni(string DBname, string DBuser_pass, 
    string WorkDirectory, ref StringBuilder ErrorMessage); 

Qualche suggerimento?

risposta

11

Prova a immettere il percorso completo della dll. Se non funziona, prova a copiare la DLL nella cartella system32.

+3

è va bene avere tutte le dipendenze nella cartella System32 e la mia DLL da qualche altra parte? –

4

Verificare che tutte le dipendenze della propria dll siano presenti vicino alla dll o in System32.

74

Da quello che mi ricordo su Windows l'ordine di ricerca per una DLL viene:

  1. Current Directory cartella System
  2. , C:\windows\system32 or c:\windows\SysWOW64 (per il processo a 32 bit in scatola a 64-bit).
  3. lettura dalla variabile Path ambiente

Inoltre mi piacerebbe verificare le dipendenze del DLL, il Dependency Walker fornito con Visual Studio può aiutarti qui, può anche essere scaricato gratuitamente: http://www.dependencywalker.com

+2

ha rilevato che manca una dipendenza (Oracle e qualche dll di IE). Ho bisogno di installare Oracle poiché la mia dll dipende da quello ... quindi lo saprò :) Trovato il problema con DependencyWalker;) –

+0

Nessun problema, mi sono risparmiate molte ore di grattacapi, ottimo piccolo strumento! :-) – display101

+0

+1 a Keith Halligan per aver suggerito DependencyWalker. Mi ha detto che non tutte le dipendenze avevano lo stesso tipo di CPU (x86/x64).Ho copiato tutti i file che avevano lo stesso tipo di CPU nella cartella bin della mia applicazione e questo ha risolto il problema. – DiligentKarma

2

Attivare la registrazione di fusione, vedere this question per un sacco di consigli su come farlo. Il debug di app in modalità mista che caricano i problemi può essere un vero dolore reale. La registrazione della fusione può essere di grande aiuto.

28

È possibile utilizzare lo strumento DUMPBIN per scoprire le dipendenze DLL richiesti:

dumpbin /DEPENDENTS my.dll 

questo vi dirà che la DLL DLL a deve caricare. Prestare particolare attenzione a MSVCR * .dll. Ho visto che il codice di errore si verifica quando non è installato il corretto ridistribuibile di Visual C++.

È possibile ottenere i "Pacchetti ridistribuibili di Visual C++ per Visual Studio 2013" dal sito Web di Microsoft. Si installa c: \ windows \ system32 \ MSVCR120.dll

Nel nome del file, 120 = 12.0 = Visual Studio 2013.

fare attenzione che avete il diritto versione di Visual Studio (10,0 = VS 10, 11 = VS 2012, 12.0 = VS 2013 ...) right architecture (x64 o x86) per la piattaforma di destinazione della tua DLL, e devi anche fare attenzione alle build di debug. La build di debug di una DLL dipende da MSVCR120d.dll che è una versione di debug della libreria, che viene installata con Visual Studio ma non dal pacchetto ridistribuibile.

+4

aggiungere i ridistribuibili VS C++ è stato per me! necessario v10.0 (2010). Grazie mille !!! –

+0

Esiste un modo per stabilire se sono necessarie versioni a 64 bit o 32 bit dei ridistribuibili? – BVB

+1

dumpbin/ALL ti dirà se my.dll è x86 di x64 –

2

Assicurarsi di impostare la Target piattaforma di costruzione su x86 o x64 in modo che sia compatibile con la DLL, che potrebbe essere compilata per una piattaforma a 32 bit.

2

Se i progetti DLL e .NET sono nella stessa soluzione e si desidera compilare ed eseguire entrambi ogni volta, è possibile fare clic con il pulsante destro del mouse sulle proprietà del progetto .NET, creare eventi, quindi aggiungere qualcosa come il seguente a post-generazione linea di comando evento:

copy $(SolutionDir)Debug\MyOwn.dll . 

e 'fondamentalmente una linea DOS ed è possibile modificare in base a dove la DLL è in costruzione a.

0

Penso che la tua biblioteca non gestita abbia bisogno di un manifest.
Here è come aggiungerlo al tuo binario. e here è il motivo.

In sintesi, diverse versioni di librerie ridistribuibili possono essere installate nella tua casella ma solo una di esse dovrebbe soddisfare la tua app e potrebbe non essere l'impostazione predefinita, quindi devi dire al sistema la versione richiesta dalla tua libreria, ecco perché il manifest.

2

Ho avuto lo stesso problema quando ho distribuito la mia applicazione per testare il PC. Il problema era lo sviluppo di PC aveva msvcp110d.dll e msvcr110d.dll ma non il PC di prova.

Ho aggiunto il modulo di unione "Visual Studio C++ 11.0 DebugCRT (x86)" in InstalledSheild e ha funzionato. Spero che questo sarà utile per qualcun altro.

7

La DLL deve trovarsi nella cartella bin.

In Visual Studio, aggiungo la dll al mio progetto (NON in Riferimenti, ma "Aggiungi file esistente"). Quindi impostare la proprietà "Copia nella directory di output" per la dll su "Copia se più recente".

1

Setup: 32-bit di Windows 7

Contesto: Installato un driver PCI-GPIB che ero in grado di comunicare attraverso a causa del problema di cui sopra.

Risposta breve: reinstallare il driver.

lungo Risposta: Ho anche usato Dependency Walker, che ha individuato diversi moduli di dipendenza mancanti. Immediatamente, ho pensato che doveva essere un'installazione di driver mal riuscita. Non volevo controllare e ripristinare ogni file mancante.

Il fatto che non sia stato possibile trovare il programma di disinstallazione in Programmi e funzionalità del Pannello di controllo è un altro indicatore di installazione errata. Ho dovuto cancellare manualmente un paio di * .dll in \ system32 e le chiavi di registro per consentire la reinstallazione del driver.

Problema risolto.

La parte inaspettata è stata che non tutti i moduli di dipendenza sono stati risolti. Tuttavia, il * .dll di interesse può ora essere referenziato.

3

C'è una cosa molto divertente (e ha una rilevanza tecnica) che potrebbero sprecare le ore così pensato di condividerlo qui -

Ho creato un progetto di applicazione di console ConsoleApplication1 e un progetto di libreria di classi ClassLibrary1.

Tutto il codice che stava facendo il p/invoke era presente in ClassLibrary1.dll. Quindi, prima di eseguire il debug dell'applicazione da Visual Studio ho semplicemente copiato l'assembly non gestito C++ (myUnmanagedFunctions.dll) nella directory \bin\debug\ del progetto ClassLibrary1 in modo che possa essere caricato in fase di esecuzione dal CLR.

ho continuato a ottenere l'errore

Unable to load DLL

per ore. In seguito mi sono reso conto che tutti gli assembly non gestiti che devono essere caricati devono essere copiati nella directory \bin\debug del progetto di avvio ConsoleApplication1 che di solito è un modulo di prova, una console o un'applicazione web.

Quindi, per favore sii cauto il Current Directory nella risposta accettata significa in realtà Current Directory dell'eseguibile principale da cui il processo dell'applicazione sta iniziando. Sembra una cosa ovvia ma potrebbe non esserlo a volte.

Lesson Learned - Posizionare sempre le DLL non classificate nella stessa directory dell'eseguibile di avvio per assicurarsi che sia possibile trovarle.

+0

Queste cose fisse anche per me. Sembra strano a mettere le DLL nel progetto principale al posto del progetto che le sta effettivamente utilizzando, anche se ... –

2

Si tratta di un 'kludge' ma si poteva almeno usare per sanity-test: Prova hard-codifica il percorso della DLL nel codice

[DllImport(@"C:\\mycompany\\MyDLL.dll")] 

Detto questo; nel mio caso l'esecuzione di dumpbin /DEPENDENTS come suggerito da @ anthony-hayward e la copia delle versioni di 32-bit delle DLL elencate nella mia directory di lavoro hanno risolto il problema per me.

Il messaggio è solo un po 'fuorviante, becuase non è "mio" dll che non può essere caricata - è le dipendenze

1

Ho incontrato lo stesso problema, nel mio caso ho avuto due 32 bit pc. Uno con .NET4.5 installato e l'altro era fresco PC.

mio 32 bit cpp dll (uscita modalità di compilazione) stava lavorando bene con .NET installato PC, ma non con il PC fresca dove ho ottenuto l'errore sotto

Unable to load DLL 'PrinterSettings.dll': The specified module could not be found. (Exception from HRESULT: 0x8007007E)

infine,

I just built my project in Debug mode configuration and this time my cpp dll was working fine.

+0

ha funzionato per me! Grazie – SaddamBinSyed

Problemi correlati