2012-01-28 17 views
2

以下のコードは、さまざまなACEの変更と追加と取り消しのために働いています。ACLにあるACEを削除しようとすると機能しませんが、このACEは継承されます。REVOKE_ACCESS:継承されたACEを '取り消し'する方法

継承されていないACEの取り消しのためのSetEntriesInAcl()は、ACL ACEカウントを減らし、次のように取り消しを行い、ACEがなくなったSetNamedSecurityInfo()を返します。

ACEが継承されても、これらのAPIの両方がSUCCESSを返したにもかかわらず、ACEが削除/取り消されなかった場合、ACL ACEの数は変わりません。

私もDeleteAce()をやってコード化されてきたが、そのDACLはSetNamedSecurityInfo()で使用されるとき、再びRCはSUCCESS(ノーリターンコード)で、ACEは、私が扱っていたフォルダのために残っている - 明確に削除する方法についてのトリックがあります継承されたACE。

Btw、問題の同じフォルダ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

アクセス許可のマスクと継承の設定は、MSガイダンスごとに取り消されるACEと同じです(唯一のガイダンスです)。 - 上記のコードでこのACEを設定すると、設定したものと一致する新しいACEが作成されます。元の継承されたACEが残っています。このテストではACLが1増加しました。このテストACEの取り消しは正しく機能しました。元のACEが継承されました。 – kevinwaite

+1

継承されたACEを削除すると、ACLの規則が破損します。高水準のAPIはこれを行うことはできません。低レベルのAPIはありますが、そうしないでください。代わりに、対象オブジェクトの継承をオフにして、保持したいACEをコピーするか、代わりに拒否エントリを使用することを検討してください。 –

+0

ありがとうHarry - プログラムで(APIを介して)**どのように私のターゲットオブジェクトの継承をオフにするのですか? - 私はこれを行うことができませんでした。(grrr).....継承が解除されたら - 私はACEをコピーする方法を知っています - あなたのコメントで、私が残したいACEをコピーすると言う - ?一度そこに「フォルダーの」セキュリティ記述子に戻す方法 - 私はそれを行うためのいくつかのAPIを知っています - 私はあなたの思考/洞察に興味があります....ありがとう、再びKevin Waiteに関して – kevinwaite

答えて

1

フォルダから既存のACLを取得し、それを変更しているかのように見えます。あなたの状況では、最初から新しいACLを作成する方が良いでしょう。これを行うには、必要なアクセス許可を示すEXPLICIT_ACCESS構造体の配列を作成し、OldAclにNULLを渡すSetEntriesInAclを呼び出します。

新しいDACLを適用するには、コードと同じ方法でSetNamedSecurityInfoを呼び出しますが、SecurityInfoにはDACL_SECURITY_INFORMATION | PROTECTED_DACL_SECURITY_INFORMATIONを渡します。 PROTECTED_DACL_SECURITY_INFORMATIONフラグは、親からの継承を無効にします。

+0

ありがとうハリー!これはうまくいった。より精通した読書/情報を求める方は、これらの2つのURLを確認してください。 http://msdn.microsoft.com/en-us/magazine/cc163885.aspx#S3-and- http://www.tenouk.com/ModuleH.html – kevinwaite

関連する問題