diff options
author | Jeremy Allison <jra@samba.org> | 2001-01-22 18:10:20 +0000 |
---|---|---|
committer | Jeremy Allison <jra@samba.org> | 2001-01-22 18:10:20 +0000 |
commit | ea05e9be70a54259bc0321d57e4aa7b3c6423d52 (patch) | |
tree | bb20c20299e69f37ae73b094b0844edecf26c154 | |
parent | c7a6dc40fac0c6b5e979c470996d4a2bdeb587c5 (diff) | |
download | samba-ea05e9be70a54259bc0321d57e4aa7b3c6423d52.tar.gz samba-ea05e9be70a54259bc0321d57e4aa7b3c6423d52.tar.xz samba-ea05e9be70a54259bc0321d57e4aa7b3c6423d52.zip |
Fixes to sync up with appliance-head. Fix from Kenichi Okuyama for a typo
in loadparm.c Removed extra \n in configure.
Jeremy.
-rwxr-xr-x | source/configure | 25 | ||||
-rw-r--r-- | source/configure.in | 2 | ||||
-rw-r--r-- | source/lib/util_seaccess.c | 147 | ||||
-rw-r--r-- | source/param/loadparm.c | 2 | ||||
-rw-r--r-- | source/printing/nt_printing.c | 32 | ||||
-rw-r--r-- | source/printing/printing.c | 79 | ||||
-rw-r--r-- | source/rpc_server/srv_spoolss_nt.c | 4 | ||||
-rw-r--r-- | source/smbd/lanman.c | 7 |
8 files changed, 216 insertions, 82 deletions
diff --git a/source/configure b/source/configure index ebe9bb19c48..b06bc7d668c 100755 --- a/source/configure +++ b/source/configure @@ -11422,9 +11422,10 @@ fi # If we don't have all of these then disable large # file support. # -echo "checking if large file support can be enabled" +echo $ac_n "checking checking if large file support can be enabled""... $ac_c" 1>&6 +echo "configure:11427: checking checking if large file support can be enabled" >&5 cat > conftest.$ac_ext <<EOF -#line 11428 "configure" +#line 11429 "configure" #include "confdefs.h" #if defined(HAVE_LONGLONG) && (defined(HAVE_OFF64_T) || (defined(SIZEOF_OFF_T) && (SIZEOF_OFF_T == 8))) @@ -11437,7 +11438,7 @@ int main() { int i ; return 0; } EOF -if { (eval echo configure:11441: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:11442: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* samba_cv_HAVE_EXPLICIT_LARGEFILE_SUPPORT=yes else @@ -11504,7 +11505,7 @@ fi # check for POSIX ACL support echo $ac_n "checking whether to support POSIX ACLs""... $ac_c" 1>&6 -echo "configure:11508: checking whether to support POSIX ACLs" >&5 +echo "configure:11509: checking whether to support POSIX ACLs" >&5 # Check whether --with-posix-acls or --without-posix-acls was given. if test "${with_posix_acls+set}" = set; then withval="$with_posix_acls" @@ -11512,7 +11513,7 @@ if test "${with_posix_acls+set}" = set; then yes) echo $ac_n "checking for acl_get_file in -lacl""... $ac_c" 1>&6 -echo "configure:11516: checking for acl_get_file in -lacl" >&5 +echo "configure:11517: checking for acl_get_file in -lacl" >&5 ac_lib_var=`echo acl'_'acl_get_file | sed 'y%./+-%__p_%'` if eval "test \"`echo '$''{'ac_cv_lib_$ac_lib_var'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 @@ -11520,7 +11521,7 @@ else ac_save_LIBS="$LIBS" LIBS="-lacl $LIBS" cat > conftest.$ac_ext <<EOF -#line 11524 "configure" +#line 11525 "configure" #include "confdefs.h" /* Override any gcc2 internal prototype to avoid an error. */ /* We use char because int might match the return type of a gcc2 @@ -11531,7 +11532,7 @@ int main() { acl_get_file() ; return 0; } EOF -if { (eval echo configure:11535: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then +if { (eval echo configure:11536: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then rm -rf conftest* eval "ac_cv_lib_$ac_lib_var=yes" else @@ -11559,13 +11560,13 @@ else fi echo $ac_n "checking for POSIX ACL support""... $ac_c" 1>&6 -echo "configure:11563: checking for POSIX ACL support" >&5 +echo "configure:11564: checking for POSIX ACL support" >&5 if eval "test \"`echo '$''{'samba_cv_HAVE_POSIX_ACLS'+set}'`\" = set"; then echo $ac_n "(cached) $ac_c" 1>&6 else cat > conftest.$ac_ext <<EOF -#line 11569 "configure" +#line 11570 "configure" #include "confdefs.h" #include <sys/types.h> #include <sys/acl.h> @@ -11573,7 +11574,7 @@ int main() { acl_t acl; int entry_id; acl_entry_t *entry_p; return acl_get_entry( acl, entry_id, entry_p); ; return 0; } EOF -if { (eval echo configure:11577: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then +if { (eval echo configure:11578: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then rm -rf conftest* samba_cv_HAVE_POSIX_ACLS=yes else @@ -11612,11 +11613,11 @@ if test "$cross_compiling" = yes; then : else cat > conftest.$ac_ext <<EOF -#line 11616 "configure" +#line 11617 "configure" #include "confdefs.h" #include "${srcdir-.}/tests/summary.c" EOF -if { (eval echo configure:11620: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null +if { (eval echo configure:11621: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext} && (./conftest; exit) 2>/dev/null then echo "configure OK"; else diff --git a/source/configure.in b/source/configure.in index a40c9c7de9f..34c5da78cc0 100644 --- a/source/configure.in +++ b/source/configure.in @@ -1905,7 +1905,7 @@ fi # If we don't have all of these then disable large # file support. # -echo "checking if large file support can be enabled" +AC_MSG_CHECKING(checking if large file support can be enabled) AC_TRY_COMPILE([ #if defined(HAVE_LONGLONG) && (defined(HAVE_OFF64_T) || (defined(SIZEOF_OFF_T) && (SIZEOF_OFF_T == 8))) #include <sys/types.h> diff --git a/source/lib/util_seaccess.c b/source/lib/util_seaccess.c index 68f900b34db..6cfcd065aad 100644 --- a/source/lib/util_seaccess.c +++ b/source/lib/util_seaccess.c @@ -51,32 +51,6 @@ static uint32 check_ace(SEC_ACE *ace, NT_USER_TOKEN *token, uint32 acc_desired, { uint32 mask = ace->info.mask; -#if 0 - - /* I think there is some aspect of inheritable ACEs that we don't - understand. A 'Manage Documents' permission has the following - ACE entries (after generic mapping has been applied): - - S-1-5-21-1067277791-1719175008-3000797951-1033 0 9 0x000f000c - S-1-5-21-1067277791-1719175008-3000797951-1033 0 2 0x00020000 - - Now a user wanting to print calls se_access_check() with desired - access PRINTER_ACCESS_USE (0x00000008). This is only allowed if - the inherit only ACE, flags & SEC_ACE_FLAG_INHERIT_ONLY (0x8) is - checked. A similar argument is used to explain how a user with - 'Full Control' permission can print. - - Having both the flags SEC_ACE_FLAG_INHERIT_ONLY and - SEC_ACE_FLAG_OBJECT_INHERIT set in an ACE doesn't seem to make - sense. According to the MSDN, an inherit only ACE "indicates an - [...] ACE which does not control access to the object to which - it is attached" and an object inherit ACE for "non-container - child objects [they] inherit the ACE as an effective ACE". - These two flags don't seem to make sense when combined. Does - the object inherit override the inherit only flag? We are also - talking about access to a printer object, not a printer job so - inheritance shouldn't even be involved. -tpot */ - /* * Inherit only is ignored. */ @@ -85,8 +59,6 @@ static uint32 check_ace(SEC_ACE *ace, NT_USER_TOKEN *token, uint32 acc_desired, return acc_desired; } -#endif - /* * If this ACE has no SID in common with the token, * ignore it as it cannot be used to make an access @@ -328,3 +300,122 @@ BOOL se_access_check(SEC_DESC *sd, struct current_user *user, DEBUG(5,("se_access_check: access (%x) denied.\n", (unsigned int)acc_desired )); return False; } + +/* Create a child security descriptor using another security descriptor as + the parent container. This child object can either be a container or + non-container object. */ + +SEC_DESC_BUF *se_create_child_secdesc(SEC_DESC *parent_ctr, + BOOL child_container) +{ + SEC_DESC_BUF *sdb; + SEC_DESC *sd; + SEC_ACL *new_dacl, *acl; + SEC_ACE *new_ace_list = NULL; + int new_ace_list_ndx = 0, i; + size_t size; + + /* Currently we only process the dacl when creating the child. The + sacl should also be processed but this is left out as sacls are + not implemented in Samba at the moment.*/ + + acl = parent_ctr->dacl; + + if (!(new_ace_list = malloc(sizeof(SEC_ACE) * acl->num_aces))) + return NULL; + + for (i = 0; acl && i < acl->num_aces; i++) { + SEC_ACE *ace = &acl->ace[i]; + SEC_ACE *new_ace = &new_ace_list[new_ace_list_ndx]; + uint8 new_flags = 0; + BOOL inherit = False; + fstring sid_str; + + /* The OBJECT_INHERIT_ACE flag causes the ACE to be + inherited by non-container children objects. Container + children objects will inherit it as an INHERIT_ONLY + ACE. */ + + if (ace->flags & SEC_ACE_FLAG_OBJECT_INHERIT) { + + if (!child_container) { + new_flags |= SEC_ACE_FLAG_OBJECT_INHERIT; + } else { + new_flags |= SEC_ACE_FLAG_INHERIT_ONLY; + } + + inherit = True; + } + + /* The CONAINER_INHERIT_ACE flag means all child container + objects will inherit and use the ACE. */ + + if (ace->flags & SEC_ACE_FLAG_CONTAINER_INHERIT) { + if (!child_container) { + inherit = False; + } else { + new_flags |= SEC_ACE_FLAG_CONTAINER_INHERIT; + } + } + + /* The INHERIT_ONLY_ACE is not used by the se_access_check() + function for the parent container, but is inherited by + all child objects as a normal ACE. */ + + if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY) { + /* Move along, nothing to see here */ + } + + /* The SEC_ACE_FLAG_NO_PROPAGATE_INHERIT flag means the ACE + is inherited by child objects but not grandchildren + objects. We clear the object inherit and container + inherit flags in the inherited ACE. */ + + if (ace->flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT) { + new_flags &= ~(SEC_ACE_FLAG_OBJECT_INHERIT | + SEC_ACE_FLAG_CONTAINER_INHERIT); + } + + /* Add ACE to ACE list */ + + if (!inherit) + continue; + + init_sec_access(&new_ace->info, ace->info.mask); + init_sec_ace(new_ace, &ace->sid, ace->type, + new_ace->info, new_flags); + + sid_to_string(sid_str, &ace->sid); + + DEBUG(5, ("se_create_child_secdesc(): %s:%d/0x%02x/0x%08x " + " inherited as %s:%d/0x%02x/0x%08x\n", sid_str, + ace->type, ace->flags, ace->info.mask, + sid_str, new_ace->type, new_ace->flags, + new_ace->info.mask)); + + new_ace_list_ndx++; + } + + /* Create child security descriptor to return */ + + new_dacl = make_sec_acl(ACL_REVISION, new_ace_list_ndx, new_ace_list); + safe_free(new_ace_list); + + /* Use the existing user and group sids. I don't think this is + correct. Perhaps the user and group should be passed in as + parameters by the caller? */ + + sd = make_sec_desc(SEC_DESC_REVISION, + parent_ctr->owner_sid, + parent_ctr->grp_sid, + parent_ctr->sacl, + new_dacl, &size); + + free_sec_acl(&new_dacl); + + sdb = make_sec_desc_buf(size, sd); + + free_sec_desc(&sd); + + return sdb; +} diff --git a/source/param/loadparm.c b/source/param/loadparm.c index b4f33bd5a7f..a418b0ba765 100644 --- a/source/param/loadparm.c +++ b/source/param/loadparm.c @@ -1514,7 +1514,7 @@ FN_GLOBAL_BOOL(lp_kernel_oplocks, &Globals.bKernelOplocks) FN_GLOBAL_INTEGER(lp_os_level, &Globals.os_level) FN_GLOBAL_INTEGER(lp_max_ttl, &Globals.max_ttl) FN_GLOBAL_INTEGER(lp_max_wins_ttl, &Globals.max_wins_ttl) -FN_GLOBAL_INTEGER(lp_min_wins_ttl, &Globals.max_wins_ttl) +FN_GLOBAL_INTEGER(lp_min_wins_ttl, &Globals.min_wins_ttl) FN_GLOBAL_INTEGER(lp_max_log_size, &Globals.max_log_size) FN_GLOBAL_INTEGER(lp_max_open_files, &Globals.max_open_files) FN_GLOBAL_INTEGER(lp_maxxmit, &Globals.max_xmit) diff --git a/source/printing/nt_printing.c b/source/printing/nt_printing.c index 7b84f951614..9eb7dc12ed3 100644 --- a/source/printing/nt_printing.c +++ b/source/printing/nt_printing.c @@ -3003,9 +3003,9 @@ void map_printer_permissions(SEC_DESC *sd) } /**************************************************************************** - Check a user has permissions to perform the given operation. We use some - constants defined in include/rpc_spoolss.h that look relevant to check - the various actions we perform when checking printer access. + Check a user has permissions to perform the given operation. We use the + permission constants defined in include/rpc_spoolss.h to check the various + actions we perform when checking printer access. PRINTER_ACCESS_ADMINISTER: print_queue_pause, print_queue_resume, update_printer_sec, @@ -3015,7 +3015,7 @@ void map_printer_permissions(SEC_DESC *sd) PRINTER_ACCESS_USE: print_job_start - PRINTER_ACCESS_ADMINISTER (should really be JOB_ACCESS_ADMINISTER): + JOB_ACCESS_ADMINISTER: print_job_delete, print_job_pause, print_job_resume, print_queue_purge @@ -3051,14 +3051,34 @@ BOOL print_access_check(struct current_user *user, int snum, int access_type) /* Get printer security descriptor */ nt_printing_getsec(pname, &secdesc); + + if (access_type == JOB_ACCESS_ADMINISTER) { + SEC_DESC_BUF *parent_secdesc = secdesc; + + /* Create a child security descriptor to check permissions + against. This is because print jobs are child objects + objects of a printer. */ + + secdesc = se_create_child_secdesc(parent_secdesc->sec, False); + + free_sec_desc_buf(&parent_secdesc); + + /* Now this is the bit that really confuses me. The access + type needs to be changed from JOB_ACCESS_ADMINISTER to + PRINTER_ACCESS_ADMINISTER for this to work. Something + to do with the child (job) object becoming like a + printer?? -tpot */ + + access_type = PRINTER_ACCESS_ADMINISTER; + } + + /* Check access */ map_printer_permissions(secdesc->sec); result = se_access_check(secdesc->sec, user, access_type, &access_granted, &status); - /* Check access */ - DEBUG(4, ("access check was %s\n", result ? "SUCCESS" : "FAILURE")); /* Free mallocated memory */ diff --git a/source/printing/printing.c b/source/printing/printing.c index 3ce58b5b78b..3a676d29b66 100644 --- a/source/printing/printing.c +++ b/source/printing/printing.c @@ -534,6 +534,14 @@ static BOOL print_job_delete1(int jobid) snum = print_job_snum(jobid); + /* Hrm - we need to be able to cope with deleting a job before it + has reached the spooler. */ + + if (pjob->sysjob == -1) { + DEBUG(5, ("attempt to delete job %d not seen by lpr\n", + jobid)); + } + if (pjob->spooled && pjob->sysjob != -1) { /* need to delete the spooled entry */ fstring jobstr; @@ -580,7 +588,7 @@ BOOL print_job_delete(struct current_user *user, int jobid, int *errcode) owns their job. */ if (!owner && - !print_access_check(user, snum, PRINTER_ACCESS_ADMINISTER)) { + !print_access_check(user, snum, JOB_ACCESS_ADMINISTER)) { DEBUG(3, ("delete denied by security descriptor\n")); *errcode = ERROR_ACCESS_DENIED; return False; @@ -622,7 +630,7 @@ BOOL print_job_pause(struct current_user *user, int jobid, int *errcode) owner = is_owner(user, jobid); if (!owner && - !print_access_check(user, snum, PRINTER_ACCESS_ADMINISTER)) { + !print_access_check(user, snum, JOB_ACCESS_ADMINISTER)) { DEBUG(3, ("pause denied by security descriptor\n")); *errcode = ERROR_ACCESS_DENIED; return False; @@ -673,7 +681,7 @@ BOOL print_job_resume(struct current_user *user, int jobid, int *errcode) owner = is_owner(user, jobid); if (!is_owner(user, jobid) && - !print_access_check(user, snum, PRINTER_ACCESS_ADMINISTER)) { + !print_access_check(user, snum, JOB_ACCESS_ADMINISTER)) { DEBUG(3, ("resume denied by security descriptor\n")); *errcode = ERROR_ACCESS_DENIED; return False; @@ -906,11 +914,11 @@ int print_job_start(struct current_user *user, int snum, char *jobname) BOOL print_job_end(int jobid) { struct printjob *pjob = print_job_find(jobid); - int snum; + int snum, ret; SMB_STRUCT_STAT sbuf; pstring current_directory; pstring print_directory; - char *wd, *p, *printer_name; + char *wd, *p; pstring jobname; if (!pjob) @@ -921,12 +929,17 @@ BOOL print_job_end(int jobid) snum = print_job_snum(jobid); - if (sys_fstat(pjob->fd, &sbuf) == 0) + if (sys_fstat(pjob->fd, &sbuf) == 0) { pjob->size = sbuf.st_size; - - close(pjob->fd); - pjob->fd = -1; - + close(pjob->fd); + pjob->fd = -1; + } else { + /* Couldn't stat the job file, so something has gone wrong. Cleanup */ + unlink(pjob->filename); + tdb_delete(tdb, print_key(jobid)); + return False; + } + if (pjob->size == 0) { /* don't bother spooling empty files */ unlink(pjob->filename); @@ -953,7 +966,7 @@ BOOL print_job_end(int jobid) pstring_sub(jobname, "'", "_"); /* send it to the system spooler */ - print_run_command(snum, + ret = print_run_command(snum, lp_printcommand(snum), NULL, "%s", p, "%J", jobname, @@ -962,19 +975,23 @@ BOOL print_job_end(int jobid) chdir(wd); - pjob->spooled = True; - print_job_store(jobid, pjob); - - /* force update the database */ - print_cache_flush(snum); - - /* Send a printer notify message */ - - printer_name = PRINTERNAME(snum); - - message_send_all(conn_tdb_ctx(),MSG_PRINTER_NOTIFY, printer_name, strlen(printer_name) + 1, False); - - return True; + if (ret == 0) { + /* The print job has been sucessfully handed over to the back-end */ + + pjob->spooled = True; + print_job_store(jobid, pjob); + + /* make sure the database is up to date */ + if (print_cache_expired(snum)) print_queue_update(snum); + + return True; + } else { + /* The print job was not succesfully started. Cleanup */ + /* Still need to add proper error return propagation! 010122:JRR */ + unlink(pjob->filename); + tdb_delete(tdb, print_key(jobid)); + return False; + } } /* utility fn to enumerate the print queue */ @@ -1186,8 +1203,8 @@ BOOL print_queue_resume(struct current_user *user, int snum, int *errcode) return False; } - /* force update the database */ - print_cache_flush(snum); + /* make sure the database is up to date */ + if (print_cache_expired(snum)) print_queue_update(snum); /* Send a printer notify message */ @@ -1207,16 +1224,20 @@ BOOL print_queue_purge(struct current_user *user, int snum, int *errcode) print_status_struct status; char *printer_name; int njobs, i; + BOOL can_job_admin; + can_job_admin = print_access_check(user, snum, JOB_ACCESS_ADMINISTER); njobs = print_queue_status(snum, &queue, &status); - if (print_access_check(user, snum, PRINTER_ACCESS_ADMINISTER)) { - for (i=0;i<njobs;i++) { + for (i=0;i<njobs;i++) { + BOOL owner = is_owner(user, queue[i].job); + + if (owner || can_job_admin) { print_job_delete1(queue[i].job); } } - print_cache_flush(snum); + print_queue_update(snum); safe_free(queue); /* Send a printer notify message */ diff --git a/source/rpc_server/srv_spoolss_nt.c b/source/rpc_server/srv_spoolss_nt.c index 5b92a51189f..d838d08c3cd 100644 --- a/source/rpc_server/srv_spoolss_nt.c +++ b/source/rpc_server/srv_spoolss_nt.c @@ -5736,8 +5736,8 @@ uint32 _spoolss_deleteprinterdata( POLICY_HND *handle, const UNISTR2 *value) return ERROR_INVALID_HANDLE; if (!print_access_check(NULL, snum, PRINTER_ACCESS_ADMINISTER)) { - DEBUG(3, ("_spoolss_deleteprinterdata: security descriptor change denied by existing " - "security descriptor\n")); + DEBUG(3, ("_spoolss_deleteprinterdata: printer properties " + "change denied by existing security descriptor\n")); return ERROR_ACCESS_DENIED; } diff --git a/source/smbd/lanman.c b/source/smbd/lanman.c index 26cb94ee53b..0899a049eb5 100644 --- a/source/smbd/lanman.c +++ b/source/smbd/lanman.c @@ -1945,6 +1945,7 @@ static BOOL api_WPrintQueueCtrl(connection_struct *conn,uint16 vuid, char *param char *QueueName = skip_string(str2,1); int errcode = NERR_notsupported; int snum; + extern struct current_user current_user; /* check it's a supported varient */ if (!(strcsequal(str1,"z") && strcsequal(str2,""))) @@ -1963,13 +1964,13 @@ static BOOL api_WPrintQueueCtrl(connection_struct *conn,uint16 vuid, char *param switch (function) { case 74: /* Pause queue */ - if (print_queue_pause(NULL, snum, &errcode)) errcode = NERR_Success; + if (print_queue_pause(¤t_user, snum, &errcode)) errcode = NERR_Success; break; case 75: /* Resume queue */ - if (print_queue_resume(NULL, snum, &errcode)) errcode = NERR_Success; + if (print_queue_resume(¤t_user, snum, &errcode)) errcode = NERR_Success; break; case 103: /* Purge */ - if (print_queue_purge(NULL, snum, &errcode)) errcode = NERR_Success; + if (print_queue_purge(¤t_user, snum, &errcode)) errcode = NERR_Success; break; } |