static NTSTATUS smb_get_nt_acl_nfs4_common(const SMB_STRUCT_STAT *sbuf, smbacl4_vfs_params *params, uint32_t security_info, TALLOC_CTX *mem_ctx, struct security_descriptor **ppdesc, struct SMB4ACL_T *theacl) { int good_aces = 0; struct dom_sid sid_owner, sid_group; size_t sd_size = 0; struct security_ace *nt_ace_list = NULL; struct security_acl *psa = NULL; TALLOC_CTX *frame = talloc_stackframe(); bool ok; if (theacl==NULL) { TALLOC_FREE(frame); return NT_STATUS_ACCESS_DENIED; /* special because we * need to think through * the null case.*/ } uid_to_sid(&sid_owner, sbuf->st_ex_uid); gid_to_sid(&sid_group, sbuf->st_ex_gid); ok = smbacl4_nfs42win(frame, params, theacl, &sid_owner, &sid_group, S_ISDIR(sbuf->st_ex_mode), &nt_ace_list, &good_aces); if (!ok) { DEBUG(8,("smbacl4_nfs42win failed\n")); TALLOC_FREE(frame); return map_nt_error_from_unix(errno); } psa = make_sec_acl(frame, NT4_ACL_REVISION, good_aces, nt_ace_list); if (psa == NULL) { DEBUG(2,("make_sec_acl failed\n")); TALLOC_FREE(frame); return NT_STATUS_NO_MEMORY; } DEBUG(10,("after make sec_acl\n")); *ppdesc = make_sec_desc( mem_ctx, SD_REVISION, smbacl4_get_controlflags(theacl), (security_info & SECINFO_OWNER) ? &sid_owner : NULL, (security_info & SECINFO_GROUP) ? &sid_group : NULL, NULL, psa, &sd_size); if (*ppdesc==NULL) { DEBUG(2,("make_sec_desc failed\n")); TALLOC_FREE(frame); return NT_STATUS_NO_MEMORY; } DEBUG(10, ("smb_get_nt_acl_nfs4_common successfully exited with " "sd_size %d\n", (int)ndr_size_security_descriptor(*ppdesc, 0))); TALLOC_FREE(frame); return NT_STATUS_OK; }
struct security_descriptor *get_share_security( TALLOC_CTX *ctx, const char *servicename, size_t *psize) { char *key; struct security_descriptor *psd = NULL; TDB_DATA data; char *c_servicename = canonicalize_servicename(talloc_tos(), servicename); NTSTATUS status; if (!c_servicename) { return NULL; } if (!share_info_db_init()) { TALLOC_FREE(c_servicename); return NULL; } if (!(key = talloc_asprintf(ctx, SHARE_SECURITY_DB_KEY_PREFIX_STR "%s", c_servicename))) { TALLOC_FREE(c_servicename); DEBUG(0, ("talloc_asprintf failed\n")); return NULL; } TALLOC_FREE(c_servicename); status = dbwrap_fetch_bystring(share_db, talloc_tos(), key, &data); TALLOC_FREE(key); if (!NT_STATUS_IS_OK(status)) { return get_share_security_default(ctx, psize, SEC_RIGHTS_DIR_ALL); } status = unmarshall_sec_desc(ctx, data.dptr, data.dsize, &psd); TALLOC_FREE(data.dptr); if (!NT_STATUS_IS_OK(status)) { DEBUG(0, ("unmarshall_sec_desc failed: %s\n", nt_errstr(status))); return get_share_security_default(ctx, psize, SEC_RIGHTS_DIR_ALL); } if (psd) { *psize = ndr_size_security_descriptor(psd, 0); } else { return get_share_security_default(ctx, psize, SEC_RIGHTS_DIR_ALL); } return psd; }
_PUBLIC_ void ndr_print_sec_desc_buf(struct ndr_print *ndr, const char *name, const struct sec_desc_buf *r) { ndr_print_struct(ndr, name, "sec_desc_buf"); ndr->depth++; ndr_print_uint32(ndr, "sd_size", (ndr->flags & LIBNDR_PRINT_SET_VALUES)?ndr_size_security_descriptor(r->sd, ndr->iconv_convenience, ndr->flags):r->sd_size); ndr_print_ptr(ndr, "sd", r->sd); ndr->depth++; if (r->sd) { ndr_print_security_descriptor(ndr, "sd", r->sd); } ndr->depth--; ndr->depth--; }
NTSTATUS ndr_push_sec_desc_buf(struct ndr_push *ndr, int ndr_flags, const struct sec_desc_buf *r) { if (ndr_flags & NDR_SCALARS) { NDR_CHECK(ndr_push_align(ndr, 4)); NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, ndr_size_security_descriptor(r->sd,ndr->flags))); NDR_CHECK(ndr_push_unique_ptr(ndr, r->sd)); } if (ndr_flags & NDR_BUFFERS) { if (r->sd) { { struct ndr_push *_ndr_sd; NDR_CHECK(ndr_push_subcontext_start(ndr, &_ndr_sd, 4, -1)); NDR_CHECK(ndr_push_security_descriptor(_ndr_sd, NDR_SCALARS|NDR_BUFFERS, r->sd)); NDR_CHECK(ndr_push_subcontext_end(ndr, _ndr_sd, 4, -1)); } } } return NT_STATUS_OK; }
_PUBLIC_ enum ndr_err_code ndr_push_sec_desc_buf(struct ndr_push *ndr, int ndr_flags, const struct sec_desc_buf *r) { if (ndr_flags & NDR_SCALARS) { NDR_CHECK(ndr_push_align(ndr, 5)); NDR_CHECK(ndr_push_uint32(ndr, NDR_SCALARS, ndr_size_security_descriptor(r->sd, ndr->iconv_convenience, ndr->flags))); NDR_CHECK(ndr_push_unique_ptr(ndr, r->sd)); NDR_CHECK(ndr_push_trailer_align(ndr, 5)); } if (ndr_flags & NDR_BUFFERS) { if (r->sd) { { struct ndr_push *_ndr_sd; NDR_CHECK(ndr_push_subcontext_start(ndr, &_ndr_sd, 4, -1)); NDR_CHECK(ndr_push_security_descriptor(_ndr_sd, NDR_SCALARS|NDR_BUFFERS, r->sd)); NDR_CHECK(ndr_push_subcontext_end(ndr, _ndr_sd, 4, -1)); } } } return NDR_ERR_SUCCESS; }
SEC_DESC *get_share_security( TALLOC_CTX *ctx, const char *servicename, size_t *psize) { char *key; SEC_DESC *psd = NULL; TDB_DATA data; NTSTATUS status; if (!share_info_db_init()) { return NULL; } if (!(key = talloc_asprintf(ctx, "SECDESC/%s", servicename))) { DEBUG(0, ("talloc_asprintf failed\n")); return NULL; } data = dbwrap_fetch_bystring(share_db, talloc_tos(), key); TALLOC_FREE(key); if (data.dptr == NULL) { return get_share_security_default(ctx, psize, GENERIC_ALL_ACCESS); } status = unmarshall_sec_desc(ctx, data.dptr, data.dsize, &psd); TALLOC_FREE(data.dptr); if (!NT_STATUS_IS_OK(status)) { DEBUG(0, ("unmarshall_sec_desc failed: %s\n", nt_errstr(status))); return NULL; } if (psd) *psize = ndr_size_security_descriptor(psd, NULL, 0); return psd; }
static NTSTATUS map_SHARE_INFO_buffer_to_srvsvc_share_info(TALLOC_CTX *mem_ctx, uint8_t *buffer, uint32_t level, union srvsvc_NetShareInfo *info) { struct SHARE_INFO_2 *i2 = NULL; struct SHARE_INFO_502 *i502 = NULL; struct SHARE_INFO_1004 *i1004 = NULL; struct srvsvc_NetShareInfo2 *s2 = NULL; struct srvsvc_NetShareInfo502 *s502 = NULL; struct srvsvc_NetShareInfo1004 *s1004 = NULL; if (!buffer) { return NT_STATUS_INVALID_PARAMETER; } switch (level) { case 2: i2 = (struct SHARE_INFO_2 *)buffer; s2 = talloc(mem_ctx, struct srvsvc_NetShareInfo2); NT_STATUS_HAVE_NO_MEMORY(s2); s2->name = i2->shi2_netname; s2->type = i2->shi2_type; s2->comment = i2->shi2_remark; s2->permissions = i2->shi2_permissions; s2->max_users = i2->shi2_max_uses; s2->current_users = i2->shi2_current_uses; s2->path = i2->shi2_path; s2->password = i2->shi2_passwd; info->info2 = s2; break; case 502: i502 = (struct SHARE_INFO_502 *)buffer; s502 = talloc(mem_ctx, struct srvsvc_NetShareInfo502); NT_STATUS_HAVE_NO_MEMORY(s502); s502->name = i502->shi502_netname; s502->type = i502->shi502_type; s502->comment = i502->shi502_remark; s502->permissions = i502->shi502_permissions; s502->max_users = i502->shi502_max_uses; s502->current_users = i502->shi502_current_uses; s502->path = i502->shi502_path; s502->password = i502->shi502_passwd; s502->sd_buf.sd_size = ndr_size_security_descriptor(i502->shi502_security_descriptor, 0); s502->sd_buf.sd = i502->shi502_security_descriptor; info->info502 = s502; break; case 1004: i1004 = (struct SHARE_INFO_1004 *)buffer; s1004 = talloc(mem_ctx, struct srvsvc_NetShareInfo1004); NT_STATUS_HAVE_NO_MEMORY(s1004); s1004->comment = i1004->shi1004_remark; info->info1004 = s1004; break; default: return NT_STATUS_INVALID_PARAMETER; } return NT_STATUS_OK; }