SafeWaitHandle 与 SafeFileHandle c#
SafeWaitHandle vs SafeFileHandle c#
我正在阅读 .net 框架源代码:
https://referencesource.microsoft.com
我发现 BCL 包含两个完全相同的 classes:SafeWaitHandle
和 SafeFileHandle
。两者的代码完全相同!
来自参考源 (SafeFileHandle):
[System.Security.SecurityCritical] // auto-generated_required
public sealed class SafeFileHandle: SafeHandleZeroOrMinusOneIsInvalid {
private SafeFileHandle() : base(true)
{
}
public SafeFileHandle(IntPtr preexistingHandle, bool ownsHandle) : base(ownsHandle) {
SetHandle(preexistingHandle);
}
[System.Security.SecurityCritical]
[ResourceExposure(ResourceScope.Machine)]
[ResourceConsumption(ResourceScope.Machine)]
override protected bool ReleaseHandle()
{
return Win32Native.CloseHandle(handle);
}
}
来自参考源 (SafeWaitHandle):
[System.Security.SecurityCritical] // auto-generated_required
public sealed class SafeWaitHandle : SafeHandleZeroOrMinusOneIsInvalid
{
// Called by P/Invoke marshaler
private SafeWaitHandle() : base(true)
{
}
[ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
public SafeWaitHandle(IntPtr existingHandle, bool ownsHandle) : base(ownsHandle)
{
SetHandle(existingHandle);
}
[System.Security.SecurityCritical]
[ResourceExposure(ResourceScope.Machine)]
[ResourceConsumption(ResourceScope.Machine)]
override protected bool ReleaseHandle()
{
return Win32Native.CloseHandle(handle);
}
}
我看到构造函数对 IntPtr
参数和 SafeWaitHandle 的注释有不同的名称,试图告诉我一些事情。但我无法理解,因为代码是平等的,据我所知,这些 classes 应该提供相同的行为。
有谁知道为什么微软的人创造了这些等于 classes 吗?为什么我应该更喜欢一个 class 而不是另一个?在什么情况下?
区别在于语义。大多数句柄都是相似的——只是对某些资源的引用(通常只是一个指针)。但是,区分它们很有用。如果你有一些接受 SafeFileHandle
的 api - 它不会接受 SafeWaitHandle
(或存在的其他类型的句柄),这可能会防止一些细微的错误。如果它改为接受一些抽象 Handle
- 那么有人可以在那里传递任何句柄,不代表对文件的引用。因此,不同类型的句柄由不同的 类 表示(即使具有相同的实现)+ C# 类型安全有利于防止将一种类型的句柄传递给预期另一种类型的句柄。
我正在阅读 .net 框架源代码: https://referencesource.microsoft.com
我发现 BCL 包含两个完全相同的 classes:SafeWaitHandle
和 SafeFileHandle
。两者的代码完全相同!
来自参考源 (SafeFileHandle):
[System.Security.SecurityCritical] // auto-generated_required
public sealed class SafeFileHandle: SafeHandleZeroOrMinusOneIsInvalid {
private SafeFileHandle() : base(true)
{
}
public SafeFileHandle(IntPtr preexistingHandle, bool ownsHandle) : base(ownsHandle) {
SetHandle(preexistingHandle);
}
[System.Security.SecurityCritical]
[ResourceExposure(ResourceScope.Machine)]
[ResourceConsumption(ResourceScope.Machine)]
override protected bool ReleaseHandle()
{
return Win32Native.CloseHandle(handle);
}
}
来自参考源 (SafeWaitHandle):
[System.Security.SecurityCritical] // auto-generated_required
public sealed class SafeWaitHandle : SafeHandleZeroOrMinusOneIsInvalid
{
// Called by P/Invoke marshaler
private SafeWaitHandle() : base(true)
{
}
[ReliabilityContract(Consistency.WillNotCorruptState, Cer.MayFail)]
public SafeWaitHandle(IntPtr existingHandle, bool ownsHandle) : base(ownsHandle)
{
SetHandle(existingHandle);
}
[System.Security.SecurityCritical]
[ResourceExposure(ResourceScope.Machine)]
[ResourceConsumption(ResourceScope.Machine)]
override protected bool ReleaseHandle()
{
return Win32Native.CloseHandle(handle);
}
}
我看到构造函数对 IntPtr
参数和 SafeWaitHandle 的注释有不同的名称,试图告诉我一些事情。但我无法理解,因为代码是平等的,据我所知,这些 classes 应该提供相同的行为。
有谁知道为什么微软的人创造了这些等于 classes 吗?为什么我应该更喜欢一个 class 而不是另一个?在什么情况下?
区别在于语义。大多数句柄都是相似的——只是对某些资源的引用(通常只是一个指针)。但是,区分它们很有用。如果你有一些接受 SafeFileHandle
的 api - 它不会接受 SafeWaitHandle
(或存在的其他类型的句柄),这可能会防止一些细微的错误。如果它改为接受一些抽象 Handle
- 那么有人可以在那里传递任何句柄,不代表对文件的引用。因此,不同类型的句柄由不同的 类 表示(即使具有相同的实现)+ C# 类型安全有利于防止将一种类型的句柄传递给预期另一种类型的句柄。