关于MSDN代码示例,“启用和禁用权限”

时间:2012-10-26 04:52:23

标签: c++ windows winapi

MSDN文章Enabling and Disabling Privileges in C++提供了一个代码示例,说明如何在访问令牌中启用或禁用权限。

我引用了被质疑的部分:

tp.PrivilegeCount = 1;
tp.Privileges[0].Luid = luid;
if (bEnablePrivilege)
    tp.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
else
    tp.Privileges[0].Attributes = 0;


Attributes成员的零值是什么意思?

根据TOKEN_PRIVILEGES结构的文档,特权的属性可以是以下值的组合:

  • SE_PRIVILEGE_ENABLEDWinNT.h 0x00000002L
  • SE_PRIVILEGE_ENABLED_BY_DEFAULTWinNT.h 0x00000001L
  • SE_PRIVILEGE_REMOVEDWinNT.h 0x00000004L
  • SE_PRIVILEGE_USED_FOR_ACCESSWinNT.h 0x80000000L

因此,我们没有看到任何值为零的有效常量。我想,零等于SE_PRIVILEGE_REMOVED

再一次,如果零意味着禁用所有权限,我对此表示怀疑,因为只需将AdjustTokenPrivileges()DisableAllPrivileges参数设置为TRUE即可禁用所有权限。

这里有人可以解释零值真正的作用吗?

2 个答案:

答案 0 :(得分:4)

禁用特权之间存在差异,允许您稍后再次启用该特权,从令牌中删除特权。删除权限意味着以后不能重新启用。

传递零意味着未设置SE_PRIVILEGE_ENABLED位,因此禁用该权限。

令牌在创建时包含许多权限。默认情况下始终启用SeChangeNotifyPrivilege,即本地安全策略/组策略的“用户权限分配”部分中的“旁路遍历检查”,并且不应禁用{有关详细信息,请参阅KB823659 )。因此DisableAllPrivileges参数实际上并没有用。

用户帐户控制(Windows Vista和更高版本)获取原始登录令牌,克隆它,并使用SE_PRIVILEGE_REMOVED标志创建用于启动shell的“过滤令牌”。然后隐藏原始令牌,以便“以管理员身份运行”功能可以使用它来启动程序。

您可以使用Sysinternals Process Explorer查看流程令牌中启用的权限。

答案 1 :(得分:1)

If SE_PRIVILEGE_REMOVED相当于零,它将被定义为零。鉴于那里的定义,我建议零值意味着从未启用或随后使用/删除任何权限:有,也从来没有任何令牌权限。