简体   繁体   English

c#:如何知道DllImport中使用的dll的完整路径?

[英]c#: how to know the full path of dll used in DllImport?

I've import dll in my code like that: 我在我的代码中导入dll是这样的:

[DllImport("dll.dll", CharSet = CharSet.Ansi)]
    private static extern int function(String pars, StringBuilder err);

I was wondered that function works, but it is not inside project and not inside Debug or Release folders. 我想知道该函数是否有效,但它不在项目内部,也不在Debug或Release文件夹中。 Ie "dll.dll" should not be availabe because it is not in the current project folder, however it IS available. 即“dll.dll”不应该可用,因为它不在当前项目文件夹中,但是它可用。 Now I want to know the exact full path of the dll used at runtime, but don't know how to get it. 现在我想知道运行时使用的dll的确切完整路径,但不知道如何获取它。

You're going to have to use the win32 API. 您将不得不使用win32 API。

First use GetModuleHandle passing "dll.dll" to it. 首先使用GetModuleHandle传递“dll.dll”。 Then pass that handle to GetModuleFileName . 然后将该句柄传递给GetModuleFileName

string GetDllPath()
{
      const int MAX_PATH = 260;
      StringBuilder builder = new StringBuilder(MAX_PATH);
      IntPtr hModule = GetModuleHandle("dll.dll");  // might return IntPtr.Zero until 
                                                    // you call a method in  
                                                    // dll.dll causing it to be 
                                                    // loaded by LoadLibrary

      Debug.Assert(hModule != IntPtr.Zero);
      uint size = GetModuleFileName(hModule, builder, builder.Capacity);
      Debug.Assert(size > 0);
      return builder.ToString();   // might need to truncate nulls
}

    [DllImport("kernel32.dll", CharSet=CharSet.Auto)]
    public static extern IntPtr GetModuleHandle(string lpModuleName);

    [DllImport("kernel32.dll", SetLastError=true)]
    [PreserveSig]
    public static extern uint GetModuleFileName
    (
        [In] IntPtr hModule,        
        [Out] StringBuilder lpFilename,        
        [In][MarshalAs(UnmanagedType.U4)] int nSize
    );

See Dynamic-Link Library Search Order -- this should hold true with P/Invoke, but the behavior is slightly alterable depending upon load method. 请参阅动态链接库搜索顺序 - 这应该适用于P / Invoke,但行为稍有可变,具体取决于加载方法。 However it doesn't say how to determine the filename of a loaded DLL ;-) 但是它没有说明如何确定加载的DLL的文件名;-)


A completely un-tested and perhaps ill-advised solution to find the DLL path at run-time . 在运行时找到DLL路径的完全未经测试且可能是不明智的解决方案。 This assumes that P/Invoke and LoadLibrary use the same resolution (eg P/Invoke doesn't use LoadLibraryEx with LOAD_WITH_ALTERED_SEARCH_PATH) and that there are no awful conflicts with this approach. 这假设P / Invoke和LoadLibrary使用相同的分辨率(例如,P / Invoke不使用LoadLibraryEx和LOAD_WITH_ALTERED_SEARCH_PATH)并且与此方法没有可怕的冲突。

  1. Load the DLL with LoadLibrary or LoadLibaryEx . 使用LoadLibraryLoadLibaryEx加载DLL。

  2. Find the filename of the module using GetModuleFileName and the handle obtained in step #1. 使用GetModuleFileName和步骤#1中获得的句柄查找模块的文件名。

  3. Unload the module with FreeLibrary . 使用FreeLibrary卸载模块。 P/Invoke should keep the module reference-count > 0, but again, this is untested ;-) P / Invoke应该保持模块reference-count> 0,但是再次,这是未经测试的;-)

(There is no guarantee about the correctness or validity of the above solution. Suggestions, warnings and/or corrections welcome. YMMV.) (不保证上述解决方案的正确性或有效性。欢迎提出建议,警告和/或更正.YMMV。)

Happy coding. 快乐的编码。

If you really want to find out, use dependency-walker 如果你真的想知道 ,请使用dependency-walker

It can even 'monitor' your application in runtime and detect dynamic loads so nothing remains hidden 它甚至可以在运行时“监控”您的应用程序并检测动态负载,因此不会隐藏任何内容

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

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