2012-01-28 47 views
2

我有下面的代码可用于各种ACE更改和添加和撤销 - 当我尝试并删除ACL中的ACE(显然存在)时,它不起作用,但此ACE是继承的。REVOKE_ACCESS:如何删除'撤销'继承的ACE?

用于撤销非继承ACE的SetEntriesInAcl()工作,减少了ACL ACE计数并且以下SetNamedSecurityInfo()被撤销并且ACE消失。

尽管ACE被继承 - 尽管这两个API返回SUCCESS - 但ACE不会被移除/撤销,但ACL ACE计数仍保持不变。

我也编码做DeleteAce()但是当DACL在SetNamedSecurityInfo()被再次使用的RC是SUCCESS(无返回码)和ACE仍然是我处理的文件夹 - 显然没有对如何删除一招继承了ACE。

顺便说一句,对于相同的文件夹问题SUBINACL命令行工具没有问题撤销这个继承的ACE。

    if(EqualSid(pSid_for_ace, pSid) ) 
        { /* ACE SID matched edit SID */ 

        if(cmd_se_edit == SE_REM) 
         { /* remove */ 

         rem_lst[ ace_idx ] = x; 

         exp_ace[ ace_idx ].grfAccessPermissions = dwAccessRights; 
         exp_ace[ ace_idx ].grfAccessMode  = REVOKE_ACCESS; 
         exp_ace[ ace_idx ].grfInheritance  = dwInheritance; 
         exp_ace[ ace_idx ].Trustee.TrusteeForm = TRUSTEE_IS_SID; 
         exp_ace[ ace_idx ].Trustee.TrusteeType = TRUSTEE_IS_WELL_KNOWN_GROUP; 
         exp_ace[ ace_idx ].Trustee.ptstrName = pSid; 

         if(ace_idx < (REMMAX-1)) ++ace_idx; 

         } /* remove */ 

        } /* ACE SID matched edit SID */ 

       pBA = (BYTE *)p_aceHdr; 

       ace_sz = p_aceHdr->AceSize; 

       p_aceHdr = (PACE_HEADER)&pBA[ ace_sz ]; 

       } /* loop through ACEs */ 


      // Create a new ACL that merges the new ACE 
      // into the existing DACL. 

      if(ace_idx) 
       { /* ACEs to remove */ 

       dwRes = SetEntriesInAcl(ace_idx, &exp_ace[0], 
                 pDacl, &pNewDacl); 
       if(ERROR_SUCCESS != dwRes) 
       { 
       printf("SetEntriesInAcl Error %u\n", dwRes); 
       goto Cleanup2; 
       } 

       // Attach the new ACL as the object's DACL. 

       dwRes = SetNamedSecurityInfo( ObjName, 
               ObjectType, 
               DACL_SECURITY_INFORMATION, 
               NULL, 
               NULL, 
               pNewDacl, 
               NULL); 

       if(ERROR_SUCCESS != dwRes) 
       { 
       rc3 = GetLastError(); 
       printf("SetNamedSecurityInfo Error %u\n", dwRes); 
       goto Cleanup2; 
       } 

       } /* ACEs to remove */ 
+0

访问权限掩码和继承设置与被撤销的ACE相同 - 每个MS指导(我发现的唯一指导)。 - 使用上面的代码设置此ACE会产生一个与我设置的ACE匹配的新ACE - 但最初继承的ACE仍然存在 - 对于此测试,ACL增长1,则此测试ACE的撤销正常工作 - 再次保留原始继承的ACE。 – kevinwaite 2012-01-28 15:02:11

+1

删除继承的ACE违反了ACL的规则。高级API不会让你这样做;低级的API会,但你不应该。相反,关闭目标对象上的继承并复制要保留的ACE,或者考虑使用Deny条目。 – 2012-02-01 03:02:26

+0

感谢哈利 - 以编程方式(通过API)**如何**关闭我的目标对象上的继承? - 我一直无法做到这一点(grrr).....一旦继承关闭 - 我知道如何复制一个ACE - 在你的评论中你说复制我希望保留的ACE - 将它们复制到哪里?有一次,你怎么把它们放回到“文件夹”的安全描述符 - 我知道一些API来做到这一点 - 我很好奇你的想法/见解....再次感谢,凯文威特 – kevinwaite 2012-02-02 07:09:24

回答

1

目前看起来好像是从文件夹中检索现有的ACL并对其进行修改。在你的情况下,你最好从头开始构建一个新的ACL。为此,请构建一个描述所需权限的EXPLICIT_ACCESS结构数组,并调用SetEntriesInAcl为OldAcl传递NULL。

要应用新的DACL,请按照您在代码中所做的相同方式调用SetNamedSecurityInfo,但为SecurityInfo传递DACL_SECURITY_INFORMATION | PROTECTED_DACL_SECURITY_INFORMATIONPROTECTED_DACL_SECURITY_INFORMATION标志禁止从父项继承。

+0

谢谢哈利!这工作。对于那些寻求更深入的阅读/信息检查这两个网址。 http://msdn.microsoft.com/en-us/magazine/cc163885.aspx#S3 - 和 - http://www.tenouk.com/ModuleH.html – kevinwaite 2012-02-08 15:06:25