Changeset 745 for trunk/server/source3/smbd/posix_acls.c
- Timestamp:
- Nov 27, 2012, 4:43:17 PM (13 years ago)
- Location:
- trunk/server
- Files:
-
- 2 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/server
- Property svn:mergeinfo changed
/vendor/current merged: 581,587,591,594,597,600,615,618,740
- Property svn:mergeinfo changed
-
trunk/server/source3/smbd/posix_acls.c
r599 r745 21 21 22 22 #include "includes.h" 23 24 extern struct current_user current_user; 23 #include "smbd/smbd.h" 24 #include "system/filesys.h" 25 #include "../libcli/security/security.h" 26 #include "trans2.h" 27 #include "passdb/lookup_sid.h" 28 #include "auth.h" 29 25 30 extern const struct generic_mapping file_generic_mapping; 26 31 … … 45 50 SMB_ACL_TAG_T type; 46 51 mode_t perms; /* Only use S_I(R|W|X)USR mode bits here. */ 47 DOM_SIDtrustee;52 struct dom_sid trustee; 48 53 enum ace_owner owner_type; 49 54 enum ace_attribute attr; … … 443 448 paie->ace_flags = SEC_ACE_FLAG_INHERITED_ACE; 444 449 if (!get_pai_owner_type(paie, entry_offset)) { 450 SAFE_FREE(paie); 445 451 return NULL; 446 452 } … … 477 483 478 484 paiv->sd_type = (CVAL(buf,PAI_V1_FLAG_OFFSET) == PAI_V1_ACL_FLAG_PROTECTED) ? 479 SE _DESC_DACL_PROTECTED : 0;485 SEC_DESC_DACL_PROTECTED : 0; 480 486 481 487 paiv->num_entries = SVAL(buf,PAI_V1_NUM_ENTRIES_OFFSET); … … 521 527 522 528 if (!get_pai_owner_type(paie, entry_offset+1)) { 529 SAFE_FREE(paie); 523 530 return NULL; 524 531 } … … 907 914 ****************************************************************************/ 908 915 909 void create_file_sids(const SMB_STRUCT_STAT *psbuf, DOM_SID *powner_sid, DOM_SID*pgroup_sid)916 void create_file_sids(const SMB_STRUCT_STAT *psbuf, struct dom_sid *powner_sid, struct dom_sid *pgroup_sid) 910 917 { 911 918 uid_to_sid( powner_sid, psbuf->st_ex_uid ); … … 946 953 947 954 if (!dir_acl) { 948 can_merge = ( sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) &&955 can_merge = (dom_sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) && 949 956 (curr_ace->attr == curr_ace_outer->attr)); 950 957 } else { 951 can_merge = ( sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) &&958 can_merge = (dom_sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) && 952 959 (curr_ace->type == curr_ace_outer->type) && 953 960 (curr_ace->attr == curr_ace_outer->attr)); … … 998 1005 */ 999 1006 1000 if ( sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) &&1007 if (dom_sid_equal(&curr_ace->trustee, &curr_ace_outer->trustee) && 1001 1008 (curr_ace_outer->attr == DENY_ACE) && (curr_ace->attr == ALLOW_ACE)) { 1002 1009 … … 1166 1173 1167 1174 /**************************************************************************** 1168 Unpack a SEC_DESC into a UNIX owner and group. 1169 ****************************************************************************/ 1170 1171 NTSTATUS unpack_nt_owners(int snum, uid_t *puser, gid_t *pgrp, uint32 security_info_sent, const SEC_DESC *psd) 1172 { 1173 DOM_SID owner_sid; 1174 DOM_SID grp_sid; 1175 Unpack a struct security_descriptor into a UNIX owner and group. 1176 ****************************************************************************/ 1177 1178 NTSTATUS unpack_nt_owners(struct connection_struct *conn, 1179 uid_t *puser, gid_t *pgrp, 1180 uint32 security_info_sent, const struct 1181 security_descriptor *psd) 1182 { 1183 struct dom_sid owner_sid; 1184 struct dom_sid grp_sid; 1175 1185 1176 1186 *puser = (uid_t)-1; … … 1196 1206 */ 1197 1207 1198 if (security_info_sent & OWNER_SECURITY_INFORMATION) {1208 if (security_info_sent & SECINFO_OWNER) { 1199 1209 sid_copy(&owner_sid, psd->owner_sid); 1200 1210 if (!sid_to_uid(&owner_sid, puser)) { 1201 if (lp_force_unknown_acl_user( snum)) {1211 if (lp_force_unknown_acl_user(SNUM(conn))) { 1202 1212 /* this allows take ownership to work 1203 1213 * reasonably */ 1204 *puser = current_user.ut.uid;1214 *puser = get_current_uid(conn); 1205 1215 } else { 1206 1216 DEBUG(3,("unpack_nt_owners: unable to validate" … … 1219 1229 */ 1220 1230 1221 if (security_info_sent & GROUP_SECURITY_INFORMATION) {1231 if (security_info_sent & SECINFO_GROUP) { 1222 1232 sid_copy(&grp_sid, psd->group_sid); 1223 1233 if (!sid_to_gid( &grp_sid, pgrp)) { 1224 if (lp_force_unknown_acl_user( snum)) {1234 if (lp_force_unknown_acl_user(SNUM(conn))) { 1225 1235 /* this allows take group ownership to work 1226 1236 * reasonably */ 1227 *pgrp = current_user.ut.gid;1237 *pgrp = get_current_gid(conn); 1228 1238 } else { 1229 1239 DEBUG(3,("unpack_nt_owners: unable to validate" … … 1290 1300 ****************************************************************************/ 1291 1301 1292 static bool uid_entry_in_group( canon_ace *uid_ace, canon_ace *group_ace )1302 static bool uid_entry_in_group(connection_struct *conn, canon_ace *uid_ace, canon_ace *group_ace ) 1293 1303 { 1294 1304 const char *u_name = NULL; … … 1296 1306 /* "Everyone" always matches every uid. */ 1297 1307 1298 if ( sid_equal(&group_ace->trustee, &global_sid_World))1308 if (dom_sid_equal(&group_ace->trustee, &global_sid_World)) 1299 1309 return True; 1300 1310 … … 1303 1313 * and don't need to do the complex user_in_group_sid() call 1304 1314 */ 1305 if (uid_ace->unix_ug.uid == current_user.ut.uid) { 1315 if (uid_ace->unix_ug.uid == get_current_uid(conn)) { 1316 const struct security_unix_token *curr_utok = NULL; 1306 1317 size_t i; 1307 1318 1308 if (group_ace->unix_ug.gid == current_user.ut.gid) {1319 if (group_ace->unix_ug.gid == get_current_gid(conn)) { 1309 1320 return True; 1310 1321 } 1311 1322 1312 for (i=0; i < current_user.ut.ngroups; i++) { 1313 if (group_ace->unix_ug.gid == current_user.ut.groups[i]) { 1323 curr_utok = get_current_utok(conn); 1324 for (i=0; i < curr_utok->ngroups; i++) { 1325 if (group_ace->unix_ug.gid == curr_utok->groups[i]) { 1314 1326 return True; 1315 1327 } … … 1342 1354 ****************************************************************************/ 1343 1355 1344 static bool ensure_canon_entry_valid(c anon_ace **pp_ace,1356 static bool ensure_canon_entry_valid(connection_struct *conn, canon_ace **pp_ace, 1345 1357 const struct share_params *params, 1346 1358 const bool is_directory, 1347 const DOM_SID*pfile_owner_sid,1348 const DOM_SID*pfile_grp_sid,1359 const struct dom_sid *pfile_owner_sid, 1360 const struct dom_sid *pfile_grp_sid, 1349 1361 const SMB_STRUCT_STAT *pst, 1350 1362 bool setting_acl) … … 1408 1420 for (pace_iter = *pp_ace; pace_iter; pace_iter = pace_iter->next) { 1409 1421 if (pace_iter->type == SMB_ACL_GROUP_OBJ || pace_iter->type == SMB_ACL_GROUP) { 1410 if (uid_entry_in_group( pace, pace_iter)) {1422 if (uid_entry_in_group(conn, pace, pace_iter)) { 1411 1423 pace->perms |= pace_iter->perms; 1412 1424 group_matched = True; … … 1487 1499 ****************************************************************************/ 1488 1500 1489 static void check_owning_objs(canon_ace *ace, DOM_SID *pfile_owner_sid, DOM_SID*pfile_grp_sid)1501 static void check_owning_objs(canon_ace *ace, struct dom_sid *pfile_owner_sid, struct dom_sid *pfile_grp_sid) 1490 1502 { 1491 1503 bool got_user_obj, got_group_obj; … … 1510 1522 for (i=0, current_ace = ace; i < entries; i++, current_ace = current_ace->next) { 1511 1523 if (!got_user_obj && current_ace->owner_type == UID_ACE && 1512 sid_equal(¤t_ace->trustee, pfile_owner_sid)) {1524 dom_sid_equal(¤t_ace->trustee, pfile_owner_sid)) { 1513 1525 current_ace->type = SMB_ACL_USER_OBJ; 1514 1526 got_user_obj = True; 1515 1527 } 1516 1528 if (!got_group_obj && current_ace->owner_type == GID_ACE && 1517 sid_equal(¤t_ace->trustee, pfile_grp_sid)) {1529 dom_sid_equal(¤t_ace->trustee, pfile_grp_sid)) { 1518 1530 current_ace->type = SMB_ACL_GROUP_OBJ; 1519 1531 got_group_obj = True; … … 1546 1558 1547 1559 if (ace->type == SMB_ACL_USER_OBJ && 1548 !( sid_equal(&ace->trustee, &global_sid_Creator_Owner))) {1560 !(dom_sid_equal(&ace->trustee, &global_sid_Creator_Owner))) { 1549 1561 canon_ace *dup_ace = dup_canon_ace(ace); 1550 1562 … … 1557 1569 1558 1570 if (ace->type == SMB_ACL_GROUP_OBJ && 1559 !( sid_equal(&ace->trustee, &global_sid_Creator_Group))) {1571 !(dom_sid_equal(&ace->trustee, &global_sid_Creator_Group))) { 1560 1572 canon_ace *dup_ace = dup_canon_ace(ace); 1561 1573 … … 1571 1583 1572 1584 /**************************************************************************** 1573 Unpack a SEC_DESCinto two canonical ace lists.1585 Unpack a struct security_descriptor into two canonical ace lists. 1574 1586 ****************************************************************************/ 1575 1587 1576 1588 static bool create_canon_ace_lists(files_struct *fsp, 1577 1589 const SMB_STRUCT_STAT *pst, 1578 DOM_SID*pfile_owner_sid,1579 DOM_SID*pfile_grp_sid,1590 struct dom_sid *pfile_owner_sid, 1591 struct dom_sid *pfile_grp_sid, 1580 1592 canon_ace **ppfile_ace, 1581 1593 canon_ace **ppdir_ace, 1582 const SEC_ACL*dacl)1594 const struct security_acl *dacl) 1583 1595 { 1584 1596 bool all_aces_are_inherit_only = (fsp->is_directory ? True : False); … … 1598 1610 1599 1611 for(i = 0; i < dacl->num_aces; i++) { 1600 SEC_ACE*psa = &dacl->aces[i];1612 struct security_ace *psa = &dacl->aces[i]; 1601 1613 1602 1614 if((psa->type != SEC_ACE_TYPE_ACCESS_ALLOWED) && (psa->type != SEC_ACE_TYPE_ACCESS_DENIED)) { … … 1635 1647 1636 1648 for(i = 0; i < dacl->num_aces; i++) { 1637 SEC_ACE*psa1 = &dacl->aces[i];1649 struct security_ace *psa1 = &dacl->aces[i]; 1638 1650 1639 1651 for (j = i + 1; j < dacl->num_aces; j++) { 1640 SEC_ACE*psa2 = &dacl->aces[j];1652 struct security_ace *psa2 = &dacl->aces[j]; 1641 1653 1642 1654 if (psa1->access_mask != psa2->access_mask) 1643 1655 continue; 1644 1656 1645 if (! sid_equal(&psa1->trustee, &psa2->trustee))1657 if (!dom_sid_equal(&psa1->trustee, &psa2->trustee)) 1646 1658 continue; 1647 1659 … … 1666 1678 1667 1679 for(i = 0; i < dacl->num_aces; i++) { 1668 SEC_ACE*psa = &dacl->aces[i];1680 struct security_ace *psa = &dacl->aces[i]; 1669 1681 1670 1682 /* 1671 * Create a can non_ace entry representing this NT DACL ACE.1683 * Create a canon_ace entry representing this NT DACL ACE. 1672 1684 */ 1673 1685 … … 1689 1701 */ 1690 1702 1691 if( sid_equal(¤t_ace->trustee, &global_sid_World)) {1703 if( dom_sid_equal(¤t_ace->trustee, &global_sid_World)) { 1692 1704 current_ace->owner_type = WORLD_ACE; 1693 1705 current_ace->unix_ug.world = -1; 1694 1706 current_ace->type = SMB_ACL_OTHER; 1695 } else if ( sid_equal(¤t_ace->trustee, &global_sid_Creator_Owner)) {1707 } else if (dom_sid_equal(¤t_ace->trustee, &global_sid_Creator_Owner)) { 1696 1708 current_ace->owner_type = UID_ACE; 1697 1709 current_ace->unix_ug.uid = pst->st_ex_uid; … … 1706 1718 psa->flags |= SEC_ACE_FLAG_INHERIT_ONLY; 1707 1719 1708 } else if ( sid_equal(¤t_ace->trustee, &global_sid_Creator_Group)) {1720 } else if (dom_sid_equal(¤t_ace->trustee, &global_sid_Creator_Group)) { 1709 1721 current_ace->owner_type = GID_ACE; 1710 1722 current_ace->unix_ug.gid = pst->st_ex_gid; … … 1753 1765 "unknown or foreign SID %s\n", 1754 1766 sid_string_dbg(&psa->trustee))); 1755 1767 SAFE_FREE(current_ace); 1756 1768 continue; 1757 1769 } … … 2066 2078 ****************************************************************************/ 2067 2079 2068 static void process_deny_list( canon_ace **pp_ace_list )2080 static void process_deny_list(connection_struct *conn, canon_ace **pp_ace_list ) 2069 2081 { 2070 2082 canon_ace *ace_list = *pp_ace_list; … … 2090 2102 } 2091 2103 2092 if (! sid_equal(&curr_ace->trustee, &global_sid_World))2104 if (!dom_sid_equal(&curr_ace->trustee, &global_sid_World)) 2093 2105 continue; 2094 2106 … … 2103 2115 */ 2104 2116 2105 canon_ace *prev_entry = curr_ace->prev;2117 canon_ace *prev_entry = DLIST_PREV(curr_ace); 2106 2118 2107 2119 free_canon_ace_list( curr_ace ); 2108 2120 if (prev_entry) 2109 prev_entry->next = NULL;2121 DLIST_REMOVE(ace_list, prev_entry); 2110 2122 else { 2111 2123 /* We deleted the entire list. */ … … 2171 2183 continue; 2172 2184 2173 if (uid_entry_in_group( curr_ace, allow_ace_p))2185 if (uid_entry_in_group(conn, curr_ace, allow_ace_p)) 2174 2186 new_perms |= allow_ace_p->perms; 2175 2187 } … … 2215 2227 /* Mask off the deny group perms. */ 2216 2228 2217 if (uid_entry_in_group( allow_ace_p, curr_ace))2229 if (uid_entry_in_group(conn, allow_ace_p, curr_ace)) 2218 2230 allow_ace_p->perms &= ~curr_ace->perms; 2219 2231 } … … 2265 2277 /* OR in the group perms. */ 2266 2278 2267 if (uid_entry_in_group( curr_ace, allow_ace_p))2279 if (uid_entry_in_group(conn, curr_ace, allow_ace_p)) 2268 2280 curr_ace->perms |= allow_ace_p->perms; 2269 2281 } … … 2313 2325 2314 2326 /**************************************************************************** 2315 Unpack a SEC_DESCinto two canonical ace lists. We don't depend on this2327 Unpack a struct security_descriptor into two canonical ace lists. We don't depend on this 2316 2328 succeeding. 2317 2329 ****************************************************************************/ … … 2319 2331 static bool unpack_canon_ace(files_struct *fsp, 2320 2332 const SMB_STRUCT_STAT *pst, 2321 DOM_SID*pfile_owner_sid,2322 DOM_SID*pfile_grp_sid,2333 struct dom_sid *pfile_owner_sid, 2334 struct dom_sid *pfile_grp_sid, 2323 2335 canon_ace **ppfile_ace, 2324 2336 canon_ace **ppdir_ace, 2325 2337 uint32 security_info_sent, 2326 const SEC_DESC*psd)2338 const struct security_descriptor *psd) 2327 2339 { 2328 2340 SMB_STRUCT_STAT st; … … 2342 2354 */ 2343 2355 2344 if(!(security_info_sent & DACL_SECURITY_INFORMATION) || !psd->dacl)2356 if(!(security_info_sent & SECINFO_DACL) || !psd->dacl) 2345 2357 return True; 2346 2358 … … 2377 2389 2378 2390 print_canon_ace_list( "file ace - before deny", file_ace); 2379 process_deny_list( &file_ace);2391 process_deny_list(fsp->conn, &file_ace); 2380 2392 2381 2393 print_canon_ace_list( "dir ace - before deny", dir_ace); 2382 process_deny_list( &dir_ace);2394 process_deny_list(fsp->conn, &dir_ace); 2383 2395 2384 2396 /* … … 2399 2411 st.st_ex_mode = create_default_mode(fsp, False); 2400 2412 2401 if (!ensure_canon_entry_valid( &file_ace, fsp->conn->params,2413 if (!ensure_canon_entry_valid(fsp->conn, &file_ace, fsp->conn->params, 2402 2414 fsp->is_directory, pfile_owner_sid, pfile_grp_sid, &st, True)) { 2403 2415 free_canon_ace_list(file_ace); … … 2416 2428 st.st_ex_mode = create_default_mode(fsp, True); 2417 2429 2418 if (dir_ace && !ensure_canon_entry_valid( &dir_ace, fsp->conn->params,2430 if (dir_ace && !ensure_canon_entry_valid(fsp->conn, &dir_ace, fsp->conn->params, 2419 2431 fsp->is_directory, pfile_owner_sid, pfile_grp_sid, &st, True)) { 2420 2432 free_canon_ace_list(file_ace); … … 2498 2510 const char *fname, SMB_ACL_T posix_acl, 2499 2511 const SMB_STRUCT_STAT *psbuf, 2500 const DOM_SID *powner, const DOM_SID*pgroup, struct pai_val *pal, SMB_ACL_TYPE_T the_acl_type)2512 const struct dom_sid *powner, const struct dom_sid *pgroup, struct pai_val *pal, SMB_ACL_TYPE_T the_acl_type) 2501 2513 { 2502 2514 mode_t acl_mask = (S_IRUSR|S_IWUSR|S_IXUSR); … … 2511 2523 SMB_ACL_TAG_T tagtype; 2512 2524 SMB_ACL_PERMSET_T permset; 2513 DOM_SIDsid;2525 struct dom_sid sid; 2514 2526 posix_id unix_ug; 2515 2527 enum ace_owner owner_type; … … 2601 2613 */ 2602 2614 2603 if (!ensure_canon_entry_valid( &l_head, conn->params,2615 if (!ensure_canon_entry_valid(conn, &l_head, conn->params, 2604 2616 S_ISDIR(psbuf->st_ex_mode), powner, pgroup, 2605 2617 psbuf, False)) … … 2645 2657 ****************************************************************************/ 2646 2658 2647 bool current_user_in_group( gid_t gid)2659 bool current_user_in_group(connection_struct *conn, gid_t gid) 2648 2660 { 2649 2661 int i; 2650 2651 for (i = 0; i < current_user.ut.ngroups; i++) { 2652 if (current_user.ut.groups[i] == gid) { 2662 const struct security_unix_token *utok = get_current_utok(conn); 2663 2664 for (i = 0; i < utok->ngroups; i++) { 2665 if (utok->groups[i] == gid) { 2653 2666 return True; 2654 2667 } … … 2671 2684 /* file primary group == user primary or supplementary group */ 2672 2685 if (lp_acl_group_control(SNUM(conn)) && 2673 current_user_in_group( smb_fname->st.st_ex_gid)) {2686 current_user_in_group(conn, smb_fname->st.st_ex_gid)) { 2674 2687 return true; 2675 2688 } … … 3069 3082 ****************************************************************************/ 3070 3083 3071 static size_t merge_default_aces( SEC_ACE*nt_ace_list, size_t num_aces)3084 static size_t merge_default_aces( struct security_ace *nt_ace_list, size_t num_aces) 3072 3085 { 3073 3086 size_t i, j; … … 3084 3097 (nt_ace_list[i].size == nt_ace_list[j].size) && 3085 3098 (nt_ace_list[i].access_mask == nt_ace_list[j].access_mask) && 3086 sid_equal(&nt_ace_list[i].trustee, &nt_ace_list[j].trustee) &&3099 dom_sid_equal(&nt_ace_list[i].trustee, &nt_ace_list[j].trustee) && 3087 3100 (i_inh == j_inh) && 3088 3101 (i_flags_ni == 0) && … … 3101 3114 if (num_aces - i - 1 > 0) 3102 3115 memmove(&nt_ace_list[i], &nt_ace_list[i+1], (num_aces-i-1) * 3103 sizeof( SEC_ACE));3116 sizeof(struct security_ace)); 3104 3117 3105 3118 DEBUG(10,("merge_default_aces: Merging zero access ACE %u onto ACE %u.\n", … … 3115 3128 if (num_aces - j - 1 > 0) 3116 3129 memmove(&nt_ace_list[j], &nt_ace_list[j+1], (num_aces-j-1) * 3117 sizeof( SEC_ACE));3130 sizeof(struct security_ace)); 3118 3131 3119 3132 DEBUG(10,("merge_default_aces: Merging ACE %u onto ACE %u.\n", … … 3140 3153 */ 3141 3154 3142 static void add_or_replace_ace( SEC_ACE*nt_ace_list, size_t *num_aces,3143 const DOM_SID*sid, enum security_ace_type type,3155 static void add_or_replace_ace(struct security_ace *nt_ace_list, size_t *num_aces, 3156 const struct dom_sid *sid, enum security_ace_type type, 3144 3157 uint32_t mask, uint8_t flags) 3145 3158 { … … 3148 3161 /* first search for a duplicate */ 3149 3162 for (i = 0; i < *num_aces; i++) { 3150 if ( sid_equal(&nt_ace_list[i].trustee, sid) &&3163 if (dom_sid_equal(&nt_ace_list[i].trustee, sid) && 3151 3164 (nt_ace_list[i].flags == flags)) break; 3152 3165 } … … 3179 3192 SMB_ACL_T def_acl, 3180 3193 uint32_t security_info, 3181 SEC_DESC**ppdesc)3182 { 3183 DOM_SIDowner_sid;3184 DOM_SIDgroup_sid;3194 struct security_descriptor **ppdesc) 3195 { 3196 struct dom_sid owner_sid; 3197 struct dom_sid group_sid; 3185 3198 size_t sd_size = 0; 3186 SEC_ACL*psa = NULL;3199 struct security_acl *psa = NULL; 3187 3200 size_t num_acls = 0; 3188 3201 size_t num_def_acls = 0; … … 3190 3203 canon_ace *file_ace = NULL; 3191 3204 canon_ace *dir_ace = NULL; 3192 SEC_ACE*nt_ace_list = NULL;3205 struct security_ace *nt_ace_list = NULL; 3193 3206 size_t num_profile_acls = 0; 3194 DOM_SIDorig_owner_sid;3195 SEC_DESC*psd = NULL;3207 struct dom_sid orig_owner_sid; 3208 struct security_descriptor *psd = NULL; 3196 3209 int i; 3197 3210 … … 3210 3223 } 3211 3224 3212 if ((security_info & DACL_SECURITY_INFORMATION) && !(security_info & PROTECTED_DACL_SECURITY_INFORMATION)) {3225 if ((security_info & SECINFO_DACL) && !(security_info & SECINFO_PROTECTED_DACL)) { 3213 3226 3214 3227 /* … … 3302 3315 3303 3316 /* Allocate the ace list. */ 3304 if ((nt_ace_list = SMB_MALLOC_ARRAY( SEC_ACE,num_acls + num_profile_acls + num_def_acls)) == NULL) {3317 if ((nt_ace_list = SMB_MALLOC_ARRAY(struct security_ace,num_acls + num_profile_acls + num_def_acls)) == NULL) { 3305 3318 DEBUG(0,("get_nt_acl: Unable to malloc space for nt_ace_list.\n")); 3306 3319 goto done; 3307 3320 } 3308 3321 3309 memset(nt_ace_list, '\0', (num_acls + num_def_acls) * sizeof( SEC_ACE) );3322 memset(nt_ace_list, '\0', (num_acls + num_def_acls) * sizeof(struct security_ace) ); 3310 3323 3311 3324 /* … … 3371 3384 if (lp_profile_acls(SNUM(conn))) { 3372 3385 for (i = 0; i < num_aces; i++) { 3373 if ( sid_equal(&nt_ace_list[i].trustee, &owner_sid)) {3386 if (dom_sid_equal(&nt_ace_list[i].trustee, &owner_sid)) { 3374 3387 add_or_replace_ace(nt_ace_list, &num_aces, 3375 3388 &orig_owner_sid, … … 3389 3402 } 3390 3403 } 3391 } /* security_info & DACL_SECURITY_INFORMATION*/3404 } /* security_info & SECINFO_DACL */ 3392 3405 3393 3406 psd = make_standard_sec_desc( talloc_tos(), 3394 (security_info & OWNER_SECURITY_INFORMATION) ? &owner_sid : NULL,3395 (security_info & GROUP_SECURITY_INFORMATION) ? &group_sid : NULL,3407 (security_info & SECINFO_OWNER) ? &owner_sid : NULL, 3408 (security_info & SECINFO_GROUP) ? &group_sid : NULL, 3396 3409 psa, 3397 3410 &sd_size); … … 3442 3455 3443 3456 NTSTATUS posix_fget_nt_acl(struct files_struct *fsp, uint32_t security_info, 3444 SEC_DESC**ppdesc)3457 struct security_descriptor **ppdesc) 3445 3458 { 3446 3459 SMB_STRUCT_STAT sbuf; … … 3475 3488 3476 3489 NTSTATUS posix_get_nt_acl(struct connection_struct *conn, const char *name, 3477 uint32_t security_info, SEC_DESC**ppdesc)3490 uint32_t security_info, struct security_descriptor **ppdesc) 3478 3491 { 3479 3492 SMB_ACL_T posix_acl = NULL; … … 3521 3534 3522 3535 1) If we have root privileges, then it will just work. 3523 2) If we have Se TakeOwnershipPrivilege we can change the user to the current user.3524 3) If we have Se RestorePrivilege we can change the user to any other user.3536 2) If we have SeRestorePrivilege we can change the user + group to any other user. 3537 3) If we have SeTakeOwnershipPrivilege we can change the user to the current user. 3525 3538 4) If we have write permission to the file and dos_filemodes is set 3526 3539 then allow chown to the currently authenticated user. 3527 3540 ****************************************************************************/ 3528 3541 3529 int try_chown(connection_struct *conn, struct smb_filename *smb_fname, 3530 uid_t uid, gid_t gid) 3531 { 3532 int ret; 3533 files_struct *fsp; 3534 3535 if(!CAN_WRITE(conn)) { 3536 return -1; 3542 NTSTATUS try_chown(files_struct *fsp, uid_t uid, gid_t gid) 3543 { 3544 NTSTATUS status; 3545 3546 if(!CAN_WRITE(fsp->conn)) { 3547 return NT_STATUS_MEDIA_WRITE_PROTECTED; 3537 3548 } 3538 3549 3539 3550 /* Case (1). */ 3540 /* try the direct way first */ 3541 if (lp_posix_pathnames()) { 3542 ret = SMB_VFS_LCHOWN(conn, smb_fname->base_name, uid, gid); 3543 } else { 3544 ret = SMB_VFS_CHOWN(conn, smb_fname->base_name, uid, gid); 3545 } 3546 3547 if (ret == 0) 3548 return 0; 3551 status = vfs_chown_fsp(fsp, uid, gid); 3552 if (NT_STATUS_IS_OK(status)) { 3553 return status; 3554 } 3549 3555 3550 3556 /* Case (2) / (3) */ 3551 3557 if (lp_enable_privileges()) { 3552 3553 bool has_take_ownership_priv = user_has_privileges(current_user.nt_user_token, 3554 &se_take_ownership); 3555 bool has_restore_priv = user_has_privileges(current_user.nt_user_token, 3556 &se_restore); 3557 3558 /* Case (2) */ 3559 if ( ( has_take_ownership_priv && ( uid == current_user.ut.uid ) ) || 3560 /* Case (3) */ 3561 ( has_restore_priv ) ) { 3562 3558 bool has_take_ownership_priv = security_token_has_privilege( 3559 get_current_nttok(fsp->conn), 3560 SEC_PRIV_TAKE_OWNERSHIP); 3561 bool has_restore_priv = security_token_has_privilege( 3562 get_current_nttok(fsp->conn), 3563 SEC_PRIV_RESTORE); 3564 3565 if (has_restore_priv) { 3566 ; /* Case (2) */ 3567 } else if (has_take_ownership_priv) { 3568 /* Case (3) */ 3569 if (uid == get_current_uid(fsp->conn)) { 3570 gid = (gid_t)-1; 3571 } else { 3572 has_take_ownership_priv = false; 3573 } 3574 } 3575 3576 if (has_take_ownership_priv || has_restore_priv) { 3563 3577 become_root(); 3564 /* Keep the current file gid the same - take ownership doesn't imply group change. */ 3565 if (lp_posix_pathnames()) { 3566 ret = SMB_VFS_LCHOWN(conn, smb_fname->base_name, uid, 3567 (gid_t)-1); 3568 } else { 3569 ret = SMB_VFS_CHOWN(conn, smb_fname->base_name, uid, 3570 (gid_t)-1); 3571 } 3578 status = vfs_chown_fsp(fsp, uid, gid); 3572 3579 unbecome_root(); 3573 return ret;3580 return status; 3574 3581 } 3575 3582 } 3576 3583 3577 3584 /* Case (4). */ 3578 if (!lp_dos_filemode(SNUM(conn))) { 3579 errno = EPERM; 3580 return -1; 3585 if (!lp_dos_filemode(SNUM(fsp->conn))) { 3586 return NT_STATUS_ACCESS_DENIED; 3581 3587 } 3582 3588 … … 3585 3591 a local SID on the users workstation 3586 3592 */ 3587 if (uid != current_user.ut.uid) { 3588 errno = EPERM; 3589 return -1; 3590 } 3591 3592 if (lp_posix_pathnames()) { 3593 ret = SMB_VFS_LSTAT(conn, smb_fname); 3594 } else { 3595 ret = SMB_VFS_STAT(conn, smb_fname); 3596 } 3597 3598 if (ret == -1) { 3599 return -1; 3600 } 3601 3602 if (!NT_STATUS_IS_OK(open_file_fchmod(conn, smb_fname, &fsp))) { 3603 return -1; 3593 if (uid != get_current_uid(fsp->conn)) { 3594 return NT_STATUS_ACCESS_DENIED; 3604 3595 } 3605 3596 3606 3597 become_root(); 3607 3598 /* Keep the current file gid the same. */ 3608 if (fsp->fh->fd == -1) { 3609 if (lp_posix_pathnames()) { 3610 ret = SMB_VFS_LCHOWN(conn, smb_fname->base_name, uid, 3611 (gid_t)-1); 3612 } else { 3613 ret = SMB_VFS_CHOWN(conn, smb_fname->base_name, uid, 3614 (gid_t)-1); 3615 } 3616 } else { 3617 ret = SMB_VFS_FCHOWN(fsp, uid, (gid_t)-1); 3618 } 3599 status = vfs_chown_fsp(fsp, uid, (gid_t)-1); 3619 3600 unbecome_root(); 3620 3601 3621 close_file(NULL, fsp, NORMAL_CLOSE); 3622 3623 return ret; 3602 return status; 3624 3603 } 3625 3604 … … 3632 3611 3633 3612 NTSTATUS append_parent_acl(files_struct *fsp, 3634 const SEC_DESC*pcsd,3635 SEC_DESC**pp_new_sd)3613 const struct security_descriptor *pcsd, 3614 struct security_descriptor **pp_new_sd) 3636 3615 { 3637 3616 struct smb_filename *smb_dname = NULL; 3638 SEC_DESC*parent_sd = NULL;3617 struct security_descriptor *parent_sd = NULL; 3639 3618 files_struct *parent_fsp = NULL; 3640 3619 TALLOC_CTX *mem_ctx = talloc_tos(); 3641 3620 char *parent_name = NULL; 3642 SEC_ACE*new_ace = NULL;3621 struct security_ace *new_ace = NULL; 3643 3622 unsigned int num_aces = pcsd->dacl->num_aces; 3644 3623 NTSTATUS status; 3645 3624 int info; 3646 3625 unsigned int i, j; 3647 SEC_DESC*psd = dup_sec_desc(talloc_tos(), pcsd);3626 struct security_descriptor *psd = dup_sec_desc(talloc_tos(), pcsd); 3648 3627 bool is_dacl_protected = (pcsd->type & SEC_DESC_DACL_PROTECTED); 3649 3628 … … 3686 3665 3687 3666 status = SMB_VFS_GET_NT_ACL(parent_fsp->conn, smb_dname->base_name, 3688 DACL_SECURITY_INFORMATION, &parent_sd );3667 SECINFO_DACL, &parent_sd ); 3689 3668 3690 3669 close_file(NULL, parent_fsp, NORMAL_CLOSE); … … 3709 3688 num_aces += parent_sd->dacl->num_aces; 3710 3689 3711 if((new_ace = TALLOC_ZERO_ARRAY(mem_ctx, SEC_ACE,3690 if((new_ace = TALLOC_ZERO_ARRAY(mem_ctx, struct security_ace, 3712 3691 num_aces)) == NULL) { 3713 3692 return NT_STATUS_NO_MEMORY; … … 3726 3705 /* Finally append any inherited ACEs. */ 3727 3706 for (j = 0; j < parent_sd->dacl->num_aces; j++) { 3728 SEC_ACE*se = &parent_sd->dacl->aces[j];3707 struct security_ace *se = &parent_sd->dacl->aces[j]; 3729 3708 3730 3709 if (fsp->is_directory) { … … 3762 3741 unsigned int k; 3763 3742 for (k = 0; k < psd->dacl->num_aces; k++) { 3764 if ( sid_equal(&psd->dacl->aces[k].trustee,3743 if (dom_sid_equal(&psd->dacl->aces[k].trustee, 3765 3744 &se->trustee)) { 3766 3745 break; … … 3817 3796 psd->dacl->aces = new_ace; 3818 3797 psd->dacl->num_aces = i; 3819 psd->type &= ~(SE _DESC_DACL_AUTO_INHERITED|3820 SE _DESC_DACL_AUTO_INHERIT_REQ);3798 psd->type &= ~(SEC_DESC_DACL_AUTO_INHERITED| 3799 SEC_DESC_DACL_AUTO_INHERIT_REQ); 3821 3800 3822 3801 *pp_new_sd = psd; … … 3829 3808 description of the following NT ACL. 3830 3809 This should be the only external function needed for the UNIX style set ACL. 3831 ****************************************************************************/ 3832 3833 NTSTATUS set_nt_acl(files_struct *fsp, uint32 security_info_sent, const SEC_DESC *psd_orig) 3810 We make a copy of psd_orig as internal functions modify the elements inside 3811 it, even though it's a const pointer. 3812 ****************************************************************************/ 3813 3814 NTSTATUS set_nt_acl(files_struct *fsp, uint32 security_info_sent, const struct security_descriptor *psd_orig) 3834 3815 { 3835 3816 connection_struct *conn = fsp->conn; 3836 3817 uid_t user = (uid_t)-1; 3837 3818 gid_t grp = (gid_t)-1; 3838 DOM_SIDfile_owner_sid;3839 DOM_SIDfile_grp_sid;3819 struct dom_sid file_owner_sid; 3820 struct dom_sid file_grp_sid; 3840 3821 canon_ace *file_ace_list = NULL; 3841 3822 canon_ace *dir_ace_list = NULL; … … 3846 3827 bool acl_set_support = false; 3847 3828 bool ret = false; 3848 SEC_DESC*psd = NULL;3829 struct security_descriptor *psd = NULL; 3849 3830 3850 3831 DEBUG(10,("set_nt_acl: called for file %s\n", … … 3889 3870 } 3890 3871 3891 status = unpack_nt_owners( SNUM(conn), &user, &grp, security_info_sent, psd);3872 status = unpack_nt_owners( conn, &user, &grp, security_info_sent, psd); 3892 3873 if (!NT_STATUS_IS_OK(status)) { 3893 3874 return status; … … 3907 3888 (unsigned int)grp)); 3908 3889 3909 if(try_chown(fsp->conn, fsp->fsp_name, user, grp) == -1) { 3890 status = try_chown(fsp, user, grp); 3891 if(!NT_STATUS_IS_OK(status)) { 3910 3892 DEBUG(3,("set_nt_acl: chown %s, %u, %u failed. Error " 3911 "= %s.\n", fsp_str_dbg(fsp), 3912 (unsigned int)user, (unsigned int)grp, 3913 strerror(errno))); 3914 if (errno == EPERM) { 3915 return NT_STATUS_INVALID_OWNER; 3916 } 3917 return map_nt_error_from_unix(errno); 3893 "= %s.\n", fsp_str_dbg(fsp), 3894 (unsigned int)user, 3895 (unsigned int)grp, 3896 nt_errstr(status))); 3897 return status; 3918 3898 } 3919 3899 … … 3942 3922 (psd->type & SEC_DESC_DACL_PRESENT) && 3943 3923 (psd->dacl == NULL)) { 3944 SEC_ACEace[3];3924 struct security_ace ace[3]; 3945 3925 3946 3926 /* We can't have NULL DACL in POSIX. … … 3992 3972 */ 3993 3973 3994 if(!(security_info_sent & DACL_SECURITY_INFORMATION) || (psd->dacl == NULL)) {3974 if(!(security_info_sent & SECINFO_DACL) || (psd->dacl == NULL)) { 3995 3975 free_canon_ace_list(file_ace_list); 3996 3976 free_canon_ace_list(dir_ace_list); … … 4757 4737 ********************************************************************/ 4758 4738 4759 SEC_DESC*get_nt_acl_no_snum( TALLOC_CTX *ctx, const char *fname)4760 { 4761 SEC_DESC*psd, *ret_sd;4739 struct security_descriptor *get_nt_acl_no_snum( TALLOC_CTX *ctx, const char *fname) 4740 { 4741 struct security_descriptor *psd, *ret_sd; 4762 4742 connection_struct *conn; 4763 4743 files_struct finfo; … … 4802 4782 } 4803 4783 4804 if (!NT_STATUS_IS_OK(SMB_VFS_FGET_NT_ACL( &finfo, DACL_SECURITY_INFORMATION, &psd))) {4784 if (!NT_STATUS_IS_OK(SMB_VFS_FGET_NT_ACL( &finfo, SECINFO_DACL, &psd))) { 4805 4785 DEBUG(0,("get_nt_acl_no_snum: get_nt_acl returned zero.\n")); 4806 4786 TALLOC_FREE(finfo.fsp_name); … … 4822 4802 const char *name, 4823 4803 SMB_STRUCT_STAT *psbuf, 4824 SEC_DESC**ppdesc)4804 struct security_descriptor **ppdesc) 4825 4805 { 4826 4806 struct dom_sid owner_sid, group_sid; 4827 4807 size_t size = 0; 4828 SEC_ACEaces[4];4808 struct security_ace aces[4]; 4829 4809 uint32_t access_mask = 0; 4830 4810 mode_t mode = psbuf->st_ex_mode; 4831 SEC_ACL*new_dacl = NULL;4811 struct security_acl *new_dacl = NULL; 4832 4812 int idx = 0; 4833 4813
Note:
See TracChangeset
for help on using the changeset viewer.