[SCM] Samba Shared Repository - branch v4-17-test updated

Jule Anger janger at samba.org
Fri Apr 28 15:58:01 UTC 2023


The branch, v4-17-test has been updated
       via  b026bbe24c1 s3:lib: Do not try to match '.' and '..' directories in is_in_path()
       via  c13b5b7dc89 s3:tests: Add test that veto files works for hidden files
       via  647c7c75f8f s3:tests: Create a temporary directory for test_veto_files.sh
       via  65168f33f95 libcli/security: rewrite calculate_inherited_from_parent()
      from  f53ef993ffc shadow_copy2: Fix stream open for streams_depot paths

https://git.samba.org/?p=samba.git;a=shortlog;h=v4-17-test


- Log -----------------------------------------------------------------
commit b026bbe24c12dcbfb716c7be26df183d339eac8b
Author: Andreas Schneider <asn at samba.org>
Date:   Wed Apr 19 16:23:10 2023 +0200

    s3:lib: Do not try to match '.' and '..' directories in is_in_path()
    
    This fixes setting veto files to '.*' to not list hidden files and
    directories starting with a dot.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15360
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>
    (cherry picked from commit 9eb44306623fc4897b373b04763e475f696ab92d)
    
    Autobuild-User(v4-17-test): Jule Anger <janger at samba.org>
    Autobuild-Date(v4-17-test): Fri Apr 28 15:57:35 UTC 2023 on sn-devel-184

commit c13b5b7dc89039cb4ee6a74b766fe944ce311d67
Author: Andreas Schneider <asn at samba.org>
Date:   Wed Apr 19 15:35:47 2023 +0200

    s3:tests: Add test that veto files works for hidden files
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15360
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>
    (cherry picked from commit a2acbd3f3cff8d1cac63acdead4b7be14a7092b2)

commit 647c7c75f8f24e1f33047697b55fc79f35dfb134
Author: Andreas Schneider <asn at samba.org>
Date:   Wed Apr 19 20:45:52 2023 +0200

    s3:tests: Create a temporary directory for test_veto_files.sh
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15360
    
    Signed-off-by: Andreas Schneider <asn at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>
    (cherry picked from commit b5a66840e3057cbff85fe6cd231310c4a9cfb34b)

commit 65168f33f95906b2c9fb38465c8ab2e799d3942d
Author: Stefan Metzmacher <metze at samba.org>
Date:   Sat Mar 18 01:17:04 2023 +0100

    libcli/security: rewrite calculate_inherited_from_parent()
    
    This allows us to pass the new tests we just added.
    
    BUG: https://bugzilla.samba.org/show_bug.cgi?id=15338
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Andrew Bartlett <abartlet at samba.org>
    (cherry picked from commit bb09c06d6d58a04e1d270a9f99d1179cfa9acbda)

-----------------------------------------------------------------------

Summary of changes:
 libcli/security/create_descriptor.c     | 247 +++++++++++++++++++++++++-------
 selftest/target/Samba3.pm               |   4 +
 source3/lib/util.c                      |   5 +
 source3/script/tests/test_veto_files.sh |  35 ++++-
 4 files changed, 234 insertions(+), 57 deletions(-)


Changeset truncated at 500 lines:

diff --git a/libcli/security/create_descriptor.c b/libcli/security/create_descriptor.c
index ef60d847033..947d6c19d58 100644
--- a/libcli/security/create_descriptor.c
+++ b/libcli/security/create_descriptor.c
@@ -78,7 +78,7 @@ uint32_t map_generic_rights_ds(uint32_t access_mask)
 
 /* Not sure what this has to be,
 * and it does not seem to have any influence */
-static bool object_in_list(struct GUID *object_list, struct GUID *object)
+static bool object_in_list(const struct GUID *object_list, const struct GUID *object)
 {
 	size_t i;
 
@@ -107,7 +107,7 @@ static bool object_in_list(struct GUID *object_list, struct GUID *object)
 /* returns true if the ACE gontains generic information
  * that needs to be processed additionally */
  
-static bool desc_ace_has_generic(struct security_ace *ace)
+static bool desc_ace_has_generic(const struct security_ace *ace)
 {
 	if (ace->access_mask & SEC_GENERIC_ALL || ace->access_mask & SEC_GENERIC_READ ||
 	    ace->access_mask & SEC_GENERIC_WRITE || ace->access_mask & SEC_GENERIC_EXECUTE) {
@@ -155,12 +155,114 @@ static struct security_acl *calculate_inherited_from_parent(TALLOC_CTX *mem_ctx,
 	}
 
 	for (i=0; i < acl->num_aces; i++) {
-		struct security_ace *ace = &acl->aces[i];
-		if ((ace->flags & SEC_ACE_FLAG_CONTAINER_INHERIT) ||
-		    (ace->flags & SEC_ACE_FLAG_OBJECT_INHERIT)) {
-			struct GUID inherited_object = GUID_zero();
+		const struct security_ace *ace = &acl->aces[i];
+		const struct GUID *inherited_object = NULL;
+		const struct GUID *inherited_property = NULL;
+		struct security_ace *tmp_ace = NULL;
+		bool applies = false;
+		bool inherited_only = false;
+		bool expand_ace = false;
+		bool expand_only = false;
+
+		if (is_container && (ace->flags & SEC_ACE_FLAG_CONTAINER_INHERIT)) {
+			applies = true;
+		} else if (!is_container && (ace->flags & SEC_ACE_FLAG_OBJECT_INHERIT)) {
+			applies = true;
+		}
+
+		if (!applies) {
+			/*
+			 * If the ace doesn't apply to the
+			 * current node, we should only keep
+			 * it as SEC_ACE_FLAG_OBJECT_INHERIT
+			 * on a container. We'll add
+			 * SEC_ACE_FLAG_INHERITED_ACE
+			 * and SEC_ACE_FLAG_INHERIT_ONLY below.
+			 *
+			 * Otherwise we should completely ignore it.
+			 */
+			if (!(ace->flags & SEC_ACE_FLAG_OBJECT_INHERIT)) {
+				continue;
+			}
+		}
+
+		switch (ace->type) {
+		case SEC_ACE_TYPE_ACCESS_ALLOWED:
+		case SEC_ACE_TYPE_ACCESS_DENIED:
+		case SEC_ACE_TYPE_SYSTEM_AUDIT:
+		case SEC_ACE_TYPE_SYSTEM_ALARM:
+		case SEC_ACE_TYPE_ALLOWED_COMPOUND:
+			break;
+
+		case SEC_ACE_TYPE_ACCESS_ALLOWED_OBJECT:
+		case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
+		case SEC_ACE_TYPE_SYSTEM_ALARM_OBJECT:
+		case SEC_ACE_TYPE_SYSTEM_AUDIT_OBJECT:
+			if (ace->object.object.flags & SEC_ACE_OBJECT_TYPE_PRESENT) {
+				inherited_property = &ace->object.object.type.type;
+			}
+			if (ace->object.object.flags & SEC_ACE_INHERITED_OBJECT_TYPE_PRESENT) {
+				inherited_object = &ace->object.object.inherited_type.inherited_type;
+			}
+
+			if (inherited_object != NULL && !object_in_list(object_list, inherited_object)) {
+				/*
+				 * An explicit object class schemaId is given,
+				 * but doesn't belong to the current object.
+				 */
+				applies = false;
+			}
 
-			tmp_acl->aces = talloc_realloc(tmp_acl, tmp_acl->aces,
+			break;
+		}
+
+		if (ace->flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT) {
+			if (!applies) {
+				/*
+				 * If the ACE doesn't apply to
+				 * the current object, we should
+				 * ignore it as it should not be
+				 * inherited any further
+				 */
+				continue;
+			}
+			/*
+			 * We should only keep the expanded version
+			 * of the ACE on the current object.
+			 */
+			expand_ace = true;
+			expand_only = true;
+		} else if (applies) {
+			/*
+			 * We check if should also add
+			 * the expanded version of the ACE
+			 * in addition, in case we should
+			 * expand generic access bits or
+			 * special sids.
+			 *
+			 * In that case we need to
+			 * keep the original ACE with
+			 * SEC_ACE_FLAG_INHERIT_ONLY.
+			 */
+			expand_ace = desc_ace_has_generic(ace);
+			if (expand_ace) {
+				inherited_only = true;
+			}
+		} else {
+			/*
+			 * If the ACE doesn't apply
+			 * to the current object,
+			 * we need to keep it with
+			 * SEC_ACE_FLAG_INHERIT_ONLY
+			 * in order to apply them to
+			 * grandchildren
+			 */
+			inherited_only = true;
+		}
+
+		if (expand_ace) {
+			tmp_acl->aces = talloc_realloc(tmp_acl,
+						       tmp_acl->aces,
 						       struct security_ace,
 						       tmp_acl->num_aces+1);
 			if (tmp_acl->aces == NULL) {
@@ -168,61 +270,96 @@ static struct security_acl *calculate_inherited_from_parent(TALLOC_CTX *mem_ctx,
 				return NULL;
 			}
 
-			tmp_acl->aces[tmp_acl->num_aces] = *ace;
-			tmp_acl->aces[tmp_acl->num_aces].flags |= SEC_ACE_FLAG_INHERITED_ACE;
-			/* remove IO flag from the child's ace */
-			if (ace->flags & SEC_ACE_FLAG_INHERIT_ONLY &&
-			    !desc_ace_has_generic(ace)) {
-				tmp_acl->aces[tmp_acl->num_aces].flags &= ~SEC_ACE_FLAG_INHERIT_ONLY;
-			}
+			tmp_ace = &tmp_acl->aces[tmp_acl->num_aces];
+			tmp_acl->num_aces++;
 
-			if (is_container && (ace->flags & SEC_ACE_FLAG_OBJECT_INHERIT))
-			    tmp_acl->aces[tmp_acl->num_aces].flags |= SEC_ACE_FLAG_INHERIT_ONLY;
-
-			switch (ace->type) {
-			case SEC_ACE_TYPE_ACCESS_ALLOWED:
-			case SEC_ACE_TYPE_ACCESS_DENIED:
-			case SEC_ACE_TYPE_SYSTEM_AUDIT:
-			case SEC_ACE_TYPE_SYSTEM_ALARM:
-			case SEC_ACE_TYPE_ALLOWED_COMPOUND:
-				break;
-
-			case SEC_ACE_TYPE_ACCESS_ALLOWED_OBJECT:
-			case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
-			case SEC_ACE_TYPE_SYSTEM_ALARM_OBJECT:
-			case SEC_ACE_TYPE_SYSTEM_AUDIT_OBJECT:
-				if (ace->object.object.flags & SEC_ACE_INHERITED_OBJECT_TYPE_PRESENT) {
-					inherited_object = ace->object.object.inherited_type.inherited_type;
-				}
+			*tmp_ace = *ace;
+
+			/*
+			 * Expand generic access bits as well as special
+			 * sids.
+			 */
+			desc_expand_generic(tmp_ace, owner, group);
+
+			/*
+			 * Expanded ACEs are marked as inherited,
+			 * but never inherited any further to
+			 * grandchildren.
+			 */
+			tmp_ace->flags |= SEC_ACE_FLAG_INHERITED_ACE;
+			tmp_ace->flags &= ~SEC_ACE_FLAG_CONTAINER_INHERIT;
+			tmp_ace->flags &= ~SEC_ACE_FLAG_OBJECT_INHERIT;
+			tmp_ace->flags &= ~SEC_ACE_FLAG_NO_PROPAGATE_INHERIT;
+
+			/*
+			 * Expanded ACEs never have an explicit
+			 * object class schemaId, so clear it
+			 * if present.
+			 */
+			if (inherited_object != NULL) {
+				tmp_ace->object.object.flags &= ~SEC_ACE_INHERITED_OBJECT_TYPE_PRESENT;
+			}
 
-				if (!object_in_list(object_list, &inherited_object)) {
-					tmp_acl->aces[tmp_acl->num_aces].flags |= SEC_ACE_FLAG_INHERIT_ONLY;
+			/*
+			 * If the ACE had an explicit object class
+			 * schemaId, but no attribute/propertySet
+			 * we need to downgrate the _OBJECT variants
+			 * to the normal ones.
+			 */
+			if (inherited_property == NULL) {
+				switch (tmp_ace->type) {
+				case SEC_ACE_TYPE_ACCESS_ALLOWED:
+				case SEC_ACE_TYPE_ACCESS_DENIED:
+				case SEC_ACE_TYPE_SYSTEM_AUDIT:
+				case SEC_ACE_TYPE_SYSTEM_ALARM:
+				case SEC_ACE_TYPE_ALLOWED_COMPOUND:
+					break;
+				case SEC_ACE_TYPE_ACCESS_ALLOWED_OBJECT:
+					tmp_ace->type = SEC_ACE_TYPE_ACCESS_ALLOWED;
+					break;
+				case SEC_ACE_TYPE_ACCESS_DENIED_OBJECT:
+					tmp_ace->type = SEC_ACE_TYPE_ACCESS_DENIED;
+					break;
+				case SEC_ACE_TYPE_SYSTEM_ALARM_OBJECT:
+					tmp_ace->type = SEC_ACE_TYPE_SYSTEM_ALARM;
+					break;
+				case SEC_ACE_TYPE_SYSTEM_AUDIT_OBJECT:
+					tmp_ace->type = SEC_ACE_TYPE_SYSTEM_AUDIT;
+					break;
 				}
-
-				break;
 			}
 
-			tmp_acl->num_aces++;
-			if (is_container) {
-				if (!(ace->flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT) &&
-				    (desc_ace_has_generic(ace))) {
-					    tmp_acl->aces = talloc_realloc(tmp_acl,
-									   tmp_acl->aces,
-									   struct security_ace,
-									   tmp_acl->num_aces+1);
-					    if (tmp_acl->aces == NULL) {
-						    talloc_free(tmp_ctx);
-						    return NULL;
-					    }
-					    tmp_acl->aces[tmp_acl->num_aces] = *ace;
-					    desc_expand_generic(&tmp_acl->aces[tmp_acl->num_aces],
-								owner,
-								group);
-					    tmp_acl->aces[tmp_acl->num_aces].flags = SEC_ACE_FLAG_INHERITED_ACE;
-					    tmp_acl->num_aces++;
-				}
+			if (expand_only) {
+				continue;
 			}
 		}
+
+		tmp_acl->aces = talloc_realloc(tmp_acl,
+					       tmp_acl->aces,
+					       struct security_ace,
+					       tmp_acl->num_aces+1);
+		if (tmp_acl->aces == NULL) {
+			talloc_free(tmp_ctx);
+			return NULL;
+		}
+
+		tmp_ace = &tmp_acl->aces[tmp_acl->num_aces];
+		tmp_acl->num_aces++;
+
+		*tmp_ace = *ace;
+		tmp_ace->flags |= SEC_ACE_FLAG_INHERITED_ACE;
+
+		if (inherited_only) {
+			tmp_ace->flags |= SEC_ACE_FLAG_INHERIT_ONLY;
+		} else {
+			tmp_ace->flags &= ~SEC_ACE_FLAG_INHERIT_ONLY;
+		}
+
+		if (ace->flags & SEC_ACE_FLAG_NO_PROPAGATE_INHERIT) {
+			tmp_ace->flags &= ~SEC_ACE_FLAG_CONTAINER_INHERIT;
+			tmp_ace->flags &= ~SEC_ACE_FLAG_OBJECT_INHERIT;
+			tmp_ace->flags &= ~SEC_ACE_FLAG_NO_PROPAGATE_INHERIT;
+		}
 	}
 	if (tmp_acl->num_aces == 0) {
 		return NULL;
diff --git a/selftest/target/Samba3.pm b/selftest/target/Samba3.pm
index f9c732284c2..9c590547c94 100755
--- a/selftest/target/Samba3.pm
+++ b/selftest/target/Samba3.pm
@@ -1974,6 +1974,10 @@ sub setup_fileserver
 	path = $veto_sharedir
 	delete veto files = yes
 
+[veto_files_nohidden]
+	path = $veto_sharedir
+	veto files = /.*/
+
 [veto_files]
 	path = $veto_sharedir
 	veto files = /veto_name*/
diff --git a/source3/lib/util.c b/source3/lib/util.c
index 912ce1d3004..919dbcf68c5 100644
--- a/source3/lib/util.c
+++ b/source3/lib/util.c
@@ -748,6 +748,11 @@ bool is_in_path(const char *name, name_compare_entry *namelist, bool case_sensit
 		return False;
 	}
 
+	/* Do not reject path components if namelist is set to '.*' */
+	if (ISDOT(name) || ISDOTDOT(name)) {
+		return false;
+	}
+
 	DEBUG(8, ("is_in_path: %s\n", name));
 
 	/* Get the last component of the unix name. */
diff --git a/source3/script/tests/test_veto_files.sh b/source3/script/tests/test_veto_files.sh
index 5ecfb53b8a4..201883ee330 100755
--- a/source3/script/tests/test_veto_files.sh
+++ b/source3/script/tests/test_veto_files.sh
@@ -22,13 +22,21 @@ SHAREPATH=${5}
 SMBCLIENT=${6}
 shift 6
 SMBCLIENT="$VALGRIND ${SMBCLIENT}"
+# Used by test_smbclient()
+# shellcheck disable=2034
+smbclient="$VALGRIND ${SMBCLIENT}"
 ADDARGS="$@"
 
 incdir=$(dirname "$0")/../../../testprogs/blackbox
 . "$incdir"/subunit.sh
+. "${incdir}/common_test_fns.inc"
 
 failed=0
 
+TMPDIR=${PREFIX_ABS}/$(basename "${0}")
+mkdir -p "${TMPDIR}" || exit 1
+cd "${TMPDIR}" || exit 1
+
 #
 # Cleanup function.
 #
@@ -41,6 +49,8 @@ do_cleanup()
 		rm -rf "$SHAREPATH/veto_name_dir\"mangle"
 		rm -f "$SHAREPATH/veto_name_file"
 		rm -f "$SHAREPATH/veto_name_file\"mangle"
+		rm -f "${SHAREPATH}/regular_file"
+		rm -f "${SHAREPATH}/.hidden_file"
 	)
 }
 
@@ -51,7 +61,7 @@ smbclient_get_expect_error()
 {
 	filename1="$1"
 	expected_error="$2"
-	tmpfile=$PREFIX/smbclient_interactive_prompt_commands
+	tmpfile=${TMPDIR}/smbclient_interactive_prompt_commands
 	cat >"$tmpfile" <<EOF
 get $filename1 got_file
 quit
@@ -88,7 +98,7 @@ smbclient_create_expect_error()
 {
 	filename="$1.$$"
 	expected_error="$2"
-	tmpfile=$PREFIX/smbclient_interactive_prompt_commands
+	tmpfile=${TMPDIR}/smbclient_interactive_prompt_commands
 	cat >"$tmpfile" <<EOF
 put $tmpfile $filename
 quit
@@ -181,6 +191,25 @@ test_create_veto_file()
 
 do_cleanup
 
+echo "regular_file" > "${SHAREPATH}/regular_file"
+echo "hidden_file" > "${SHAREPATH}/.hidden_file"
+
+test_smbclient "download regular file" \
+	"get regular_file" "//${SERVER}/veto_files_nohidden" \
+	-U"${USERNAME}%${PASSWORD}" ||
+	failed=$((failed + 1))
+rm -f regular_file
+test_smbclient_expect_failure "hidden file can't be downloaded" \
+	"get .hidden_file" "//${SERVER}/veto_files_nohidden" \
+	-U"${USERNAME}%${PASSWORD}" ||
+	failed=$((failed + 1))
+test_smbclient "list files" \
+	"ls" "//${SERVER}/veto_files_nohidden" \
+	-U"${USERNAME}%${PASSWORD}" ||
+	failed=$((failed + 1))
+
+do_cleanup
+
 # Using hash2, veto_name_file\"mangle == VHXE5P~M
 # Using hash2, veto_name_dir\"mangle == VF5SKC~B
 
@@ -245,4 +274,6 @@ testit "get_veto_file" test_get_veto_file || failed=$(("$failed" + 1))
 
 do_cleanup
 
+cd "${PREFIX_ABS}" && rm -rf ${TMPDIR}
+
 exit "$failed"


-- 
Samba Shared Repository



More information about the samba-cvs mailing list