我正在尝试将访问规则添加到RegistryKey
这样的:
using ( RegistryKey registry = OpenOrCreateMyKey() )
{
RegistrySecurity security = registry.GetAccessControl();
security.AddAccessRule( new RegistryAccessRule(
new SecurityIdentifier( WellKnownSidType.BuiltinUsersSid, null ),
RegistryRights.WriteKey,
InheritanceFlags.ContainerInherit | InheritanceFlags.ObjectInherit,
PropagationFlags.None,
AccessControlType.Allow ) );
registry.SetAccessControl( security );
}
但是,如果注册表被破坏,则会AddAccessRule
引发异常(Reflector 显示该GetAccessControl
调用预先确定它们不是规范的,并且当您在RegistrySecurity
实例处于该状态时尝试执行写入时,您会触发故障安全):
System.InvalidOperationException: This access control list is not in canonical form and therefore cannot be modified.
运行regedt32(可能还有regedit)然后显示一个弹出窗口the permissions on <key> are incorrectly ordered, which may cause some entries to be ineffective <paraphrasing>Do you want to unmangle them now? Y/N</paraprasing>
我在这个问题上看到的最权威的文章是http://www.codeproject.com/KB/system/accessctrl3.aspx,它说:
但是,控制标志是作为属性实现的(谈论不一致!)。
AreAccessRulesProtected
您可以从/检索自动继承设置AreAuditRulesProtected
(回想一下,如果 ACL 受保护,它不会自动继承)。如果您阅读第 2 部分,您会知道某些 Windows API 不支持继承,因此可能会破坏您机器的继承设置。好消息是 .NET 完全支持继承机制并将正确保留继承设置。如果您打开的安全描述符以某种方式获得了混乱的 ACL(可能来自某些流氓 Win32 应用程序),如果您尝试对其进行编辑,则会引发 InvalidOperationException。
通常,此类非规范 ACL 是使用 [sinceretired] NewSID 工具产生的,人们写知识库文章说“那就别再那样做了”。
但是,至关重要的是,这并不总是原因,有时代码只需要工作。有什么好的干净安全的方法来处理这个?
我将提供两个答案,人们可以投票和挑选漏洞、投票、评论和挑剔。