繁体   English   中英

DLLImport可在VS中使用,但不能在IIS中使用

[英]DLLImport works in VS but not in IIS

我们有使用第三方DLL的Soap Webservice项目。 在Visual Studio中,当我运行该程序时,它可以完美运行。 它可以找到dll。 但是,当我将项目放入IIS时,We​​b服务无法找到dll。 这是下面的DLLImport部分。

[DllImport(@"/dll/y1d431_mit.dll",
        EntryPoint = "Y1DPackG", SetLastError = false, ExactSpelling = true)]
    private static extern void Y1DPackG(ref int ErrorNumb, ref int ErrorMsgs,
        string RegCustomer, int RegPassword, int CostOptim, int IgnoreLast,
        int EffortLev, int ReduceLays, int PrefShort, int DiffStocks,
        int DiffPieces, int ReusLength, int GapItIt, int GapItEnd,
        int GapGripEnd, int OptimTime, int IterMult, int LayByMark,
        int RunMsgMode, int ReservInp2, ref int StockGrLth, ref int StockGrCst,
        ref short StockGrQty, ref int PartGrLth, ref int PartGrMrkID, ref short PartGrQty,
        ref int Critsum, ref int Effsum, ref int StockSum, ref int PartSum,
        ref int LengthSum, ref int WasteSum, ref int CostSum, ref int LastStockNo,
        ref int LastParts, ref int LastLength, ref int LastWaste, ref int LastCost,
        ref int PatternSum, ref int LayoutSum, ref int LayoutCuts, ref int ReservOut1,
        ref int ReservOut2, ref short StockGrNo, ref short PartGrNo, ref short PartStockNo,
        ref short StockLayNo, ref short StockPatNo, ref short StockParts, ref int StockWaste);

IIS根据DLLImport语句在哪里寻找dll文件? 我应该在哪里根据DLLIMPORT语句放置dll文件,以便IIS找到它?

加载Sysinternal的免费进程监视器 在运行执行dllimport的代码之前立即启动它,并在出现错误后停止事件收集。 该工具将告诉您发生的每件事,包括IIS在哪里开始搜索。 它还会告诉您是否遇到权限错误。

如果它是64位系统上的32位dll,则可能会出现权限错误,因为该dll随后将通过WOW64运行,并且很可能复制到WOW64目录中以供执行。 默认情况下,这不是任何匿名Internet用户帐户都可以访问的目录。

谢谢马克。 Process Monitor准确地显示了Windows在哪里寻找我的DLLImport非托管/本机DLL及其所有从属/导入。 我找到2种方法来找到我的DLL:

方法1:SetDllDirectory()

using System.Web;

public myClass
{
    private static bool dllIsLoaded = false;

    [DllImport("kernel32.dll", CharSet = CharSet.Unicode, SetLastError = true)]
    [return: MarshalAs(UnmanagedType.Bool)]
    static extern bool SetDllDirectory(string lpPathName);

    public void myDllLoader()
    {
        if (!dllIsLoaded)
        {
#if DEBUG
            string dllDir = Path.Combine(HttpRuntime.AppDomainAppPath, @"Lib\Debug\");
#else
            string dllDir = Path.Combine(HttpRuntime.AppDomainAppPath, @"Lib\Release\");
#endif
            SetDllDirectory(dllDir);
             // Call any function in your DLL to load it.  Stays loaded for the duration of the app.
            string ver = myDllGetVersion();
            SetDllDirectory("");    // Reset path to original

            dllIsLoaded = true;
        }
    }
}

方法#2:在PATH环境变量中添加DLL的我的应用程序目录:

using System.Web;

string dllDir = Path.Combine(HttpRuntime.AppDomainAppPath, @"myAppDLLDirectory\");
string currentPath = Environment.GetEnvironmentVariable("path");
Environment.SetEnvironmentVariable("path", $"{dllDir};{currentPath}");

PATH的此修改仅影响当前进程。

ps如果您的错误消息说它找不到您的DLL,但是您的DLL在DLL搜索路径中,则实际上可能意味着找不到您要导入的DLL之一。 例如,我的DLL依赖于开发计算机上的“ vcruntime140d.dll”和“ ucrtbased.dll”,而不依赖于要部署到的服务器。 使用“ dumpbin.exe / imports my.dll”列出依赖项。 可从Visual Studio“ x64本机工具命令提示符”中获得转储。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM