summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--source3/include/vfs.h7
-rw-r--r--source3/include/vfs_macros.h4
-rw-r--r--source3/rpc_parse/parse_sec.c57
-rw-r--r--source3/rpc_server/srv_srvsvc_nt.c2
-rw-r--r--source3/smbd/dir.c6
-rw-r--r--source3/smbd/nttrans.c194
-rw-r--r--source3/smbd/posix_acls.c283
-rw-r--r--source3/smbd/vfs-wrap.c8
8 files changed, 278 insertions, 283 deletions
diff --git a/source3/include/vfs.h b/source3/include/vfs.h
index f10719144d..92cd065c83 100644
--- a/source3/include/vfs.h
+++ b/source3/include/vfs.h
@@ -47,7 +47,8 @@
/* Changed to version 4 for cascaded VFS interface. Alexander Bokovoy. */
/* Changed to version 5 for sendfile addition. JRA. */
/* Changed to version 6 for the new module system, fixed cascading and quota functions. --metze */
-#define SMB_VFS_INTERFACE_VERSION 6
+/* Version 7 to include the get_nt_acl info parameter. JRA. */
+#define SMB_VFS_INTERFACE_VERSION 7
/* to bug old modules witch are trying to compile with the old functions */
@@ -218,8 +219,8 @@ struct vfs_ops {
/* NT ACL operations. */
- size_t (*fget_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, int fd, struct security_descriptor_info **ppdesc);
- size_t (*get_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, const char *name, struct security_descriptor_info **ppdesc);
+ size_t (*fget_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, int fd, uint32 security_info, struct security_descriptor_info **ppdesc);
+ size_t (*get_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, const char *name, uint32 security_info, struct security_descriptor_info **ppdesc);
BOOL (*fset_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, int fd, uint32 security_info_sent, struct security_descriptor_info *psd);
BOOL (*set_nt_acl)(struct vfs_handle_struct *handle, struct files_struct *fsp, const char *name, uint32 security_info_sent, struct security_descriptor_info *psd);
diff --git a/source3/include/vfs_macros.h b/source3/include/vfs_macros.h
index aac8dcdca5..fc25976383 100644
--- a/source3/include/vfs_macros.h
+++ b/source3/include/vfs_macros.h
@@ -70,8 +70,8 @@
#define SMB_VFS_REALPATH(conn, path, resolved_path) ((conn)->vfs.ops.realpath((conn)->vfs.handles.realpath, (conn), (path), (resolved_path)))
/* NT ACL operations. */
-#define SMB_VFS_FGET_NT_ACL(fsp, fd, ppdesc) ((fsp)->conn->vfs.ops.fget_nt_acl((fsp)->conn->vfs.handles.fget_nt_acl, (fsp), (fd), (ppdesc)))
-#define SMB_VFS_GET_NT_ACL(fsp, name, ppdesc) ((fsp)->conn->vfs.ops.get_nt_acl((fsp)->conn->vfs.handles.get_nt_acl, (fsp), (name), (ppdesc)))
+#define SMB_VFS_FGET_NT_ACL(fsp, fd, security_info, ppdesc) ((fsp)->conn->vfs.ops.fget_nt_acl((fsp)->conn->vfs.handles.fget_nt_acl, (fsp), (fd), (security_info), (ppdesc)))
+#define SMB_VFS_GET_NT_ACL(fsp, name, security_info, ppdesc) ((fsp)->conn->vfs.ops.get_nt_acl((fsp)->conn->vfs.handles.get_nt_acl, (fsp), (name), (security_info), (ppdesc)))
#define SMB_VFS_FSET_NT_ACL(fsp, fd, security_info_sent, psd) ((fsp)->conn->vfs.ops.fset_nt_acl((fsp)->conn->vfs.handles.fset_nt_acl, (fsp), (fd), (security_info_sent), (psd)))
#define SMB_VFS_SET_NT_ACL(fsp, name, security_info_sent, psd) ((fsp)->conn->vfs.ops.set_nt_acl((fsp)->conn->vfs.handles.set_nt_acl, (fsp), (name), (security_info_sent), (psd)))
diff --git a/source3/rpc_parse/parse_sec.c b/source3/rpc_parse/parse_sec.c
index 081173cf8d..870402db5d 100644
--- a/source3/rpc_parse/parse_sec.c
+++ b/source3/rpc_parse/parse_sec.c
@@ -48,7 +48,7 @@ BOOL sec_io_access(const char *desc, SEC_ACCESS *t, prs_struct *ps, int depth)
prs_debug(ps, depth, desc, "sec_io_access");
depth++;
- if(!prs_uint32("mask", ps, depth, &(t->mask)))
+ if(!prs_uint32("mask", ps, depth, &t->mask))
return False;
return True;
@@ -579,8 +579,6 @@ SEC_DESC *make_sec_desc(TALLOC_CTX *ctx, uint16 revision,
{
SEC_DESC *dst;
uint32 offset = 0;
- uint32 offset_sid = SEC_DESC_HEADER_SIZE;
- uint32 offset_acl = 0;
*sd_size = 0;
@@ -610,58 +608,33 @@ SEC_DESC *make_sec_desc(TALLOC_CTX *ctx, uint16 revision,
if(dacl && ((dst->dacl = dup_sec_acl(ctx, dacl)) == NULL))
goto error_exit;
- offset = 0;
+ offset = SEC_DESC_HEADER_SIZE;
/*
* Work out the linearization sizes.
*/
- if (dst->owner_sid != NULL) {
-
- if (offset == 0)
- offset = SEC_DESC_HEADER_SIZE;
-
- offset += sid_size(dst->owner_sid);
- }
-
- if (dst->grp_sid != NULL) {
-
- if (offset == 0)
- offset = SEC_DESC_HEADER_SIZE;
-
- offset += sid_size(dst->grp_sid);
- }
if (dst->sacl != NULL) {
-
- offset_acl = SEC_DESC_HEADER_SIZE;
-
- dst->off_sacl = offset_acl;
- offset_acl += dst->sacl->size;
- offset += dst->sacl->size;
- offset_sid += dst->sacl->size;
+ dst->off_sacl = offset;
+ offset += dst->sacl->size;
}
if (dst->dacl != NULL) {
-
- if (offset_acl == 0)
- offset_acl = SEC_DESC_HEADER_SIZE;
-
- dst->off_dacl = offset_acl;
- offset_acl += dst->dacl->size;
- offset += dst->dacl->size;
- offset_sid += dst->dacl->size;
+ dst->off_dacl = offset;
+ offset += dst->dacl->size;
}
- *sd_size = (size_t)((offset == 0) ? SEC_DESC_HEADER_SIZE : offset);
+ if (dst->owner_sid != NULL) {
+ dst->off_owner_sid = offset;
+ offset += sid_size(dst->owner_sid);
+ }
- if (dst->owner_sid != NULL)
- dst->off_owner_sid = offset_sid;
-
- /* sid_size() returns 0 if the sid is NULL so this is ok */
-
- if (dst->grp_sid != NULL)
- dst->off_grp_sid = offset_sid + sid_size(dst->owner_sid);
+ if (dst->grp_sid != NULL) {
+ dst->off_grp_sid = offset;
+ offset += sid_size(dst->grp_sid);
+ }
+ *sd_size = (size_t)offset;
return dst;
error_exit:
diff --git a/source3/rpc_server/srv_srvsvc_nt.c b/source3/rpc_server/srv_srvsvc_nt.c
index 154376dd33..57ba055aef 100644
--- a/source3/rpc_server/srv_srvsvc_nt.c
+++ b/source3/rpc_server/srv_srvsvc_nt.c
@@ -1887,7 +1887,7 @@ WERROR _srv_net_file_query_secdesc(pipes_struct *p, SRV_Q_NET_FILE_QUERY_SECDESC
}
}
- sd_size = SMB_VFS_GET_NT_ACL(fsp, fsp->fsp_name, &psd);
+ sd_size = SMB_VFS_GET_NT_ACL(fsp, fsp->fsp_name, (OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|DACL_SECURITY_INFORMATION), &psd);
if (sd_size == 0) {
DEBUG(3,("_srv_net_file_query_secdesc: Unable to get NT ACL for file %s\n", filename));
diff --git a/source3/smbd/dir.c b/source3/smbd/dir.c
index 910ab35de8..94b605ee8f 100644
--- a/source3/smbd/dir.c
+++ b/source3/smbd/dir.c
@@ -715,7 +715,8 @@ static BOOL user_can_read_file(connection_struct *conn, char *name, SMB_STRUCT_S
return False;
/* Get NT ACL -allocated in main loop talloc context. No free needed here. */
- sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd, &psd);
+ sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd,
+ (OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|DACL_SECURITY_INFORMATION), &psd);
close_file(fsp, True);
/* No access if SD get failed. */
@@ -768,7 +769,8 @@ static BOOL user_can_write_file(connection_struct *conn, char *name, SMB_STRUCT_
return False;
/* Get NT ACL -allocated in main loop talloc context. No free needed here. */
- sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd, &psd);
+ sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd,
+ (OWNER_SECURITY_INFORMATION|GROUP_SECURITY_INFORMATION|DACL_SECURITY_INFORMATION), &psd);
close_file(fsp, False);
/* No access if SD get failed. */
diff --git a/source3/smbd/nttrans.c b/source3/smbd/nttrans.c
index d0066c367c..fa7b78ecc2 100644
--- a/source3/smbd/nttrans.c
+++ b/source3/smbd/nttrans.c
@@ -964,13 +964,12 @@ create_options = 0x%x root_dir_fid = 0x%x\n", flags, desired_access, file_attrib
Reply to a NT_TRANSACT_CREATE call to open a pipe.
****************************************************************************/
-static int do_nt_transact_create_pipe( connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize, char **ppsetup, char **ppparams,
- char **ppdata)
+static int do_nt_transact_create_pipe( connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
pstring fname;
- int total_parameter_count = (int)IVAL(inbuf, smb_nt_TotalParameterCount);
char *params = *ppparams;
int ret;
int pnum = -1;
@@ -980,12 +979,12 @@ static int do_nt_transact_create_pipe( connection_struct *conn,
* Ensure minimum number of parameters sent.
*/
- if(total_parameter_count < 54) {
- DEBUG(0,("do_nt_transact_create_pipe - insufficient parameters (%u)\n", (unsigned int)total_parameter_count));
+ if(parameter_count < 54) {
+ DEBUG(0,("do_nt_transact_create_pipe - insufficient parameters (%u)\n", (unsigned int)parameter_count));
return ERROR_DOS(ERRDOS,ERRnoaccess);
}
- srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
+ srvstr_pull(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE);
if ((ret = nt_open_pipe(fname, conn, inbuf, outbuf, &pnum)) != 0)
return ret;
@@ -1091,15 +1090,14 @@ static NTSTATUS set_sd(files_struct *fsp, char *data, uint32 sd_len, uint32 secu
Reply to a NT_TRANSACT_CREATE call (needs to process SD's).
****************************************************************************/
-static int call_nt_transact_create(connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize, char **ppsetup, char **ppparams,
- char **ppdata)
+static int call_nt_transact_create(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
pstring fname;
char *params = *ppparams;
char *data = *ppdata;
- int total_parameter_count = (int)IVAL(inbuf, smb_nt_TotalParameterCount);
/* Breakout the oplock request bits so we can set the reply bits separately. */
int oplock_request = 0;
mode_t unixmode;
@@ -1135,7 +1133,10 @@ static int call_nt_transact_create(connection_struct *conn,
if (IS_IPC(conn)) {
if (lp_nt_pipe_support())
return do_nt_transact_create_pipe(conn, inbuf, outbuf, length,
- bufsize, ppsetup, ppparams, ppdata);
+ bufsize,
+ ppsetup, setup_count,
+ ppparams, parameter_count,
+ ppdata, data_count);
else
return ERROR_DOS(ERRDOS,ERRnoaccess);
}
@@ -1144,8 +1145,8 @@ static int call_nt_transact_create(connection_struct *conn,
* Ensure minimum number of parameters sent.
*/
- if(total_parameter_count < 54) {
- DEBUG(0,("call_nt_transact_create - insufficient parameters (%u)\n", (unsigned int)total_parameter_count));
+ if(parameter_count < 54) {
+ DEBUG(0,("call_nt_transact_create - insufficient parameters (%u)\n", (unsigned int)parameter_count));
return ERROR_DOS(ERRDOS,ERRnoaccess);
}
@@ -1189,7 +1190,7 @@ static int call_nt_transact_create(connection_struct *conn,
if(!dir_fsp->is_directory) {
- srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
+ srvstr_pull(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE);
/*
* Check to see if this is a mac fork of some kind.
@@ -1218,9 +1219,9 @@ static int call_nt_transact_create(connection_struct *conn,
}
srvstr_pull(inbuf, &fname[dir_name_len], params+53, sizeof(fname)-dir_name_len,
- total_parameter_count-53, STR_TERMINATE);
+ parameter_count-53, STR_TERMINATE);
} else {
- srvstr_pull(inbuf, fname, params+53, sizeof(fname), total_parameter_count-53, STR_TERMINATE);
+ srvstr_pull(inbuf, fname, params+53, sizeof(fname), parameter_count-53, STR_TERMINATE);
/*
* Check to see if this is a mac fork of some kind.
@@ -1467,11 +1468,10 @@ int reply_nttranss(connection_struct *conn,
don't allow a directory to be opened.
****************************************************************************/
-static int call_nt_transact_notify_change(connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize,
- char **ppsetup,
- char **ppparams, char **ppdata)
+static int call_nt_transact_notify_change(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
char *setup = *ppsetup;
files_struct *fsp;
@@ -1501,17 +1501,22 @@ name = %s\n", fsp->fsp_name ));
Reply to an NT transact rename command.
****************************************************************************/
-static int call_nt_transact_rename(connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize,
- char **ppsetup, char **ppparams, char **ppdata)
+static int call_nt_transact_rename(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
char *params = *ppparams;
pstring new_name;
- files_struct *fsp = file_fsp(params, 0);
- BOOL replace_if_exists = (SVAL(params,2) & RENAME_REPLACE_IF_EXISTS) ? True : False;
+ files_struct *fsp = NULL;
+ BOOL replace_if_exists = False;
NTSTATUS status;
+ if(parameter_count < 4)
+ return ERROR_DOS(ERRDOS,ERRbadfunc);
+
+ fsp = file_fsp(params, 0);
+ replace_if_exists = (SVAL(params,2) & RENAME_REPLACE_IF_EXISTS) ? True : False;
CHECK_FSP(fsp, conn);
srvstr_pull(inbuf, new_name, params+4, sizeof(new_name), -1, STR_TERMINATE);
@@ -1557,15 +1562,13 @@ static size_t get_null_nt_acl(TALLOC_CTX *mem_ctx, SEC_DESC **ppsd)
}
/****************************************************************************
- Reply to query a security descriptor - currently this is not implemented (it
- is planned to be though). Right now it just returns the same thing NT would
- when queried on a FAT filesystem. JRA.
+ Reply to query a security descriptor.
****************************************************************************/
-static int call_nt_transact_query_security_desc(connection_struct *conn,
- char *inbuf, char *outbuf,
- int length, int bufsize,
- char **ppsetup, char **ppparams, char **ppdata)
+static int call_nt_transact_query_security_desc(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
uint32 max_data_count = IVAL(inbuf,smb_nt_MaxDataCount);
char *params = *ppparams;
@@ -1573,13 +1576,19 @@ static int call_nt_transact_query_security_desc(connection_struct *conn,
prs_struct pd;
SEC_DESC *psd = NULL;
size_t sd_size;
+ uint32 security_info_wanted;
TALLOC_CTX *mem_ctx;
+ files_struct *fsp = NULL;
- files_struct *fsp = file_fsp(params,0);
+ if(parameter_count < 8)
+ return ERROR_DOS(ERRDOS,ERRbadfunc);
+ fsp = file_fsp(params,0);
if(!fsp)
return ERROR_DOS(ERRDOS,ERRbadfid);
+ security_info_wanted = IVAL(params,4);
+
DEBUG(3,("call_nt_transact_query_security_desc: file = %s\n", fsp->fsp_name ));
params = nttrans_realloc(ppparams, 4);
@@ -1598,7 +1607,7 @@ static int call_nt_transact_query_security_desc(connection_struct *conn,
if (!lp_nt_acl_support(SNUM(conn)))
sd_size = get_null_nt_acl(mem_ctx, &psd);
else
- sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd, &psd);
+ sd_size = SMB_VFS_FGET_NT_ACL(fsp, fsp->fd, security_info_wanted, &psd);
if (sd_size == 0) {
talloc_destroy(mem_ctx);
@@ -1665,23 +1674,21 @@ security descriptor.\n"));
}
/****************************************************************************
- Reply to set a security descriptor. Map to UNIX perms.
+ Reply to set a security descriptor. Map to UNIX perms or POSIX ACLs.
****************************************************************************/
-static int call_nt_transact_set_security_desc(connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize, char **ppsetup,
- char **ppparams, char **ppdata)
+static int call_nt_transact_set_security_desc(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
- uint32 total_parameter_count = IVAL(inbuf, smb_nts_TotalParameterCount);
char *params= *ppparams;
char *data = *ppdata;
- uint32 total_data_count = (uint32)IVAL(inbuf, smb_nts_TotalDataCount);
files_struct *fsp = NULL;
uint32 security_info_sent = 0;
NTSTATUS nt_status;
- if(total_parameter_count < 8)
+ if(parameter_count < 8)
return ERROR_DOS(ERRDOS,ERRbadfunc);
if((fsp = file_fsp(params,0)) == NULL)
@@ -1695,10 +1702,10 @@ static int call_nt_transact_set_security_desc(connection_struct *conn,
DEBUG(3,("call_nt_transact_set_security_desc: file = %s, sent 0x%x\n", fsp->fsp_name,
(unsigned int)security_info_sent ));
- if (total_data_count == 0)
+ if (data_count == 0)
return ERROR_DOS(ERRDOS, ERRnoaccess);
- if (!NT_STATUS_IS_OK(nt_status = set_sd( fsp, data, total_data_count, security_info_sent)))
+ if (!NT_STATUS_IS_OK(nt_status = set_sd( fsp, data, data_count, security_info_sent)))
return ERROR_NT(nt_status);
done:
@@ -1710,12 +1717,11 @@ static int call_nt_transact_set_security_desc(connection_struct *conn,
/****************************************************************************
Reply to NT IOCTL
****************************************************************************/
-static int call_nt_transact_ioctl(connection_struct *conn,
- char *inbuf, char *outbuf, int length,
- int bufsize,
- char **ppsetup, int setup_count,
- char **ppparams, int parameter_count,
- char **ppdata, int data_count)
+
+static int call_nt_transact_ioctl(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
unsigned fnum, control;
static BOOL logged_message;
@@ -1835,12 +1841,10 @@ static int call_nt_transact_ioctl(connection_struct *conn,
Reply to get user quota
****************************************************************************/
-static int call_nt_transact_get_user_quota(connection_struct *conn,
- char *inbuf, char *outbuf,
- int length, int bufsize,
- char **ppsetup, int setup_count,
- char **ppparams, int params_count,
- char **ppdata, int data_count)
+static int call_nt_transact_get_user_quota(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
NTSTATUS nt_status = NT_STATUS_OK;
uint32 max_data_count = IVAL(inbuf,smb_nt_MaxDataCount);
@@ -1872,8 +1876,8 @@ static int call_nt_transact_get_user_quota(connection_struct *conn,
* Ensure minimum number of parameters sent.
*/
- if (params_count < 4) {
- DEBUG(0,("TRANSACT_GET_USER_QUOTA: requires %d >= 4 bytes parameters\n",params_count));
+ if (parameter_count < 4) {
+ DEBUG(0,("TRANSACT_GET_USER_QUOTA: requires %d >= 4 bytes parameters\n",parameter_count));
return ERROR_DOS(ERRDOS,ERRinvalidparam);
}
@@ -2086,12 +2090,10 @@ static int call_nt_transact_get_user_quota(connection_struct *conn,
Reply to set user quota
****************************************************************************/
-static int call_nt_transact_set_user_quota(connection_struct *conn,
- char *inbuf, char *outbuf,
- int length, int bufsize,
- char **ppsetup, int setup_count,
- char **ppparams, int params_count,
- char **ppdata, int data_count)
+static int call_nt_transact_set_user_quota(connection_struct *conn, char *inbuf, char *outbuf, int length, int bufsize,
+ char **ppsetup, uint32 setup_count,
+ char **ppparams, uint32 parameter_count,
+ char **ppdata, uint32 data_count)
{
char *params = *ppparams;
char *pdata = *ppdata;
@@ -2114,8 +2116,8 @@ static int call_nt_transact_set_user_quota(connection_struct *conn,
* Ensure minimum number of parameters sent.
*/
- if (params_count < 2) {
- DEBUG(0,("TRANSACT_SET_USER_QUOTA: requires %d >= 2 bytes parameters\n",params_count));
+ if (parameter_count < 2) {
+ DEBUG(0,("TRANSACT_SET_USER_QUOTA: requires %d >= 2 bytes parameters\n",parameter_count));
return ERROR_DOS(ERRDOS,ERRinvalidparam);
}
@@ -2403,8 +2405,10 @@ due to being in oplock break state.\n", (unsigned int)function_code ));
case NT_TRANSACT_CREATE:
START_PROFILE_NESTED(NT_transact_create);
outsize = call_nt_transact_create(conn, inbuf, outbuf,
- length, bufsize,
- &setup, &params, &data);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_create);
break;
case NT_TRANSACT_IOCTL:
@@ -2412,56 +2416,64 @@ due to being in oplock break state.\n", (unsigned int)function_code ));
outsize = call_nt_transact_ioctl(conn, inbuf, outbuf,
length, bufsize,
&setup, setup_count,
- &params, parameter_count,
- &data, data_count);
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_ioctl);
break;
case NT_TRANSACT_SET_SECURITY_DESC:
START_PROFILE_NESTED(NT_transact_set_security_desc);
outsize = call_nt_transact_set_security_desc(conn, inbuf, outbuf,
- length, bufsize,
- &setup, &params, &data);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_set_security_desc);
break;
case NT_TRANSACT_NOTIFY_CHANGE:
START_PROFILE_NESTED(NT_transact_notify_change);
outsize = call_nt_transact_notify_change(conn, inbuf, outbuf,
- length, bufsize,
- &setup, &params, &data);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_notify_change);
break;
case NT_TRANSACT_RENAME:
START_PROFILE_NESTED(NT_transact_rename);
outsize = call_nt_transact_rename(conn, inbuf, outbuf,
- length, bufsize,
- &setup, &params, &data);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_rename);
break;
case NT_TRANSACT_QUERY_SECURITY_DESC:
START_PROFILE_NESTED(NT_transact_query_security_desc);
outsize = call_nt_transact_query_security_desc(conn, inbuf, outbuf,
- length, bufsize,
- &setup, &params, &data);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_query_security_desc);
break;
#ifdef HAVE_SYS_QUOTAS
case NT_TRANSACT_GET_USER_QUOTA:
START_PROFILE_NESTED(NT_transact_get_user_quota);
outsize = call_nt_transact_get_user_quota(conn, inbuf, outbuf,
- length, bufsize,
- &setup, setup_count,
- &params, parameter_count,
- &data, data_count);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_get_user_quota);
break;
case NT_TRANSACT_SET_USER_QUOTA:
START_PROFILE_NESTED(NT_transact_set_user_quota);
outsize = call_nt_transact_set_user_quota(conn, inbuf, outbuf,
- length, bufsize,
- &setup, setup_count,
- &params, parameter_count,
- &data, data_count);
+ length, bufsize,
+ &setup, setup_count,
+ &params, total_parameter_count,
+ &data, total_data_count);
END_PROFILE_NESTED(NT_transact_set_user_quota);
break;
#endif /* HAVE_SYS_QUOTAS */
diff --git a/source3/smbd/posix_acls.c b/source3/smbd/posix_acls.c
index d775a82d2d..9773076a46 100644
--- a/source3/smbd/posix_acls.c
+++ b/source3/smbd/posix_acls.c
@@ -2165,7 +2165,7 @@ static size_t merge_default_aces( SEC_ACE *nt_ace_list, size_t num_aces)
the UNIX style get ACL.
****************************************************************************/
-size_t get_nt_acl(files_struct *fsp, SEC_DESC **ppdesc)
+size_t get_nt_acl(files_struct *fsp, uint32 security_info, SEC_DESC **ppdesc)
{
extern DOM_SID global_sid_Builtin_Administrators;
extern DOM_SID global_sid_Builtin_Users;
@@ -2241,177 +2241,184 @@ size_t get_nt_acl(files_struct *fsp, SEC_DESC **ppdesc)
create_file_sids(&sbuf, &owner_sid, &group_sid);
}
- /*
- * In the optimum case Creator Owner and Creator Group would be used for
- * the ACL_USER_OBJ and ACL_GROUP_OBJ entries, respectively, but this
- * would lead to usability problems under Windows: The Creator entries
- * are only available in browse lists of directories and not for files;
- * additionally the identity of the owning group couldn't be determined.
- * We therefore use those identities only for Default ACLs.
- */
-
- /* Create the canon_ace lists. */
- file_ace = canonicalise_acl( fsp, posix_acl, &sbuf, &owner_sid, &group_sid, SMB_ACL_TYPE_ACCESS );
+ if (security_info & DACL_SECURITY_INFORMATION) {
- /* We must have *some* ACLS. */
+ /*
+ * In the optimum case Creator Owner and Creator Group would be used for
+ * the ACL_USER_OBJ and ACL_GROUP_OBJ entries, respectively, but this
+ * would lead to usability problems under Windows: The Creator entries
+ * are only available in browse lists of directories and not for files;
+ * additionally the identity of the owning group couldn't be determined.
+ * We therefore use those identities only for Default ACLs.
+ */
- if (count_canon_ace_list(file_ace) == 0) {
- DEBUG(0,("get_nt_acl : No ACLs on file (%s) !\n", fsp->fsp_name ));
- return 0;
- }
+ /* Create the canon_ace lists. */
+ file_ace = canonicalise_acl( fsp, posix_acl, &sbuf, &owner_sid, &group_sid, SMB_ACL_TYPE_ACCESS );
- if (fsp->is_directory && dir_acl) {
- dir_ace = canonicalise_acl(fsp, dir_acl, &sbuf,
- &global_sid_Creator_Owner,
- &global_sid_Creator_Group, SMB_ACL_TYPE_DEFAULT );
- }
+ /* We must have *some* ACLS. */
+
+ if (count_canon_ace_list(file_ace) == 0) {
+ DEBUG(0,("get_nt_acl : No ACLs on file (%s) !\n", fsp->fsp_name ));
+ return 0;
+ }
- /*
- * Create the NT ACE list from the canonical ace lists.
- */
+ if (fsp->is_directory && dir_acl) {
+ dir_ace = canonicalise_acl(fsp, dir_acl, &sbuf,
+ &global_sid_Creator_Owner,
+ &global_sid_Creator_Group, SMB_ACL_TYPE_DEFAULT );
+ }
- {
- canon_ace *ace;
- int nt_acl_type;
- int i;
+ /*
+ * Create the NT ACE list from the canonical ace lists.
+ */
- if (nt4_compatible_acls() && dir_ace) {
- /*
- * NT 4 chokes if an ACL contains an INHERIT_ONLY entry
- * but no non-INHERIT_ONLY entry for one SID. So we only
- * remove entries from the Access ACL if the
- * corresponding Default ACL entries have also been
- * removed. ACEs for CREATOR-OWNER and CREATOR-GROUP
- * are exceptions. We can do nothing
- * intelligent if the Default ACL contains entries that
- * are not also contained in the Access ACL, so this
- * case will still fail under NT 4.
- */
+ {
+ canon_ace *ace;
+ int nt_acl_type;
+ int i;
- ace = canon_ace_entry_for(dir_ace, SMB_ACL_OTHER, NULL);
- if (ace && !ace->perms) {
- DLIST_REMOVE(dir_ace, ace);
- SAFE_FREE(ace);
+ if (nt4_compatible_acls() && dir_ace) {
+ /*
+ * NT 4 chokes if an ACL contains an INHERIT_ONLY entry
+ * but no non-INHERIT_ONLY entry for one SID. So we only
+ * remove entries from the Access ACL if the
+ * corresponding Default ACL entries have also been
+ * removed. ACEs for CREATOR-OWNER and CREATOR-GROUP
+ * are exceptions. We can do nothing
+ * intelligent if the Default ACL contains entries that
+ * are not also contained in the Access ACL, so this
+ * case will still fail under NT 4.
+ */
- ace = canon_ace_entry_for(file_ace, SMB_ACL_OTHER, NULL);
+ ace = canon_ace_entry_for(dir_ace, SMB_ACL_OTHER, NULL);
if (ace && !ace->perms) {
- DLIST_REMOVE(file_ace, ace);
+ DLIST_REMOVE(dir_ace, ace);
SAFE_FREE(ace);
+
+ ace = canon_ace_entry_for(file_ace, SMB_ACL_OTHER, NULL);
+ if (ace && !ace->perms) {
+ DLIST_REMOVE(file_ace, ace);
+ SAFE_FREE(ace);
+ }
}
- }
- /*
- * WinNT doesn't usually have Creator Group
- * in browse lists, so we send this entry to
- * WinNT even if it contains no relevant
- * permissions. Once we can add
- * Creator Group to browse lists we can
- * re-enable this.
- */
+ /*
+ * WinNT doesn't usually have Creator Group
+ * in browse lists, so we send this entry to
+ * WinNT even if it contains no relevant
+ * permissions. Once we can add
+ * Creator Group to browse lists we can
+ * re-enable this.
+ */
#if 0
- ace = canon_ace_entry_for(dir_ace, SMB_ACL_GROUP_OBJ, NULL);
- if (ace && !ace->perms) {
- DLIST_REMOVE(dir_ace, ace);
- SAFE_FREE(ace);
- }
+ ace = canon_ace_entry_for(dir_ace, SMB_ACL_GROUP_OBJ, NULL);
+ if (ace && !ace->perms) {
+ DLIST_REMOVE(dir_ace, ace);
+ SAFE_FREE(ace);
+ }
#endif
- ace = canon_ace_entry_for(file_ace, SMB_ACL_GROUP_OBJ, NULL);
- if (ace && !ace->perms) {
- DLIST_REMOVE(file_ace, ace);
- SAFE_FREE(ace);
+ ace = canon_ace_entry_for(file_ace, SMB_ACL_GROUP_OBJ, NULL);
+ if (ace && !ace->perms) {
+ DLIST_REMOVE(file_ace, ace);
+ SAFE_FREE(ace);
+ }
+ } else {
+
+ ace = canon_ace_entry_for(dir_ace, SMB_ACL_OTHER, NULL);
+ if (ace && !ace->perms) {
+ DLIST_REMOVE(dir_ace, ace);
+ SAFE_FREE(ace);
+ }
+ ace = canon_ace_entry_for(dir_ace, SMB_ACL_GROUP_OBJ, NULL);
+ if (ace && !ace->perms) {
+ DLIST_REMOVE(dir_ace, ace);
+ SAFE_FREE(ace);
+ }
}
- } else {
+
+ num_acls = count_canon_ace_list(file_ace);
+ num_dir_acls = count_canon_ace_list(dir_ace);
- ace = canon_ace_entry_for(dir_ace, SMB_ACL_OTHER, NULL);
- if (ace && !ace->perms) {
- DLIST_REMOVE(dir_ace, ace);
- SAFE_FREE(ace);
- }
- ace = canon_ace_entry_for(dir_ace, SMB_ACL_GROUP_OBJ, NULL);
- if (ace && !ace->perms) {
- DLIST_REMOVE(dir_ace, ace);
- SAFE_FREE(ace);
+ /* Allocate the ace list. */
+ if ((nt_ace_list = (SEC_ACE *)malloc((num_acls + num_profile_acls + num_dir_acls)* sizeof(SEC_ACE))) == NULL) {
+ DEBUG(0,("get_nt_acl: Unable to malloc space for nt_ace_list.\n"));
+ goto done;
}
- }
-
- num_acls = count_canon_ace_list(file_ace);
- num_dir_acls = count_canon_ace_list(dir_ace);
-
- /* Allocate the ace list. */
- if ((nt_ace_list = (SEC_ACE *)malloc((num_acls + num_profile_acls + num_dir_acls)* sizeof(SEC_ACE))) == NULL) {
- DEBUG(0,("get_nt_acl: Unable to malloc space for nt_ace_list.\n"));
- goto done;
- }
- memset(nt_ace_list, '\0', (num_acls + num_dir_acls) * sizeof(SEC_ACE) );
-
- /*
- * Create the NT ACE list from the canonical ace lists.
- */
-
- ace = file_ace;
-
- for (i = 0; i < num_acls; i++, ace = ace->next) {
- SEC_ACCESS acc;
+ memset(nt_ace_list, '\0', (num_acls + num_dir_acls) * sizeof(SEC_ACE) );
+
+ /*
+ * Create the NT ACE list from the canonical ace lists.
+ */
+
+ ace = file_ace;
- acc = map_canon_ace_perms(&nt_acl_type, &owner_sid, ace );
- init_sec_ace(&nt_ace_list[num_aces++], &ace->trustee, nt_acl_type, acc, 0);
- }
+ for (i = 0; i < num_acls; i++, ace = ace->next) {
+ SEC_ACCESS acc;
- /* The User must have access to a profile share - even if we can't map the SID. */
- if (lp_profile_acls(SNUM(fsp->conn))) {
- SEC_ACCESS acc;
+ acc = map_canon_ace_perms(&nt_acl_type, &owner_sid, ace );
+ init_sec_ace(&nt_ace_list[num_aces++], &ace->trustee, nt_acl_type, acc, 0);
+ }
- init_sec_access(&acc,FILE_GENERIC_ALL);
- init_sec_ace(&nt_ace_list[num_aces++], &global_sid_Builtin_Users, SEC_ACE_TYPE_ACCESS_ALLOWED, acc, 0);
- }
+ /* The User must have access to a profile share - even if we can't map the SID. */
+ if (lp_profile_acls(SNUM(fsp->conn))) {
+ SEC_ACCESS acc;
- ace = dir_ace;
+ init_sec_access(&acc,FILE_GENERIC_ALL);
+ init_sec_ace(&nt_ace_list[num_aces++], &global_sid_Builtin_Users, SEC_ACE_TYPE_ACCESS_ALLOWED, acc, 0);
+ }
- for (i = 0; i < num_dir_acls; i++, ace = ace->next) {
- SEC_ACCESS acc;
+ ace = dir_ace;
- acc = map_canon_ace_perms(&nt_acl_type, &owner_sid, ace );
- init_sec_ace(&nt_ace_list[num_aces++], &ace->trustee, nt_acl_type, acc,
- SEC_ACE_FLAG_OBJECT_INHERIT|SEC_ACE_FLAG_CONTAINER_INHERIT|SEC_ACE_FLAG_INHERIT_ONLY);
- }
+ for (i = 0; i < num_dir_acls; i++, ace = ace->next) {
+ SEC_ACCESS acc;
+
+ acc = map_canon_ace_perms(&nt_acl_type, &owner_sid, ace );
+ init_sec_ace(&nt_ace_list[num_aces++], &ace->trustee, nt_acl_type, acc,
+ SEC_ACE_FLAG_OBJECT_INHERIT|SEC_ACE_FLAG_CONTAINER_INHERIT|SEC_ACE_FLAG_INHERIT_ONLY);
+ }
- /* The User must have access to a profile share - even if we can't map the SID. */
- if (lp_profile_acls(SNUM(fsp->conn))) {
- SEC_ACCESS acc;
+ /* The User must have access to a profile share - even if we can't map the SID. */
+ if (lp_profile_acls(SNUM(fsp->conn))) {
+ SEC_ACCESS acc;
- init_sec_access(&acc,FILE_GENERIC_ALL);
- init_sec_ace(&nt_ace_list[num_aces++], &global_sid_Builtin_Users, SEC_ACE_TYPE_ACCESS_ALLOWED, acc,
- SEC_ACE_FLAG_OBJECT_INHERIT|SEC_ACE_FLAG_CONTAINER_INHERIT|
- SEC_ACE_FLAG_INHERIT_ONLY);
- }
-
- /*
- * Merge POSIX default ACLs and normal ACLs into one NT ACE.
- * Win2K needs this to get the inheritance correct when replacing ACLs
- * on a directory tree. Based on work by Jim @ IBM.
- */
+ init_sec_access(&acc,FILE_GENERIC_ALL);
+ init_sec_ace(&nt_ace_list[num_aces++], &global_sid_Builtin_Users, SEC_ACE_TYPE_ACCESS_ALLOWED, acc,
+ SEC_ACE_FLAG_OBJECT_INHERIT|SEC_ACE_FLAG_CONTAINER_INHERIT|
+ SEC_ACE_FLAG_INHERIT_ONLY);
+ }
- num_aces = merge_default_aces(nt_ace_list, num_aces);
+ /*
+ * Merge POSIX default ACLs and normal ACLs into one NT ACE.
+ * Win2K needs this to get the inheritance correct when replacing ACLs
+ * on a directory tree. Based on work by Jim @ IBM.
+ */
- /*
- * Sort to force deny entries to the front.
- */
+ num_aces = merge_default_aces(nt_ace_list, num_aces);
- if (num_aces)
- qsort( nt_ace_list, num_aces, sizeof(nt_ace_list[0]), QSORT_CAST nt_ace_comp);
- }
+ /*
+ * Sort to force deny entries to the front.
+ */
+
+ if (num_aces)
+ qsort( nt_ace_list, num_aces, sizeof(nt_ace_list[0]), QSORT_CAST nt_ace_comp);
+ }
- if (num_aces) {
- if((psa = make_sec_acl( main_loop_talloc_get(), ACL_REVISION, num_aces, nt_ace_list)) == NULL) {
- DEBUG(0,("get_nt_acl: Unable to malloc space for acl.\n"));
- goto done;
+ if (num_aces) {
+ if((psa = make_sec_acl( main_loop_talloc_get(), ACL_REVISION, num_aces, nt_ace_list)) == NULL) {
+ DEBUG(0,("get_nt_acl: Unable to malloc space for acl.\n"));
+ goto done;
+ }
}
- }
+ } /* security_info & DACL_SECURITY_INFORMATION */
- *ppdesc = make_standard_sec_desc( main_loop_talloc_get(), &owner_sid, &group_sid, psa, &sd_size);
+ *ppdesc = make_standard_sec_desc( main_loop_talloc_get(),
+ (security_info & OWNER_SECURITY_INFORMATION) ? &owner_sid : NULL,
+ (security_info & GROUP_SECURITY_INFORMATION) ? &group_sid : NULL,
+ psa,
+ &sd_size);
if(!*ppdesc) {
DEBUG(0,("get_nt_acl: Unable to malloc space for security descriptor.\n"));
diff --git a/source3/smbd/vfs-wrap.c b/source3/smbd/vfs-wrap.c
index 2160bca9f7..f923d22aea 100644
--- a/source3/smbd/vfs-wrap.c
+++ b/source3/smbd/vfs-wrap.c
@@ -576,22 +576,22 @@ char *vfswrap_realpath(vfs_handle_struct *handle, connection_struct *conn, const
return result;
}
-size_t vfswrap_fget_nt_acl(vfs_handle_struct *handle, files_struct *fsp, int fd, SEC_DESC **ppdesc)
+size_t vfswrap_fget_nt_acl(vfs_handle_struct *handle, files_struct *fsp, int fd, uint32 security_info, SEC_DESC **ppdesc)
{
size_t result;
START_PROFILE(fget_nt_acl);
- result = get_nt_acl(fsp, ppdesc);
+ result = get_nt_acl(fsp, security_info, ppdesc);
END_PROFILE(fget_nt_acl);
return result;
}
-size_t vfswrap_get_nt_acl(vfs_handle_struct *handle, files_struct *fsp, const char *name, SEC_DESC **ppdesc)
+size_t vfswrap_get_nt_acl(vfs_handle_struct *handle, files_struct *fsp, const char *name, uint32 security_info, SEC_DESC **ppdesc)
{
size_t result;
START_PROFILE(get_nt_acl);
- result = get_nt_acl(fsp, ppdesc);
+ result = get_nt_acl(fsp, security_info, ppdesc);
END_PROFILE(get_nt_acl);
return result;
}