簡體   English   中英

DllImport 在 Docker 上不起作用 - DllNotFoundException

[英]DllImport not working on Docker - DllNotFoundException

I have a project developed with .NET Core and C#, running on Docker, that has to call a few functions on a DLL developed with C++. The problem is: when I run my project without Docker, on Windows using Visual Code, the code runs smoothly, but when I run on Docker, on a Linux container, the code throws an error when trying to execute the DLL function.

我已經嘗試將 .dll 文件復制到 /lib 文件夾,將其更改為項目的父文件夾,但這些都不起作用。 我開始懷疑問題是找不到文件,通過研究,我發現它可能與文件權限有關,所以我對.dll 文件運行 chmod a+wrx ,也沒有成功。

這是我的 Dockerfile 配置:

FROM mcr.microsoft.com/dotnet/core/aspnet:2.2 AS base
WORKDIR /app
EXPOSE 80
RUN apt-get update \
    && apt-get install -y --allow-unauthenticated \
        libc6-dev \
        libgdiplus \
        libx11-dev \
     && rm -rf /var/lib/apt/lists/*
RUN apt-get update \
    && apt-get install -y poppler-utils

FROM mcr.microsoft.com/dotnet/core/sdk:2.2 AS build-env
WORKDIR /app
COPY . .
RUN dotnet restore --configfile Nuget.config -nowarn:msb3202,nu1503
RUN dotnet publish -c Release -o ./out 
    
FROM base AS final
WORKDIR /app
COPY --from=build-env /app/out .
ENTRYPOINT ["dotnet", "MdeGateway.dll"]

這是嘗試訪問 DLL function 的代碼:

[DllImport("MyDll.dll")]
private static extern int dllfunction(Int32 argc, IntPtr[] argv);

public static void CallDll(string[] args)
{
    IntPtr[] argv = ArrayToArgs(args);
    dllfunction(args.Length, argv);

    FreeMemory(args, argv);
}

當行 'dllfunction(args.Length, argv);' 時發生錯誤被執行。

確切的信息是:

“無法加載共享庫 'MyDll.dll' 或其依賴項之一。為了幫助診斷加載問題,請考慮設置LD_DEBUG環境變量:libMyDll.dll:無法打開共享 object 文件:沒有這樣的文件或目錄”

另外,如果有人可以教我如何設置LD_DEBUG環境變量,我將不勝感激。

I have a project developed with .NET Core and C#, running on Docker, that has to call a few functions on a DLL developed with C++. The problem is: when I run my project without Docker, on Windows using Visual Code, the code runs smoothly, but when I run on Docker, on a Linux container, the code throws an error when trying to execute the DLL function.

如果我沒看錯,那么您有一個 C++ 應用程序,您將其編譯為.dll (在 Windows 上)。 您可以將這個DllImport.dll上,但不能導入到 Linux(容器)上。 那正確嗎?

您是否知道 C++ 代碼編譯成.dll (共享庫)是 Windows 特定的東西? 非托管代碼是特定於體系結構和平台的。 在 x64 上編譯的非托管.dll不會在 arm64 上運行。 .dll上編譯的非托管 .dll 不會在 Linux 上運行。

Linux(和 Linux 容器,例如在 docker 中)不能使用從.dll上的非托管代碼構建的 .dll。 Linux 需要將非托管 (C++) 代碼編譯到共享庫( .so文件)中,以便DllImport (和底層dlopen調用)在 Linux 上工作。 理想情況下,與它將在其中運行的容器在同一平台上。

mono 文檔涵蓋了DllImport的(一個特定的)實現,並提供了有關它如何在 Linux 上工作的更多背景信息:

https://www.mono-project.com/docs/advanced/pinvoke/

(但請記住,Mono.= .NET Core。它仍然應該為您提供更多背景信息。)

這並不能解決 OP 的問題,但有助於回答他的第二個問題

另外,如果有人可以教我如何設置LD_DEBUG環境變量,我將不勝感激。

我面臨着類似的問題,並且也在努力理解如何處理這個LD_DEBUG變量。 事實證明,它控制了 Unix 動態 linker 的調試信息的詳細程度。

按照此處的建議,在 linux 終端中運行LD_DEBUG=help cat將為您提供設置LD_DEBUG的所有有效選項。

這是該命令的 output 的屏幕截圖: 在此處輸入圖像描述

其他有用的資源:

引用上面提到的 LD.SO 手冊頁:

LD_DEBUG(自 glibc 2.1 起) Output 有關動態 linker 操作的詳細調試信息。 此變量的內容是以下類別之一,以冒號、逗號或(如果引用值)空格分隔:

          help   Specifying help in the value of this variable does
                 not run the specified program, and displays a help
                 message about which categories can be specified in
                 this environment variable.

          all    Print all debugging information (except statistics
                 and unused; see below).

          bindings
                 Display information about which definition each
                 symbol is bound to.

          files  Display progress for input file.

          libs   Display library search paths.

          reloc  Display relocation processing.

          scopes Display scope information.

          statistics
                 Display relocation statistics.

          symbols
                 Display search paths for each symbol look-up.

          unused Determine unused DSOs.

          versions
                 Display version dependencies.

          Since glibc 2.3.4, LD_DEBUG is ignored in secure-execution
          mode, unless the file /etc/suid-debug exists (the content
          of the file is irrelevant).

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM