如何通过C#释放手柄?
我有一个隐式打开dll/文件句柄的应用程序。在应用程序中的某个时刻,我想释放这个句柄。我怎么做?我的应用程序在C#中。只需使用打开句柄的类的Dispose或Close方法。只需使用打开句柄的类的Dispose或Close方法。我不知道一个简单的方法。过度的隐式文件锁定是我一直不喜欢Windows的一点 如果需要替换该文件,MoveFileEx可以在下次引导时执行。您可以使用它来重命名或删除原始文件,然后将其他文件重命名到它的位置。 如果您不想直接干扰API,SysInternals套件中有一个MoveFile,它的作用与此相同: 或者,当您的程序未运行时,您可以让另一个程序访问该文件 如果您真的想关闭句柄,有很多方法可以获取每个进程的句柄列表,如果.NET再次尝试访问,很可能会导致程序崩溃。这并不漂亮,示例是C++:如何通过C#释放手柄?,c#,handle,filehandle,C#,Handle,Filehandle,我有一个隐式打开dll/文件句柄的应用程序。在应用程序中的某个时刻,我想释放这个句柄。我怎么做?我的应用程序在C#中。只需使用打开句柄的类的Dispose或Close方法。只需使用打开句柄的类的Dispose或Close方法。我不知道一个简单的方法。过度的隐式文件锁定是我一直不喜欢Windows的一点 如果需要替换该文件,MoveFileEx可以在下次引导时执行。您可以使用它来重命名或删除原始文件,然后将其他文件重命名到它的位置。 如果您不想直接干扰API,SysInternals套件中有一个
我不知道一个简单的方法。过度的隐式文件锁定是我一直不喜欢Windows的一点 如果需要替换该文件,MoveFileEx可以在下次引导时执行。您可以使用它来重命名或删除原始文件,然后将其他文件重命名到它的位置。 如果您不想直接干扰API,SysInternals套件中有一个MoveFile,它的作用与此相同: 或者,当您的程序未运行时,您可以让另一个程序访问该文件 如果您真的想关闭句柄,有很多方法可以获取每个进程的句柄列表,如果.NET再次尝试访问,很可能会导致程序崩溃。这并不漂亮,示例是C++:
你到底想做什么?如果你想加载一个程序集来完成一些事情,然后完全卸载它,你需要依赖于创建一个新的应用程序域
public static void Main(string[] args)
{
AppDomain appDomain = AppDomain.CreateDomain("NewAppDomain");
appDomain.DoCallBack(new CrossAppDomainDelegate(AsmLoad));
// At this point, your assembly is locked, you can't delete
AppDomain.Unload(appDomain);
Console.WriteLine("AppDomain unloaded");
//You've completely unloaded your assembly. Now if you want, you can delete the same
}
public static void AsmLoad()
{
Assembly assembly = Assembly.LoadFrom(@"c:\Yourassembly.dll");
//Loaded to the new app domain. You can do some stuff here
Console.WriteLine("Assembly loaded in {0}",AppDomain.CurrentDomain.FriendlyName);
}
更多信息,请查看此帖子
或者,如果你只是担心
保持文件锁定,您可以使用
阴影复制。那可以复制一份
磁盘上的文件,并从
新地点。原始文件
不会被该负载锁定。到
那样做,集合
AppDomainSetup.ShadowCopyFiles到
创建AppDomain或时为“true”
将AppDomain.ShadowCopyFiles设置为true
在它已经被创建之后
你到底想做什么?如果你想加载一个程序集来完成一些事情,然后完全卸载它,你需要依赖于创建一个新的应用程序域
public static void Main(string[] args)
{
AppDomain appDomain = AppDomain.CreateDomain("NewAppDomain");
appDomain.DoCallBack(new CrossAppDomainDelegate(AsmLoad));
// At this point, your assembly is locked, you can't delete
AppDomain.Unload(appDomain);
Console.WriteLine("AppDomain unloaded");
//You've completely unloaded your assembly. Now if you want, you can delete the same
}
public static void AsmLoad()
{
Assembly assembly = Assembly.LoadFrom(@"c:\Yourassembly.dll");
//Loaded to the new app domain. You can do some stuff here
Console.WriteLine("Assembly loaded in {0}",AppDomain.CurrentDomain.FriendlyName);
}
更多信息,请查看此帖子
或者,如果你只是担心
保持文件锁定,您可以使用
阴影复制。那可以复制一份
磁盘上的文件,并从
新地点。原始文件
不会被该负载锁定。到
那样做,集合
AppDomainSetup.ShadowCopyFiles到
创建AppDomain或时为“true”
将AppDomain.ShadowCopyFiles设置为true
在它已经被创建之后
如果有要关闭的处理程序,请使用PInvoke
[System.Runtime.InteropServices.DllImport("Kernel32")]
private extern static Boolean CloseHandle(IntPtr handle);
如果有要关闭的处理程序,请使用PInvoke
[System.Runtime.InteropServices.DllImport("Kernel32")]
private extern static Boolean CloseHandle(IntPtr handle);
有问题的文件是什么?它是资源还是引用的程序集?您似乎确实知道它为什么被打开,这是对它的用途和关闭时间的最好提示。介意让我们进去吗?280Z28说的一切。。。加上“卷影复制”-戳。我的应用程序使用GUI自动化工具在安装程序上进行一些测试。我启动安装程序,(xyx.exe)使用自动化工具生成的代码执行GUI操作,使用安装程序更新软件。在此期间,在“xyz.exe”上打开的句柄不会关闭。这是我想关上的把手。生成的代码包含所有静态成员,因此我无法调用Dispose或Close方法。我也不会加载程序集,因此我无法创建另一个应用程序域并在使用后卸载它。有问题的文件是什么?它是资源还是引用的程序集?您似乎确实知道它为什么被打开,这是对它的用途和关闭时间的最好提示。介意让我们进去吗?280Z28说的一切。。。加上“卷影复制”-戳。我的应用程序使用GUI自动化工具在安装程序上进行一些测试。我启动安装程序,(xyx.exe)使用自动化工具生成的代码执行GUI操作,使用安装程序更新软件。在此期间,在“xyz.exe”上打开的句柄不会关闭。这是我想关上的把手。生成的代码包含所有静态成员,因此我无法调用Dispose或Close方法。我也不会加载程序集,因此我无法创建另一个应用程序域,并在使用后卸载它。但我如何找到必须关闭的句柄呢。我只知道文件名。进程在该文件上打开的句柄未知。是否使用进程类启动exe?但如何找到必须关闭的句柄。我只知道文件名。我的进程在该文件上打开的句柄未知。是否使用进程类启动exe?