繁体   English   中英

无法加载文件或程序集

[英]Could not load file or assembly

我有一个简单的可执行文件,我想在其中使用dll。我已将其添加为参考。 我创建了一个app.config文件,因为dll最终不会在可执行文件目录中。 如果我从IDE执行程序,一切都很好,因为dll是在本地复制的,但是一旦我将可执行文件拉出,它就会崩溃。 我的融合日志暗示它找不到指定的文件。

我的Main()方法:

AppDomain currentDomain = AppDomain.CurrentDomain;
currentDomain.AssemblyResolve += new ResolveEventHandler(MyResolveEventHandler);

Assembly assembly = null;
String dllLocation = @"C:\BMS_ACTD\bin\DX\Tools\BmsReplayAnalysis.dll";
IToolsInterface myProgram = null; //from ToolsInterface.dll
try
{
    assembly = Assembly.LoadFrom(dllLocation);
}
catch
{
}

foreach (Type myType in assembly.GetTypes())
{
    if (myType.GetInterface(typeof(IToolsInterface).FullName) != null)
    {
        myProgram = (IToolsInterface)assembly.CreateInstance(myType.Namespace + "." + myType.Name, true);
        myProgram.RunTool();
        break;
    }
}

这是我的配置文件:

<runtime>
    <dependentAssembly>
        <assemblyIdentity name="ToolsInterface" publicKeyToken="null" culture="neutral" />
        <codeBase version="1.0.0.0" href="file://C:/BMS_ACTD/bin/DX/Globals/ToolsInterface.dll"/>
    </dependentAssembly>
</runtime>

我不想担心进行强命名。 我将只拥有该dll的1个版本,这就是我关心的全部。

这是Fusionlog的摘录:

The operation failed.
Bind result: hr = 0x80070002. The system cannot find the file specified.

Assembly manager loaded from:  C:\Windows\Microsoft.NET\Framework\v4.0.30319\clr.dll
Running under executable  C:\Users\greenj\Desktop\BmsReplayLauncher.exe
--- A detailed error log follows. 

=== Pre-bind state information ===
LOG: User = BMS-JMGREEN\greenj
LOG: DisplayName = ToolsInterface, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null
 (Fully-specified)
LOG: Appbase = file:///C:/Users/greenj/Desktop/
LOG: Initial PrivatePath = NULL
LOG: Dynamic Base = NULL
LOG: Cache Base = NULL
LOG: AppName = BmsReplayLauncher.exe
Calling assembly : BmsReplayLauncher, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null.
===
LOG: This bind starts in default load context.
LOG: Using application configuration file: C:\Users\greenj\Desktop\BmsReplayLauncher.exe.Config
LOG: Using host configuration file: 
LOG: Using machine configuration file from C:\Windows\Microsoft.NET\Framework\v4.0.30319\config\machine.config.
LOG: Policy not being applied to reference at this time (private, custom, partial, or location-based assembly bind).
LOG: Attempting download of new URL file:///C:/Users/greenj/Desktop/ToolsInterface.DLL.
LOG: Attempting download of new URL file:///C:/Users/greenj/Desktop/ToolsInterface/ToolsInterface.DLL.
LOG: Attempting download of new URL file:///C:/Users/greenj/Desktop/ToolsInterface.EXE.
LOG: Attempting download of new URL file:///C:/Users/greenj/Desktop/ToolsInterface/ToolsInterface.EXE.
LOG: All probing URLs attempted and failed.

如果您尝试从不在应用程序EXE位置的文件夹或子文件夹内的文件夹加载,则.net总是很棘手。 我建议尝试两件事。 首先,使用<probing>属性指定在哪里查找您的自定义DLL,请参见此答案 ,而不是您的操作方式。

其次,如果这不起作用,请尝试使用AppDomain.AssemblyResolve事件,而不是使用配置文件。 然后,您可以从任何地方加载程序集。

编辑 :杰伊·沃克(Jay Walker)指出.NET 4和更高版本更改了AssemblyResolve,因此,如果DLL是不在自定义文件夹中的DLL,则返回null以保留默认行为。

以下是AssemblyResolve的一些示例代码:

Assembly currentDomain_AssemblyResolve(object sender, ResolveEventArgs args)
{
    if (args.Name == THE_DLL_I_WANT_TO_CUSTOM_LOAD)
    {
        // Load from our custom path
        string finalPath = null;
        try
        {
            finalPath = MyCustomPath + args.Name.Substring(0, args.Name.IndexOf(",")) + ".dll";
            return Assembly.LoadFrom(finalPath);
        }
        catch ()
        {
        }
    }

    // Not our custom, use the default loading
    return null;
}

将MSDN引用为<codebase>

如果程序集具有强名称,则代码库设置可以位于本地Intranet或Internet上的任何位置。 如果程序集是私有程序集,则代码库设置必须是相对于应用程序目录的路径。

您的程序集没有任何强名称,因此您不能通过指定完整路径来使用此伪指令。 签名您的程序集(使用Visual Studio单击三下)或按照AresAvatar的建议使用AssemblyResolve

暂无
暂无

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

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