2012-01-25 24 views
77

Mam bibliotekę DLL z niezarządzanym kodem API C++, który muszę użyć w mojej aplikacji .NET 4.0. Ale każda metoda próbuję załadować moje dll pojawia się błąd:Nie można załadować biblioteki DLL (moduł nie został znaleziony HRESULT: 0x8007007E)

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

Przeczytałem i sprawdzone rozwiązania Severa znalazłem w internecie. Nic nie działa ..

Próbowałem przy użyciu następujących metod:

[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); 

Kiedy próbowałem następujące this article i kiedy uruchomić ten przykład (z pobranego kodu) działa bez problemu (dll jest używany w folder bin/debug)

Skopiowałem moją bibliotekę DLL (wraz ze wszystkimi plikami, od których zależy to do mojego folderu bin).

Próbowałem też to podejście, ale mam ten sam błąd:

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

jakieś sugestie?

Odpowiedz

11

Spróbuj wprowadzić pełną ścieżkę biblioteki dll. Jeśli to nie zadziała, spróbuj skopiować plik dll do folderu system32.

+3

jest to jest ok mieć wszystkie zależności w folderze System32, a moja biblioteka dll gdzie indziej? –

4

Upewnij się, że wszystkie zależności własnej biblioteki dll są obecne w pobliżu biblioteki DLL lub w wersji System32.

74

Z tego co pamiętam na Windows kolejność wyszukiwania dla dll jest:

  1. Aktualny katalog
  2. folderu System, C:\windows\system32 or c:\windows\SysWOW64 (dla procesu 32-bitowej na 64-bitowym polu).
  3. Czytanie ze zmiennej Path środowiska

Ponadto chciałbym sprawdzić zależnościami DLL, zależność Walker wyposażony Visual Studio może pomóc tutaj, można również pobrać za darmo: http://www.dependencywalker.com

+2

znaleziono brak zależności (Oracle i niektóre dll z IE). Trzeba zainstalować Oracle, ponieważ moje dll zależy od tego .. potem będę wiedzieć :) Znalazłem problem z DependencyWalker;) –

+0

Nie martw się, to zaoszczędziło wiele godzin drapania głowy dla mnie, wielkie małe narzędzie! :-) – display101

+0

+1 do Keitha Halligana za sugestię DependencyWalker. Powiedział mi, że nie wszystkie zależności miały ten sam typ procesora (x86/x64).Skopiowałem wszystkie pliki, które miały ten sam typ procesora do folderu bin mojej aplikacji i to rozwiązało problem. – DiligentKarma

2

Włącz rejestrowanie fuzji, zobacz this question, aby uzyskać wiele porad, jak to zrobić. Debugowanie problemów z ładowaniem aplikacji w trybie mieszanym może być dobrym królewskim bólem. Rejestrowanie fuzji może być dużą pomocą.

28

Można użyć narzędzia DUMPBIN aby dowiedzieć się, wymaganych zależności DLL:

dumpbin /DEPENDENTS my.dll 

To powie Ci który bibliotek DLL DLL musi załadować. Szczególnie uważaj na MSVCR * .dll. Widziałem twój kod błędu występujący, gdy poprawny redystrybucyjny Visual C++ nie jest zainstalowany.

Możesz otrzymać "Pakiet redystrybucyjny Visual C++ dla Visual Studio 2013" ze strony internetowej Microsoft. Instaluje C: \ Windows \ system32 \ MSVCR120.dll

w nazwie pliku, 120 = 12,0 = Visual Studio 2013.

Bądź ostrożny, że masz odpowiednią wersję Visual Studio (10,0 = VS 10, 11 = VS 2012, 12,0 = VS 2013 ...) odpowiednią architekturę (x64 lub x86) dla docelowej platformy DLL, a także należy uważać na kompilacje debugowania. Wersja debugowania biblioteki DLL zależy od wersji MSVCR120d.dll, która jest wersją debugowania biblioteki, która jest instalowana z programem Visual Studio, ale nie z pakietu redystrybucyjnego.

+4

dodanie składników redystrybucyjnych VS C++ było dla mnie! potrzebne v10.0 (2010). Wielkie dzięki! –

+0

Czy istnieje sposób sprawdzenia, czy 64-bitowe lub 32-bitowe wersje składników redystrybucyjnych są wymagane? – BVB

+1

dumpbin/ALL powie ci, czy plik my.dll to x86 z x64 –

2

Upewnij się, że ustawisz opcję Buduj platformę na x86 lub x64, aby była kompatybilna z twoją biblioteką DLL - która może być kompilowana dla platformy 32-bitowej.

2

Jeśli projekty DLL i .NET są w tym samym rozwiązaniu i chcesz je skompilować i uruchomić za każdym razem, możesz kliknąć prawym przyciskiem myszy właściwości projektu .NET, Utwórz zdarzenia, a następnie dodać coś takiego do post-build wiersza polecenia event:

copy $(SolutionDir)Debug\MyOwn.dll . 

jest to w zasadzie linii DOS, można podkręcić na podstawie gdzie DLL jest zbudowany.

0

Myślę, że twoja niezarządzana biblioteka potrzebuje manifestu.
Here to sposób dodania go do pliku binarnego. i dlaczego jest to here.

Podsumowując, kilka wersji Biblioteki redystrybucyjnej może być zainstalowanych w twoim pudełku, ale tylko jedna z nich powinna zadowolić twoją Aplikację i może nie być domyślna, więc musisz powiedzieć systemowi, jakiej wersji potrzebuje twoja biblioteka, dlatego manifest.

2

Miałem ten sam problem, gdy wdrożyłem moją aplikację do testowania komputera. Problem polegał na tym, że komputer PC miał msvcp110d.dll i msvcr110d.dll, ale nie komputer testowy.

Dodałem moduł scalający "Visual Studio C++ 11.0 DebugCRT (x86)" w InstalledSheild i zadziałało. Mam nadzieję, że będzie to pomocne dla kogoś innego.

7

Biblioteka DLL musi znajdować się w folderze bin.

W Visual Studio dodaję bibliotekę DLL do mojego projektu (NIE w Referencjach, ale "Dodaj istniejący plik"). Następnie ustaw właściwość "Copy to Output Directory" dla biblioteki DLL na "Copy if newer".

1

Konfiguracja: 32-bitowy system Windows 7

Kontekst: Zainstalowany sterownik PCI-GPIB, że nie byłem w stanie komunikować się za pomocą powodu wspomnianej kwestii.

Krótka odpowiedź: Zainstaluj ponownie sterownik.

Długa odpowiedź: Użyłem także Dependency Walker, która zidentyfikowała kilka brakujących modułów zależności. Od razu pomyślałem, że musiała to być nieudana instalacja sterowników. Nie chciałem sprawdzać i przywracać każdego brakującego pliku.

Fakt, że nie udało mi się znaleźć dezinstalatora w obszarze Programy i funkcje Panelu sterowania, jest kolejnym wskaźnikiem nieprawidłowej instalacji. Musiałem ręcznie usunąć kilka *. Dll w \ system32 i klucze rejestru, aby umożliwić ponowną instalację sterownika.

Problem został rozwiązany.

Nieoczekiwana część polegała na tym, że nie wszystkie moduły zależności zostały rozwiązane. Niemniej można teraz odwoływać się do * .dll zainteresowania.

3

Jest jedna bardzo zabawna rzecz (a ma znaczenia technicznego), który może trać godzin, więc myślałem, dzielenia go tutaj -

I stworzył projekt aplikacji konsoli ConsoleApplication1 i projektu biblioteki klasy ClassLibrary1.

Cały kod, który spowodował, że p/invoke był obecny w ClassLibrary1.dll. Tak więc przed usunięciem debugowania aplikacji ze studia wizualnego po prostu skopiowałem niezarządzany zespół C++ (myUnmanagedFunctions.dll) do projektu \bin\debug\ katalogu ClassLibrary1, tak aby mógł zostać załadowany w czasie wykonywania przez CLR.

Ciągle otrzymuję błąd godzinami

Unable to load DLL

. Później zdałem sobie sprawę, że wszystkie takie niezarządzane zespoły, które mają zostać załadowane, muszą być skopiowane do katalogu początkowego projektu, który zwykle jest formą wygranej, konsolą lub aplikacją internetową.

Proszę więc bądź ostrożny, ponieważ Current Directory w zaakceptowanej odpowiedzi oznacza w rzeczywistości główny plik wykonywalny, od którego rozpoczyna się proces aplikacji. Wygląda to na oczywistą rzecz, ale może nie być tak czasami.

Odczytana lekcja - Zawsze umieszczaj pliki DLL niezamówione w tym samym katalogu, co plik wykonywalny uruchamiania, aby upewnić się, że można go znaleźć.

+0

To również naprawiło sytuację. Czuje się dziwnie, umieszczając biblioteki DLL w głównym projekcie zamiast projektu, który faktycznie ich używa, chociaż ... –

2

To jest „kludge” ale można przynajmniej używać go do normalności testu: Spróbuj ciężko kodowania ścieżkę do biblioteki DLL w kodzie

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

Mimo, że; w moim przypadku z uruchomieniem dumpbin /DEPENDENTS zgodnie z sugestią @ anthony-hayward i skopiowaniem ponad 32-bitowych wersji bibliotek DLL wymienionych w moim katalogu roboczym rozwiązał ten problem dla mnie.

Przesłanie jest tylko nieco mylące, ponieważ posiadał on nie jest „mój” dll, które nie mogą być załadowane - to Zależności

1

mam natknąć tego samego problemu, w moim przypadku miałem dwa 32 bit szt. Jeden z zainstalowanym .NET4.5 i drugi był świeżym komputerem.

moja 32-bitowy CPP dll (tryb Release Build) działa dobrze z .NET zainstalowany komputer, ale nie ze świeżych komputerze gdzie mam poniższy błąd

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

wreszcie

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

+0

pracował dla mnie! dzięki – SaddamBinSyed

Powiązane problemy