C# EventLog.Delete 拒绝访问

C# EventLog.Delete Access Denied

我已经阅读了有关安全和注册表项的其他问题,但没有任何内容可以帮助我解决我的特定用例场景。

这是我的场景:

我想做什么

我想在代码中删除一个 windows 事件日志。

问题

执行函数时,我收到 System.ComponentModel.Win32Exception。异常消息是 "Access is denied".

我目前是怎么做的

我正在使用我编写的模拟函数,它环绕 EventLog.Delete 函数,它使我进入具有对 EventLog Registry Hive 的完全访问权限的用户上下文。随后,我感兴趣的日志也对该特定用户具有完全访问权限。

我的问题

如果我 运行 下的用户(通过模拟)对相关日志具有完全访问权限,为什么我会收到 "Access Is Denied"?我已经测试了我的 Impersonation 函数,对于我编写的其他代码,它可以正常工作。我不明白为什么我会为此拒绝访问。

在另一个使用我的模拟函数的场景中,它工作得很好,例如,如果我试图写入一个文件,而该文件的用户上下文 运行 程序没有写入权限,那么我会无法写入文本文件,但是如果我使用我的模拟进入 确实 具有写入权限的用户上下文,那么它就可以正常工作(我可以写入文件) .所以我只是不明白为什么不能将相同的概念应用于注册表项。

我在这里错过了什么?

代码

  1. 异常消息

  2. 我的测试

其中 sw-test 是我为测试目的创建的用户,它对我们要删除的注册表具有完全访问权限。

        [TestMethod]
        public void DeleteEventLog_ValidatedUser_DeleteLog()
        {
            using (new Impersonator(Environment.UserDomainName, "sw-test", "pswd"))
            {
                Logging logging = new Logging();
                logging.DeleteEventLog("testLog");
            }
        }

好吧,我终于解决了这个问题,这里有两个问题导致上述异常被抛出,它们如下:

1. Visual Studio 未 运行 处于管理员模式。

Not 运行ning visual studio 在管理员模式下是问题的一部分,这似乎与 windows OS 中的访问令牌有关。根据我读到的消息来源,如果我 运行 一个没有打开 UAC 的程序(这是我的场景,我关闭了它),那么 运行 的程序会得到我的访问令牌的副本。但是,如果我启用了 UAC,程序会获取我的访问令牌的副本,但它是受限访问令牌。 (参见:What precisely does 'Run as administrator' do?)- 老实说,这对我来说没有意义,如果我关闭了 UAC,为什么我必须 运行 作为管理员? visual studio 不应该拥有我的访问令牌的不受限制的副本吗?我在 UAC 关闭的管理员组中...

2。未在模拟中将 NewCredentials 指定为 Logon32Type

我不太明白,但是当我为我的模拟指定这个时,一切都开始完美地工作,我读了一篇关于它的博客,它谈到了它是如何在 VISTA 时代引入的,以及它主要是如何用于指定到服务器的出站网络连接的凭据,主要用于修复服务器端的安全相关问题。不过,看不到它与本地事件日志的接口有何关联。 (参见:https://blogs.msdn.microsoft.com/winsdk/2015/08/25/logonuser-logon32_logon_new_credentials-what-is-this-flag-used-for/

代码

            using (new Impersonator(Environment.UserDomainName, "sw-test", "pswd", Advapi32.Logon32Type.NewCredentials))
            {
                EventLog.CreateEventSource("testSource", "testLog");
                EventLog.Delete("testLog");
            }

其中 NewCredentials 是一个整数 9