LCOV - code coverage report
Current view: top level - libcli/security - access_check.c (source / functions) Hit Total Coverage
Test: coverage report for recycleplus df22b230 Lines: 236 271 87.1 %
Date: 2024-02-14 10:14:15 Functions: 11 11 100.0 %

          Line data    Source code
       1             : /*
       2             :    Unix SMB/CIFS implementation.
       3             : 
       4             :    Copyright (C) Andrew Tridgell 2004
       5             :    Copyright (C) Gerald Carter 2005
       6             :    Copyright (C) Volker Lendecke 2007
       7             :    Copyright (C) Jeremy Allison 2008
       8             :    Copyright (C) Andrew Bartlett 2010
       9             : 
      10             :    This program is free software; you can redistribute it and/or modify
      11             :    it under the terms of the GNU General Public License as published by
      12             :    the Free Software Foundation; either version 3 of the License, or
      13             :    (at your option) any later version.
      14             : 
      15             :    This program is distributed in the hope that it will be useful,
      16             :    but WITHOUT ANY WARRANTY; without even the implied warranty of
      17             :    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
      18             :    GNU General Public License for more details.
      19             : 
      20             :    You should have received a copy of the GNU General Public License
      21             :    along with this program.  If not, see <http://www.gnu.org/licenses/>.
      22             : */
      23             : 
      24             : #include "includes.h"
      25             : #include "libcli/security/security.h"
      26             : 
      27             : /* Map generic access rights to object specific rights.  This technique is
      28             :    used to give meaning to assigning read, write, execute and all access to
      29             :    objects.  Each type of object has its own mapping of generic to object
      30             :    specific access rights. */
      31             : 
      32       65036 : void se_map_generic(uint32_t *access_mask, const struct generic_mapping *mapping)
      33             : {
      34       65036 :         uint32_t old_mask = *access_mask;
      35             : 
      36       65036 :         if (*access_mask & GENERIC_READ_ACCESS) {
      37         105 :                 *access_mask &= ~GENERIC_READ_ACCESS;
      38         105 :                 *access_mask |= mapping->generic_read;
      39             :         }
      40             : 
      41       65036 :         if (*access_mask & GENERIC_WRITE_ACCESS) {
      42           2 :                 *access_mask &= ~GENERIC_WRITE_ACCESS;
      43           2 :                 *access_mask |= mapping->generic_write;
      44             :         }
      45             : 
      46       65036 :         if (*access_mask & GENERIC_EXECUTE_ACCESS) {
      47         103 :                 *access_mask &= ~GENERIC_EXECUTE_ACCESS;
      48         103 :                 *access_mask |= mapping->generic_execute;
      49             :         }
      50             : 
      51       65036 :         if (*access_mask & GENERIC_ALL_ACCESS) {
      52         109 :                 *access_mask &= ~GENERIC_ALL_ACCESS;
      53         109 :                 *access_mask |= mapping->generic_all;
      54             :         }
      55             : 
      56       65036 :         if (old_mask != *access_mask) {
      57         113 :                 DEBUG(10, ("se_map_generic(): mapped mask 0x%08x to 0x%08x\n",
      58             :                            old_mask, *access_mask));
      59             :         }
      60       65036 : }
      61             : 
      62             : /* Map generic access rights to object specific rights for all the ACE's
      63             :  * in a security_acl.
      64             :  */
      65             : 
      66        3181 : void security_acl_map_generic(struct security_acl *sa,
      67             :                                 const struct generic_mapping *mapping)
      68             : {
      69             :         unsigned int i;
      70             : 
      71        3181 :         if (!sa) {
      72           0 :                 return;
      73             :         }
      74             : 
      75       31602 :         for (i = 0; i < sa->num_aces; i++) {
      76       28421 :                 se_map_generic(&sa->aces[i].access_mask, mapping);
      77             :         }
      78             : }
      79             : 
      80             : /* Map standard access rights to object specific rights.  This technique is
      81             :    used to give meaning to assigning read, write, execute and all access to
      82             :    objects.  Each type of object has its own mapping of standard to object
      83             :    specific access rights. */
      84             : 
      85           2 : void se_map_standard(uint32_t *access_mask, const struct standard_mapping *mapping)
      86             : {
      87           2 :         uint32_t old_mask = *access_mask;
      88             : 
      89           2 :         if (*access_mask & SEC_STD_READ_CONTROL) {
      90           0 :                 *access_mask &= ~SEC_STD_READ_CONTROL;
      91           0 :                 *access_mask |= mapping->std_read;
      92             :         }
      93             : 
      94           2 :         if (*access_mask & (SEC_STD_DELETE|SEC_STD_WRITE_DAC|SEC_STD_WRITE_OWNER|SEC_STD_SYNCHRONIZE)) {
      95           0 :                 *access_mask &= ~(SEC_STD_DELETE|SEC_STD_WRITE_DAC|SEC_STD_WRITE_OWNER|SEC_STD_SYNCHRONIZE);
      96           0 :                 *access_mask |= mapping->std_all;
      97             :         }
      98             : 
      99           2 :         if (old_mask != *access_mask) {
     100           0 :                 DEBUG(10, ("se_map_standard(): mapped mask 0x%08x to 0x%08x\n",
     101             :                            old_mask, *access_mask));
     102             :         }
     103           2 : }
     104             : 
     105             : /*
     106             :   perform a SEC_FLAG_MAXIMUM_ALLOWED access check
     107             : */
     108       15953 : static uint32_t access_check_max_allowed(const struct security_descriptor *sd,
     109             :                                          const struct security_token *token,
     110             :                                          enum implicit_owner_rights implicit_owner_rights)
     111             : {
     112       15953 :         uint32_t denied = 0, granted = 0;
     113       15953 :         bool am_owner = false;
     114       15953 :         bool have_owner_rights_ace = false;
     115             :         unsigned i;
     116             : 
     117       15953 :         if (sd->dacl == NULL) {
     118           0 :                 if (security_token_has_sid(token, sd->owner_sid)) {
     119           0 :                         switch (implicit_owner_rights) {
     120           0 :                         case IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS:
     121           0 :                                 granted |= SEC_STD_WRITE_DAC;
     122             :                                 FALL_THROUGH;
     123           0 :                         case IMPLICIT_OWNER_READ_CONTROL_RIGHTS:
     124           0 :                                 granted |= SEC_STD_READ_CONTROL;
     125           0 :                                 break;
     126             :                         }
     127             :                 }
     128           0 :                 return granted;
     129             :         }
     130             : 
     131       15953 :         if (security_token_has_sid(token, sd->owner_sid)) {
     132             :                 /*
     133             :                  * Check for explicit owner rights: if there are none, we remove
     134             :                  * the default owner right SEC_STD_WRITE_DAC|SEC_STD_READ_CONTROL
     135             :                  * from remaining_access. Otherwise we just process the
     136             :                  * explicitly granted rights when processing the ACEs.
     137             :                  */
     138        2291 :                 am_owner = true;
     139             : 
     140       22727 :                 for (i=0; i < sd->dacl->num_aces; i++) {
     141       20436 :                         struct security_ace *ace = &sd->dacl->aces[i];
     142             : 
     143       20436 :                         if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) {
     144           9 :                                 continue;
     145             :                         }
     146             : 
     147       20427 :                         have_owner_rights_ace = dom_sid_equal(
     148       20427 :                                 &ace->trustee, &global_sid_Owner_Rights);
     149       20427 :                         if (have_owner_rights_ace) {
     150           0 :                                 break;
     151             :                         }
     152             :                 }
     153             :         }
     154             : 
     155       15953 :         if (am_owner && !have_owner_rights_ace) {
     156        2291 :                 switch (implicit_owner_rights) {
     157        2291 :                 case IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS:
     158        2291 :                         granted |= SEC_STD_WRITE_DAC;
     159             :                         FALL_THROUGH;
     160        2291 :                 case IMPLICIT_OWNER_READ_CONTROL_RIGHTS:
     161        2291 :                         granted |= SEC_STD_READ_CONTROL;
     162        2291 :                         break;
     163             :                 }
     164             :         }
     165             : 
     166       50331 :         for (i = 0;i<sd->dacl->num_aces; i++) {
     167       34378 :                 struct security_ace *ace = &sd->dacl->aces[i];
     168       34378 :                 bool is_owner_rights_ace = false;
     169             : 
     170       34378 :                 if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) {
     171           9 :                         continue;
     172             :                 }
     173             : 
     174       34369 :                 if (am_owner) {
     175       20427 :                         is_owner_rights_ace = dom_sid_equal(
     176       20427 :                                 &ace->trustee, &global_sid_Owner_Rights);
     177             :                 }
     178             : 
     179       34369 :                 if (!is_owner_rights_ace &&
     180       34369 :                     !security_token_has_sid(token, &ace->trustee))
     181             :                 {
     182       17282 :                         continue;
     183             :                 }
     184             : 
     185       17087 :                 switch (ace->type) {
     186       17078 :                 case SEC_ACE_TYPE_ACCESS_ALLOWED:
     187       17078 :                         granted |= ace->access_mask;
     188       17078 :                         break;
     189           0 :                 case SEC_ACE_TYPE_ACCESS_DENIED:
     190             :                 case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
     191           0 :                         denied |= ~granted & ace->access_mask;
     192           0 :                         break;
     193           9 :                 default:        /* Other ACE types not handled/supported */
     194           9 :                         break;
     195             :                 }
     196             :         }
     197             : 
     198       15953 :         return granted & ~denied;
     199             : }
     200             : 
     201       22411 : static NTSTATUS se_access_check_implicit_owner(const struct security_descriptor *sd,
     202             :                                                const struct security_token *token,
     203             :                                                uint32_t access_desired,
     204             :                                                uint32_t *access_granted,
     205             :                                                enum implicit_owner_rights implicit_owner_rights)
     206             : {
     207             :         uint32_t i;
     208             :         uint32_t bits_remaining;
     209       22411 :         uint32_t explicitly_denied_bits = 0;
     210       22411 :         bool am_owner = false;
     211       22411 :         bool have_owner_rights_ace = false;
     212             : 
     213       22411 :         *access_granted = access_desired;
     214       22411 :         bits_remaining = access_desired;
     215             : 
     216             :         /* handle the maximum allowed flag */
     217       22411 :         if (access_desired & SEC_FLAG_MAXIMUM_ALLOWED) {
     218        2338 :                 uint32_t orig_access_desired = access_desired;
     219             : 
     220        2338 :                 access_desired |= access_check_max_allowed(sd, token, implicit_owner_rights);
     221        2338 :                 access_desired &= ~SEC_FLAG_MAXIMUM_ALLOWED;
     222        2338 :                 *access_granted = access_desired;
     223        2338 :                 bits_remaining = access_desired;
     224             : 
     225        2338 :                 DEBUG(10,("se_access_check: MAX desired = 0x%x, granted = 0x%x, remaining = 0x%x\n",
     226             :                         orig_access_desired,
     227             :                         *access_granted,
     228             :                         bits_remaining));
     229             :         }
     230             : 
     231             :         /* a NULL dacl allows access */
     232       22411 :         if ((sd->type & SEC_DESC_DACL_PRESENT) && sd->dacl == NULL) {
     233          19 :                 *access_granted = access_desired;
     234          19 :                 return NT_STATUS_OK;
     235             :         }
     236             : 
     237       22392 :         if (sd->dacl == NULL) {
     238           0 :                 goto done;
     239             :         }
     240             : 
     241       22392 :         if (security_token_has_sid(token, sd->owner_sid)) {
     242             :                 /*
     243             :                  * Check for explicit owner rights: if there are none, we remove
     244             :                  * the default owner right SEC_STD_WRITE_DAC|SEC_STD_READ_CONTROL
     245             :                  * from remaining_access. Otherwise we just process the
     246             :                  * explicitly granted rights when processing the ACEs.
     247             :                  */
     248        6925 :                 am_owner = true;
     249             : 
     250       57774 :                 for (i=0; i < sd->dacl->num_aces; i++) {
     251       50849 :                         struct security_ace *ace = &sd->dacl->aces[i];
     252             : 
     253       50849 :                         if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) {
     254        4567 :                                 continue;
     255             :                         }
     256             : 
     257       46282 :                         have_owner_rights_ace = dom_sid_equal(
     258       46282 :                                 &ace->trustee, &global_sid_Owner_Rights);
     259       46282 :                         if (have_owner_rights_ace) {
     260           0 :                                 break;
     261             :                         }
     262             :                 }
     263             :         }
     264       22392 :         if (am_owner && !have_owner_rights_ace) {
     265        6925 :                 switch (implicit_owner_rights) {
     266        6925 :                 case IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS:
     267        6925 :                         bits_remaining &= ~SEC_STD_WRITE_DAC;
     268             :                         FALL_THROUGH;
     269        6925 :                 case IMPLICIT_OWNER_READ_CONTROL_RIGHTS:
     270        6925 :                         bits_remaining &= ~SEC_STD_READ_CONTROL;
     271        6925 :                         break;
     272             :                 }
     273             :         }
     274             : 
     275             :         /* check each ace in turn. */
     276       51287 :         for (i=0; bits_remaining && i < sd->dacl->num_aces; i++) {
     277       28895 :                 struct security_ace *ace = &sd->dacl->aces[i];
     278       28895 :                 bool is_owner_rights_ace = false;
     279             : 
     280       28895 :                 if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) {
     281         450 :                         continue;
     282             :                 }
     283             : 
     284       28445 :                 if (am_owner) {
     285        9795 :                         is_owner_rights_ace = dom_sid_equal(
     286        9795 :                                 &ace->trustee, &global_sid_Owner_Rights);
     287             :                 }
     288             : 
     289       28445 :                 if (!is_owner_rights_ace &&
     290       28445 :                     !security_token_has_sid(token, &ace->trustee))
     291             :                 {
     292        7413 :                         continue;
     293             :                 }
     294             : 
     295       21032 :                 switch (ace->type) {
     296       20920 :                 case SEC_ACE_TYPE_ACCESS_ALLOWED:
     297       20920 :                         bits_remaining &= ~ace->access_mask;
     298       20920 :                         break;
     299           0 :                 case SEC_ACE_TYPE_ACCESS_DENIED:
     300             :                 case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
     301           0 :                         explicitly_denied_bits |= (bits_remaining & ace->access_mask);
     302           0 :                         break;
     303         112 :                 default:        /* Other ACE types not handled/supported */
     304         112 :                         break;
     305             :                 }
     306             :         }
     307             : 
     308             :         /* Explicitly denied bits always override */
     309       22392 :         bits_remaining |= explicitly_denied_bits;
     310             : 
     311             :         /*
     312             :          * We check privileges here because they override even DENY entries.
     313             :          */
     314             : 
     315             :         /* Does the user have the privilege to gain SEC_PRIV_SECURITY? */
     316       22392 :         if (bits_remaining & SEC_FLAG_SYSTEM_SECURITY) {
     317        8371 :                 if (security_token_has_privilege(token, SEC_PRIV_SECURITY)) {
     318        8371 :                         bits_remaining &= ~SEC_FLAG_SYSTEM_SECURITY;
     319             :                 } else {
     320           0 :                         return NT_STATUS_PRIVILEGE_NOT_HELD;
     321             :                 }
     322             :         }
     323             : 
     324       23650 :         if ((bits_remaining & SEC_STD_WRITE_OWNER) &&
     325        1258 :              security_token_has_privilege(token, SEC_PRIV_TAKE_OWNERSHIP)) {
     326        1258 :                 bits_remaining &= ~(SEC_STD_WRITE_OWNER);
     327             :         }
     328             : 
     329       21134 : done:
     330       22392 :         if (bits_remaining != 0) {
     331        1322 :                 *access_granted = bits_remaining;
     332        1322 :                 return NT_STATUS_ACCESS_DENIED;
     333             :         }
     334             : 
     335       21070 :         return NT_STATUS_OK;
     336             : }
     337             : 
     338             : /*
     339             :   The main entry point for access checking. If returning ACCESS_DENIED
     340             :   this function returns the denied bits in the uint32_t pointed
     341             :   to by the access_granted pointer.
     342             : */
     343        2814 : NTSTATUS se_access_check(const struct security_descriptor *sd,
     344             :                          const struct security_token *token,
     345             :                          uint32_t access_desired,
     346             :                          uint32_t *access_granted)
     347             : {
     348        2814 :         return se_access_check_implicit_owner(sd,
     349             :                                               token,
     350             :                                               access_desired,
     351             :                                               access_granted,
     352             :                                               IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS);
     353             : }
     354             : 
     355             : /*
     356             :   The main entry point for access checking FOR THE FILE SERVER ONLY !
     357             :   If returning ACCESS_DENIED this function returns the denied bits in
     358             :   the uint32_t pointed to by the access_granted pointer.
     359             : */
     360       19597 : NTSTATUS se_file_access_check(const struct security_descriptor *sd,
     361             :                           const struct security_token *token,
     362             :                           bool priv_open_requested,
     363             :                           uint32_t access_desired,
     364             :                           uint32_t *access_granted)
     365             : {
     366             :         uint32_t bits_remaining;
     367             :         NTSTATUS status;
     368             : 
     369       19597 :         if (!priv_open_requested) {
     370             :                 /* Fall back to generic se_access_check(). */
     371        5982 :                 return se_access_check_implicit_owner(sd,
     372             :                                                       token,
     373             :                                                       access_desired,
     374             :                                                       access_granted,
     375             :                                                       IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS);
     376             :         }
     377             : 
     378             :         /*
     379             :          * We need to handle the maximum allowed flag
     380             :          * outside of se_access_check(), as we need to
     381             :          * add in the access allowed by the privileges
     382             :          * as well.
     383             :          */
     384             : 
     385       13615 :         if (access_desired & SEC_FLAG_MAXIMUM_ALLOWED) {
     386       13615 :                 uint32_t orig_access_desired = access_desired;
     387             : 
     388       13615 :                 access_desired |= access_check_max_allowed(sd, token, true);
     389       13615 :                 access_desired &= ~SEC_FLAG_MAXIMUM_ALLOWED;
     390             : 
     391       13615 :                 if (security_token_has_privilege(token, SEC_PRIV_BACKUP)) {
     392        8213 :                         access_desired |= SEC_RIGHTS_PRIV_BACKUP;
     393             :                 }
     394             : 
     395       13615 :                 if (security_token_has_privilege(token, SEC_PRIV_RESTORE)) {
     396        8213 :                         access_desired |= SEC_RIGHTS_PRIV_RESTORE;
     397             :                 }
     398             : 
     399       13615 :                 DEBUG(10,("se_file_access_check: MAX desired = 0x%x "
     400             :                         "mapped to 0x%x\n",
     401             :                         orig_access_desired,
     402             :                         access_desired));
     403             :         }
     404             : 
     405       13615 :         status = se_access_check_implicit_owner(sd,
     406             :                                                 token,
     407             :                                                 access_desired,
     408             :                                                 access_granted,
     409             :                                                 IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS);
     410             : 
     411       13615 :         if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
     412       12444 :                 return status;
     413             :         }
     414             : 
     415        1171 :         bits_remaining = *access_granted;
     416             : 
     417             :         /* Check if we should override with privileges. */
     418        2342 :         if ((bits_remaining & SEC_RIGHTS_PRIV_BACKUP) &&
     419        1171 :             security_token_has_privilege(token, SEC_PRIV_BACKUP)) {
     420        1171 :                 bits_remaining &= ~(SEC_RIGHTS_PRIV_BACKUP);
     421             :         }
     422        2342 :         if ((bits_remaining & SEC_RIGHTS_PRIV_RESTORE) &&
     423        1171 :             security_token_has_privilege(token, SEC_PRIV_RESTORE)) {
     424        1171 :                 bits_remaining &= ~(SEC_RIGHTS_PRIV_RESTORE);
     425             :         }
     426        1171 :         if (bits_remaining != 0) {
     427           0 :                 *access_granted = bits_remaining;
     428           0 :                 return NT_STATUS_ACCESS_DENIED;
     429             :         }
     430             : 
     431        1171 :         return NT_STATUS_OK;
     432             : }
     433             : 
     434     5050850 : static const struct GUID *get_ace_object_type(const struct security_ace *ace)
     435             : {
     436     5050850 :         if (ace->object.object.flags & SEC_ACE_OBJECT_TYPE_PRESENT) {
     437     4778968 :                 return &ace->object.object.type.type;
     438             :         }
     439             : 
     440      271882 :         return NULL;
     441             : }
     442             : 
     443             : /**
     444             :  * Evaluates access rights specified in a object-specific ACE for an AD object.
     445             :  * This logic corresponds to MS-ADTS 5.1.3.3.3 Checking Object-Specific Access.
     446             :  * @param[in] ace - the ACE being processed
     447             :  * @param[in/out] tree - remaining_access gets updated for the tree
     448             :  * @param[out] grant_access - set to true if the ACE grants sufficient access
     449             :  *                            rights to the object/attribute
     450             :  * @returns NT_STATUS_OK, unless access was denied
     451             :  */
     452     5727728 : static NTSTATUS check_object_specific_access(const struct security_ace *ace,
     453             :                                              struct object_tree *tree,
     454             :                                              bool *grant_access)
     455             : {
     456     5727728 :         struct object_tree *node = NULL;
     457     5727728 :         const struct GUID *type = NULL;
     458             : 
     459     5727728 :         *grant_access = false;
     460             : 
     461             :         /* if no tree was supplied, we can't do object-specific access checks */
     462     5727728 :         if (!tree) {
     463      676878 :                 return NT_STATUS_OK;
     464             :         }
     465             : 
     466             :         /* Get the ObjectType GUID this ACE applies to */
     467     5050850 :         type = get_ace_object_type(ace);
     468             : 
     469             :         /*
     470             :          * If the ACE doesn't have a type, then apply it to the whole tree, i.e.
     471             :          * treat 'OA' ACEs as 'A' and 'OD' as 'D'
     472             :          */
     473     5050850 :         if (!type) {
     474      271882 :                 node = tree;
     475             :         } else {
     476             : 
     477             :                 /* skip it if the ACE's ObjectType GUID is not in the tree */
     478     4778968 :                 node = get_object_tree_by_GUID(tree, type);
     479     4778968 :                 if (!node) {
     480     4121718 :                         return NT_STATUS_OK;
     481             :                 }
     482             :         }
     483             : 
     484      929132 :         if (ace->type == SEC_ACE_TYPE_ACCESS_ALLOWED_OBJECT) {
     485             : 
     486             :                 /* apply the access rights to this node, and any children */
     487      928544 :                 object_tree_modify_access(node, ace->access_mask);
     488             : 
     489             :                 /*
     490             :                  * Currently all nodes in the tree request the same access mask,
     491             :                  * so we can use any node to check if processing this ACE now
     492             :                  * means the requested access has been granted
     493             :                  */
     494      928544 :                 if (node->remaining_access == 0) {
     495      915260 :                         *grant_access = true;
     496      915260 :                         return NT_STATUS_OK;
     497             :                 }
     498             : 
     499             :                 /*
     500             :                  * As per 5.1.3.3.4 Checking Control Access Right-Based Access,
     501             :                  * if the CONTROL_ACCESS right is present, then we can grant
     502             :                  * access and stop any further access checks
     503             :                  */
     504       13284 :                 if (ace->access_mask & SEC_ADS_CONTROL_ACCESS) {
     505         894 :                         *grant_access = true;
     506         894 :                         return NT_STATUS_OK;
     507             :                 }
     508             :         } else {
     509             : 
     510             :                 /* this ACE denies access to the requested object/attribute */
     511         588 :                 if (node->remaining_access & ace->access_mask){
     512         552 :                         return NT_STATUS_ACCESS_DENIED;
     513             :                 }
     514             :         }
     515       12426 :         return NT_STATUS_OK;
     516             : }
     517             : 
     518     7628496 : NTSTATUS sec_access_check_ds_implicit_owner(const struct security_descriptor *sd,
     519             :                                             const struct security_token *token,
     520             :                                             uint32_t access_desired,
     521             :                                             uint32_t *access_granted,
     522             :                                             struct object_tree *tree,
     523             :                                             const struct dom_sid *replace_sid,
     524             :                                             enum implicit_owner_rights implicit_owner_rights)
     525             : {
     526             :         uint32_t i;
     527             :         uint32_t bits_remaining;
     528             :         struct dom_sid self_sid;
     529             : 
     530     7628496 :         dom_sid_parse(SID_NT_SELF, &self_sid);
     531             : 
     532     7628496 :         *access_granted = access_desired;
     533     7628496 :         bits_remaining = access_desired;
     534             : 
     535             :         /* handle the maximum allowed flag */
     536     7628496 :         if (access_desired & SEC_FLAG_MAXIMUM_ALLOWED) {
     537           0 :                 access_desired |= access_check_max_allowed(sd, token, implicit_owner_rights);
     538           0 :                 access_desired &= ~SEC_FLAG_MAXIMUM_ALLOWED;
     539           0 :                 *access_granted = access_desired;
     540           0 :                 bits_remaining = access_desired;
     541             :         }
     542             : 
     543     7628496 :         if (access_desired & SEC_FLAG_SYSTEM_SECURITY) {
     544       33246 :                 if (security_token_has_privilege(token, SEC_PRIV_SECURITY)) {
     545       32532 :                         bits_remaining &= ~SEC_FLAG_SYSTEM_SECURITY;
     546             :                 } else {
     547         714 :                         return NT_STATUS_PRIVILEGE_NOT_HELD;
     548             :                 }
     549             :         }
     550             : 
     551             :         /* the owner always gets SEC_STD_WRITE_DAC and SEC_STD_READ_CONTROL */
     552     7675680 :         if ((bits_remaining & (SEC_STD_WRITE_DAC|SEC_STD_READ_CONTROL)) &&
     553       47898 :             security_token_has_sid(token, sd->owner_sid)) {
     554       45882 :                 switch (implicit_owner_rights) {
     555       25768 :                 case IMPLICIT_OWNER_READ_CONTROL_AND_WRITE_DAC_RIGHTS:
     556       25768 :                         bits_remaining &= ~SEC_STD_WRITE_DAC;
     557             :                         FALL_THROUGH;
     558       45882 :                 case IMPLICIT_OWNER_READ_CONTROL_RIGHTS:
     559       45882 :                         bits_remaining &= ~SEC_STD_READ_CONTROL;
     560       45882 :                         break;
     561             :                 }
     562             :         }
     563             : 
     564             :         /* SEC_PRIV_TAKE_OWNERSHIP grants SEC_STD_WRITE_OWNER */
     565     7640152 :         if ((bits_remaining & (SEC_STD_WRITE_OWNER)) &&
     566       12370 :             security_token_has_privilege(token, SEC_PRIV_TAKE_OWNERSHIP)) {
     567       11998 :                 bits_remaining &= ~(SEC_STD_WRITE_OWNER);
     568             :         }
     569             : 
     570             :         /* a NULL dacl allows access */
     571     7627782 :         if ((sd->type & SEC_DESC_DACL_PRESENT) && sd->dacl == NULL) {
     572           0 :                 *access_granted = access_desired;
     573           0 :                 return NT_STATUS_OK;
     574             :         }
     575             : 
     576     7627782 :         if (sd->dacl == NULL) {
     577           0 :                 goto done;
     578             :         }
     579             : 
     580             :         /* check each ace in turn. */
     581    41148693 :         for (i=0; bits_remaining && i < sd->dacl->num_aces; i++) {
     582             :                 const struct dom_sid *trustee;
     583    34453096 :                 const struct security_ace *ace = &sd->dacl->aces[i];
     584             :                 NTSTATUS status;
     585    34453096 :                 bool grant_access = false;
     586             : 
     587    34453096 :                 if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) {
     588    20976064 :                         continue;
     589             :                 }
     590             : 
     591    29839613 :                 if (dom_sid_equal(&ace->trustee, &self_sid) && replace_sid) {
     592     6320778 :                         trustee = replace_sid;
     593             :                 } else {
     594    23518835 :                         trustee = &ace->trustee;
     595             :                 }
     596             : 
     597    29839613 :                 if (!security_token_has_sid(token, trustee)) {
     598    16362581 :                         continue;
     599             :                 }
     600             : 
     601    13477032 :                 switch (ace->type) {
     602     7717362 :                 case SEC_ACE_TYPE_ACCESS_ALLOWED:
     603     7717362 :                         if (tree) {
     604     6878570 :                                 object_tree_modify_access(tree, ace->access_mask);
     605             :                         }
     606             : 
     607     7717362 :                         bits_remaining &= ~ace->access_mask;
     608     7717362 :                         break;
     609       31942 :                 case SEC_ACE_TYPE_ACCESS_DENIED:
     610       31942 :                         if (bits_remaining & ace->access_mask) {
     611       15479 :                                 return NT_STATUS_ACCESS_DENIED;
     612             :                         }
     613       16463 :                         break;
     614     5727728 :                 case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
     615             :                 case SEC_ACE_TYPE_ACCESS_ALLOWED_OBJECT:
     616     5727728 :                         status = check_object_specific_access(ace, tree,
     617             :                                                               &grant_access);
     618             : 
     619     5727728 :                         if (!NT_STATUS_IS_OK(status)) {
     620         552 :                                 return status;
     621             :                         }
     622             : 
     623     5727176 :                         if (grant_access) {
     624      916154 :                                 return NT_STATUS_OK;
     625             :                         }
     626     4811022 :                         break;
     627           0 :                 default:        /* Other ACE types not handled/supported */
     628           0 :                         break;
     629             :                 }
     630             :         }
     631             : 
     632     6695597 : done:
     633     6695597 :         if (bits_remaining != 0) {
     634       64990 :                 return NT_STATUS_ACCESS_DENIED;
     635             :         }
     636             : 
     637     6630607 :         return NT_STATUS_OK;
     638             : }
     639             : 
     640             : /**
     641             :  * @brief Perform directoryservice (DS) related access checks for a given user
     642             :  *
     643             :  * Perform DS access checks for the user represented by its security_token, on
     644             :  * the provided security descriptor. If an tree associating GUID and access
     645             :  * required is provided then object access (OA) are checked as well. *
     646             :  * @param[in]   sd             The security descritor against which the required
     647             :  *                             access are requested
     648             :  *
     649             :  * @param[in]   token          The security_token associated with the user to
     650             :  *                             test
     651             :  *
     652             :  * @param[in]   access_desired A bitfield of rights that must be granted for the
     653             :  *                             given user in the specified SD.
     654             :  *
     655             :  * If one
     656             :  * of the entry in the tree grants all the requested rights for the given GUID
     657             :  * FIXME
     658             :  * tree can be null if not null it's the
     659             :  * Lots of code duplication, it will be united in just one
     660             :  * function eventually */
     661             : 
     662     1246444 : NTSTATUS sec_access_check_ds(const struct security_descriptor *sd,
     663             :                              const struct security_token *token,
     664             :                              uint32_t access_desired,
     665             :                              uint32_t *access_granted,
     666             :                              struct object_tree *tree,
     667             :                              struct dom_sid *replace_sid)
     668             : {
     669     1246444 :         return sec_access_check_ds_implicit_owner(sd,
     670             :                                                   token,
     671             :                                                   access_desired,
     672             :                                                   access_granted,
     673             :                                                   tree,
     674             :                                                   replace_sid,
     675             :                                                   IMPLICIT_OWNER_READ_CONTROL_RIGHTS);
     676             : }

Generated by: LCOV version 1.14