Reputation: 686
I'm having some problems with DllImport and ASP.NET because when I use a imported method ASP.NET loads the Dll and locks the file even after it finished using it. Is there any way to force ASP.NET to release the lock on the file?
Upvotes: 4
Views: 1163
Reputation: 116
Unloading the AppDomain is not the only answer. You can also use LoadLibrary
and FreeLibrary
over pinvoke to unload the library. Just make sure you're calling FreeLibrary
twice to ensure any dependencies of your library get unloaded as well.
I haven't tested this, but I imagine a class like this would make doing this easier:
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
private static extern IntPtr LoadLibrary(string libname);
[DllImport("kernel32.dll", CharSet = CharSet.Auto)]
private static extern bool FreeLibrary(IntPtr hModule);
class LibraryHandle
{
readonly string libName;
int refCount = 0;
IntPtr handle;
public LibraryHandle(string name)
{
libName = name;
}
public void Increment()
{
if (refCount == 0)
{
handle = LoadLibrary(libName);
if (Handle == IntPtr.Zero)
{
int error = Marshal.GetLastWin32Error();
throw new Exception(string.Format("{0})", error));
}
}
++refCount;
}
public void Decrement()
{
if (refCount <= 0)
return;
if (--refCount)
{
// It might be better in some cases to:
// while(FreeLibrary(handle));
FreeLibrary(handle);
FreeLibrary(handle);
}
}
}
Just be warned that this example is not thread safe, which you'll want to guarantee in ASP.NET, and doesn't do complete error checking.
Also, as this may violate some assumptions made by the runtime, using FreeLibrary
on a library you didn't load may not be a good idea.
Another alternative would be to perform whatever operation in a new AppDomain
and then unload it when you are done.
Upvotes: 0
Reputation: 14956
Only if you create a new AppDomain and load the dll into the domain. Afterwards you can unload the AppDomain and the dll will be unloaded.
Upvotes: 2
Reputation: 754505
The only way to force a DLL out of the process in .Net is to unload the AppDomain in which the Dll is loaded. Unless you create a separate AppDomain in which run the DllImport code this will not be possible.
Also I know this policy applies to managed DLL's. I am not 100% sure if this applies to DLL's loaded via PINvoke but I am fairly certain.
Upvotes: 2