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

Karolin Seeger kseeger at samba.org
Thu Jul 2 09:04:52 UTC 2020


The branch, v4-11-test has been updated
       via  7d407fa84ae VERSION: Bump version up to 4.11.12.
       via  fe2edeccab4 Merge tag 'samba-4.11.11' into v4-11-test
       via  c9fa9874747 VERSION: Disable GIT_SNAPSHOT for the 4.11.11 release.
       via  1fa951943b5 Add release notes for Samba 4.11.11.
       via  df599b6b790 CVE-2020-10760 dsdb: Add tests for paged_results and VLV over the Global Catalog port
       via  4def2dc5547 CVE-2020-10760 dsdb: Ensure a proper talloc tree for saved controls
       via  153c8db09b2 CVE-2020-14303: s4 nbt: fix busy loop on empty UDP packet
       via  11034ea33fc CVE-2020-14303 Ensure an empty packet will not DoS the NBT server
       via  23e9eb71052 CVE-2020-10745: ndr/dns-utils: prepare for NBT compatibility
       via  83b00656ea0 CVE-2020-10745: dns_util/push: forbid names longer than 255 bytes
       via  507503f80e8 CVE-2020-10745: ndr_dns: do not allow consecutive dots
       via  b687813ac36 CVE-2020-10745: ndr/dns_utils: correct a comment
       via  37cacb8f41b CVE-2020-10745: ndr_dns: move ndr_push_dns_string core into sharable function
       via  ddeabf87957 CVE-2020-10745: librpc/tests: cmocka tests of dns and ndr strings
       via  ddd3ed7ce2e CVE-2020-10745: pytests: hand-rolled invalid dns/nbt packet tests
       via  c9fd1dbb131 ldb: Bump version to 2.0.12
       via  303947c58ab CVE-2020-10730: lib ldb: Check if ldb_lock_backend_callback called twice
       via  ae6e9445ac8 CVE-2020-10730: s4 dsdb vlv_pagination: Prevent repeat call of ldb_module_done
       via  dcf713038ff CVE-2020-10730: s4 dsdb paged_results: Prevent repeat call of ldb_module_done
       via  0c8cd0a9fbd CVE-2020-10730: dsdb: Ban the combination of paged_results and VLV
       via  c7608e43c93 CVE-2020-10730: dsdb: Fix crash when vlv and paged_results are combined
       via  01cce3d1fc6 CVE-2020-10730: selftest: Add test to show that VLV and paged_results are incompatible
       via  3fd7ce69761 CVE-2020-10730: vlv: Another workaround for mixing ASQ and VLV
       via  cf10f9b9a9a CVE-2020-10730: selftest: Add test to confirm VLV interaction with ASQ
       via  2041c05d9b4 CVE-2020-10730: vlv: Do not re-ASQ search the results of an ASQ search with VLV
       via  b8628cb4476 CVE-2020-10730: vlv: Use strcmp(), not strncmp() checking the NULL terminated control OIDs
       via  a29be4ffa3b VERSION: Bump version up to 4.11.11...
      from  08a51254198 VERSION: Bump version up to 4.11.11...

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


- Log -----------------------------------------------------------------
commit 7d407fa84ae53605db801ec6488641d0622686e5
Author: Karolin Seeger <kseeger at samba.org>
Date:   Thu Jul 2 11:04:19 2020 +0200

    VERSION: Bump version up to 4.11.12.
    
    Signed-off-by: Karolin Seeger <kseeger at samba.org>

commit fe2edeccab47dcc5783632828f1b6419df5e49ad
Merge: 08a51254198 c9fa9874747
Author: Karolin Seeger <kseeger at samba.org>
Date:   Thu Jul 2 11:03:55 2020 +0200

    Merge tag 'samba-4.11.11' into v4-11-test
    
    samba: tag release samba-4.11.11

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

Summary of changes:
 VERSION                                            |   2 +-
 WHATSNEW.txt                                       |  88 +++++++-
 lib/ldb/ABI/{ldb-2.0.10.sigs => ldb-2.0.12.sigs}   |   0
 ...ldb-util-1.1.10.sigs => pyldb-util-2.0.12.sigs} |   0
 lib/ldb/common/ldb.c                               |   9 +-
 lib/ldb/wscript                                    |   2 +-
 libcli/nbt/nbtsocket.c                             |  17 +-
 librpc/ndr/ndr_dns.c                               |  80 +------
 librpc/ndr/ndr_dns_utils.c                         | 134 ++++++++++++
 librpc/ndr/ndr_dns_utils.h                         |   6 +
 librpc/ndr/ndr_nbt.c                               |  72 +------
 librpc/tests/test_ndr_dns_nbt.c                    | 236 +++++++++++++++++++++
 librpc/wscript_build                               |  16 +-
 python/samba/tests/dns_packet.py                   | 230 ++++++++++++++++++++
 .../__init__.py => selftest/knownfail.d/dns_packet |   0
 selftest/knownfail.d/vlv                           |   2 +-
 source4/dsdb/samdb/ldb_modules/paged_results.c     |  65 +++++-
 source4/dsdb/samdb/ldb_modules/vlv_pagination.c    | 102 +++++++--
 source4/dsdb/tests/python/asq.py                   |  54 +++++
 source4/dsdb/tests/python/vlv.py                   | 184 ++++++++++------
 source4/selftest/tests.py                          |  12 ++
 21 files changed, 1076 insertions(+), 235 deletions(-)
 copy lib/ldb/ABI/{ldb-2.0.10.sigs => ldb-2.0.12.sigs} (100%)
 copy lib/ldb/ABI/{pyldb-util-1.1.10.sigs => pyldb-util-2.0.12.sigs} (100%)
 create mode 100644 librpc/ndr/ndr_dns_utils.c
 create mode 100644 librpc/ndr/ndr_dns_utils.h
 create mode 100644 librpc/tests/test_ndr_dns_nbt.c
 create mode 100644 python/samba/tests/dns_packet.py
 copy buildtools/wafsamba/__init__.py => selftest/knownfail.d/dns_packet (100%)


Changeset truncated at 500 lines:

diff --git a/VERSION b/VERSION
index 8f8da5faff0..b522cf1179e 100644
--- a/VERSION
+++ b/VERSION
@@ -25,7 +25,7 @@
 ########################################################
 SAMBA_VERSION_MAJOR=4
 SAMBA_VERSION_MINOR=11
-SAMBA_VERSION_RELEASE=11
+SAMBA_VERSION_RELEASE=12
 
 ########################################################
 # If a official release has a serious bug              #
diff --git a/WHATSNEW.txt b/WHATSNEW.txt
index c3f04c7993a..b9a6ac2e537 100644
--- a/WHATSNEW.txt
+++ b/WHATSNEW.txt
@@ -1,3 +1,87 @@
+                   ===============================
+                   Release Notes for Samba 4.11.11
+                            July 02, 2020
+		   ===============================
+
+
+This is a security release in order to address the following defects:
+
+o CVE-2020-10730: NULL pointer de-reference and use-after-free in Samba AD DC
+		  LDAP Server with ASQ, VLV and paged_results.
+o CVE-2020-10745: Parsing and packing of NBT and DNS packets can consume
+		  excessive CPU
+o CVE-2020-10760: LDAP Use-after-free in Samba AD DC Global Catalog with
+		  paged_results and VLV.
+o CVE-2020-14303: Empty UDP packet DoS in Samba AD DC nbtd.
+
+
+=======
+Details
+=======
+
+o  CVE-2020-10730:
+   A client combining the 'ASQ' and 'VLV' LDAP controls can cause a NULL pointer
+   de-reference and further combinations with the LDAP paged_results feature can
+   give a use-after-free in Samba's AD DC LDAP server.
+
+o  CVE-2020-10745: Parsing and packing of NBT and DNS packets can consume
+   excessive CPU.
+
+o  CVE-2020-10760:
+   The use of the paged_results or VLV controls against the Global Catalog LDAP
+   server on the AD DC will cause a use-after-free.
+
+o  CVE-2020-14303:
+   The AD DC NBT server in Samba 4.0 will enter a CPU spin and not process
+   further requests once it receives an empty (zero-length) UDP packet to
+   port 137.
+
+For more details, please refer to the security advisories.
+
+
+Changes since 4.11.10
+---------------------
+
+o  Douglas Bagnall <douglas.bagnall at catalyst.net.nz>
+   * BUG 14378: CVE-2020-10745: Invalid DNS or NBT queries containing dots use
+     several seconds of CPU each.
+
+o  Andrew Bartlett <abartlet at samba.org>
+   * BUG 14364: CVE-2020-10730: NULL de-reference in AD DC LDAP server when ASQ
+     and VLV combined.
+   * BUG 14402: CVE-2020-10760: Fix use-after-free in AD DC Global Catalog LDAP
+     server with paged_result or VLV.
+   * BUG 14417: CVE-2020-14303: Fix endless loop from empty UDP packet sent to
+     AD DC nbt_server.
+
+o  Gary Lockyer <gary at catalyst.net.nz>
+   * BUG 14364: CVE-2020-10730: NULL de-reference in AD DC LDAP server when ASQ
+     and VLV combined, ldb: Bump version to 2.1.4.  
+
+
+#######################################
+Reporting bugs & Development Discussion
+#######################################
+
+Please discuss this release on the samba-technical mailing list or by
+joining the #samba-technical IRC channel on irc.freenode.net.
+
+If you do report problems then please try to send high quality
+feedback. If you don't provide vital information to help us track down
+the problem then you will probably be ignored.  All bug reports should
+be filed under the "Samba 4.1 and newer" product in the project's Bugzilla
+database (https://bugzilla.samba.org/).
+
+
+======================================================================
+== Our Code, Our Bugs, Our Responsibility.
+== The Samba Team
+======================================================================
+
+
+Release notes for older releases follow:
+----------------------------------------
+
                    ===============================
                    Release Notes for Samba 4.11.10
                             June 30, 2020
@@ -54,8 +138,8 @@ database (https://bugzilla.samba.org/).
 ======================================================================
 
 
-Release notes for older releases follow:
-----------------------------------------
+----------------------------------------------------------------------
+
 
                    ==============================
                    Release Notes for Samba 4.11.9
diff --git a/lib/ldb/ABI/ldb-2.0.10.sigs b/lib/ldb/ABI/ldb-2.0.12.sigs
similarity index 100%
copy from lib/ldb/ABI/ldb-2.0.10.sigs
copy to lib/ldb/ABI/ldb-2.0.12.sigs
diff --git a/lib/ldb/ABI/pyldb-util-1.1.10.sigs b/lib/ldb/ABI/pyldb-util-2.0.12.sigs
similarity index 100%
copy from lib/ldb/ABI/pyldb-util-1.1.10.sigs
copy to lib/ldb/ABI/pyldb-util-2.0.12.sigs
diff --git a/lib/ldb/common/ldb.c b/lib/ldb/common/ldb.c
index 95e9138a56b..2d0926ffaf9 100644
--- a/lib/ldb/common/ldb.c
+++ b/lib/ldb/common/ldb.c
@@ -1018,6 +1018,13 @@ static int ldb_lock_backend_callback(struct ldb_request *req,
 	struct ldb_db_lock_context *lock_context;
 	int ret;
 
+	if (req->context == NULL) {
+		/*
+		 * The usual way to get here is to ignore the return codes
+		 * and continuing processing after an error.
+		 */
+		abort();
+	}
 	lock_context = talloc_get_type(req->context,
 				       struct ldb_db_lock_context);
 
@@ -1032,7 +1039,7 @@ static int ldb_lock_backend_callback(struct ldb_request *req,
 		 * If this is a LDB_REPLY_DONE or an error, unlock the
 		 * DB by calling the destructor on this context
 		 */
-		talloc_free(lock_context);
+		TALLOC_FREE(req->context);
 		return ret;
 	}
 
diff --git a/lib/ldb/wscript b/lib/ldb/wscript
index aeb6cfa6c45..da2b935d102 100644
--- a/lib/ldb/wscript
+++ b/lib/ldb/wscript
@@ -1,7 +1,7 @@
 #!/usr/bin/env python
 
 APPNAME = 'ldb'
-VERSION = '2.0.11'
+VERSION = '2.0.12'
 
 import sys, os
 
diff --git a/libcli/nbt/nbtsocket.c b/libcli/nbt/nbtsocket.c
index 33d53fba993..8aecaf73247 100644
--- a/libcli/nbt/nbtsocket.c
+++ b/libcli/nbt/nbtsocket.c
@@ -167,8 +167,23 @@ static void nbt_name_socket_recv(struct nbt_name_socket *nbtsock)
 		return;
 	}
 
+	/*
+	 * Given a zero length, data_blob_talloc() returns the
+	 * NULL blob {NULL, 0}.
+	 *
+	 * We only want to error return here on a real out of memory condition
+	 * (i.e. dsize != 0, so the UDP packet has data, but the return of the
+	 * allocation failed, so blob.data==NULL).
+	 *
+	 * Given an actual zero length UDP packet having blob.data == NULL
+	 * isn't an out of memory error condition, that's the defined semantics
+	 * of data_blob_talloc() when asked for zero bytes.
+	 *
+	 * We still need to continue to do the zero-length socket_recvfrom()
+	 * read in order to clear the "read pending" condition on the socket.
+	 */
 	blob = data_blob_talloc(tmp_ctx, NULL, dsize);
-	if (blob.data == NULL) {
+	if (blob.data == NULL && dsize != 0) {
 		talloc_free(tmp_ctx);
 		return;
 	}
diff --git a/librpc/ndr/ndr_dns.c b/librpc/ndr/ndr_dns.c
index d37c8cc2ece..966e0b59786 100644
--- a/librpc/ndr/ndr_dns.c
+++ b/librpc/ndr/ndr_dns.c
@@ -33,6 +33,7 @@
 #include "librpc/gen_ndr/ndr_dnsp.h"
 #include "system/locale.h"
 #include "lib/util/util_net.h"
+#include "ndr_dns_utils.h"
 
 /* don't allow an unlimited number of name components */
 #define MAX_COMPONENTS 128
@@ -159,80 +160,11 @@ _PUBLIC_ enum ndr_err_code ndr_push_dns_string(struct ndr_push *ndr,
 					       int ndr_flags,
 					       const char *s)
 {
-	if (!(ndr_flags & NDR_SCALARS)) {
-		return NDR_ERR_SUCCESS;
-	}
-
-	while (s && *s) {
-		enum ndr_err_code ndr_err;
-		char *compname;
-		size_t complen;
-		uint32_t offset;
-
-		if (!(ndr->flags & LIBNDR_FLAG_NO_COMPRESSION)) {
-			/* see if we have pushed the remaining string already,
-			 * if so we use a label pointer to this string
-			 */
-			ndr_err = ndr_token_retrieve_cmp_fn(&ndr->dns_string_list, s,
-							    &offset,
-							    (comparison_fn_t)strcmp,
-							    false);
-			if (NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
-				uint8_t b[2];
-
-				if (offset > 0x3FFF) {
-					return ndr_push_error(ndr, NDR_ERR_STRING,
-							      "offset for dns string " \
-							      "label pointer " \
-							      "%u[%08X] > 0x00003FFF",
-							      offset, offset);
-				}
-
-				b[0] = 0xC0 | (offset>>8);
-				b[1] = (offset & 0xFF);
-
-				return ndr_push_bytes(ndr, b, 2);
-			}
-		}
-
-		complen = strcspn(s, ".");
-
-		/* we need to make sure the length fits into 6 bytes */
-		if (complen > 0x3F) {
-			return ndr_push_error(ndr, NDR_ERR_STRING,
-					      "component length %u[%08X] > " \
-					      "0x0000003F",
-					      (unsigned)complen,
-					      (unsigned)complen);
-		}
-
-		compname = talloc_asprintf(ndr, "%c%*.*s",
-						(unsigned char)complen,
-						(unsigned char)complen,
-						(unsigned char)complen, s);
-		NDR_ERR_HAVE_NO_MEMORY(compname);
-
-		/* remember the current component + the rest of the string
-		 * so it can be reused later
-		 */
-		if (!(ndr->flags & LIBNDR_FLAG_NO_COMPRESSION)) {
-			NDR_CHECK(ndr_token_store(ndr, &ndr->dns_string_list, s,
-						  ndr->offset));
-		}
-
-		/* push just this component into the blob */
-		NDR_CHECK(ndr_push_bytes(ndr, (const uint8_t *)compname,
-					 complen+1));
-		talloc_free(compname);
-
-		s += complen;
-		if (*s == '.') s++;
-	}
-
-	/* if we reach the end of the string and have pushed the last component
-	 * without using a label pointer, we need to terminate the string
-	 */
-	return ndr_push_bytes(ndr, (const uint8_t *)"", 1);
+	return ndr_push_dns_string_list(ndr,
+					&ndr->dns_string_list,
+					ndr_flags,
+					s,
+					false);
 }
 
 _PUBLIC_ enum ndr_err_code ndr_pull_dns_txt_record(struct ndr_pull *ndr, int ndr_flags, struct dns_txt_record *r)
diff --git a/librpc/ndr/ndr_dns_utils.c b/librpc/ndr/ndr_dns_utils.c
new file mode 100644
index 00000000000..325d9c68bea
--- /dev/null
+++ b/librpc/ndr/ndr_dns_utils.c
@@ -0,0 +1,134 @@
+#include "includes.h"
+#include "../librpc/ndr/libndr.h"
+#include "ndr_dns_utils.h"
+
+
+/**
+  push a dns/nbt string list to the wire
+*/
+enum ndr_err_code ndr_push_dns_string_list(struct ndr_push *ndr,
+					   struct ndr_token_list *string_list,
+					   int ndr_flags,
+					   const char *s,
+					   bool is_nbt)
+{
+	const char *start = s;
+	bool use_compression;
+	size_t max_length;
+	if (is_nbt) {
+		use_compression = true;
+		/*
+		 * Max length is longer in NBT/Wins, because Windows counts
+		 * the semi-decompressed size of the netbios name (16 bytes)
+		 * rather than the wire size of 32, which is what you'd expect
+		 * if it followed RFC1002 (it uses the short form in
+		 * [MS-WINSRA]). In other words the maximum size of the
+		 * "scope" is 237, not 221.
+		 *
+		 * We make the size limit slightly larger than 255 + 16,
+		 * because the 237 scope limit is already enforced in the
+		 * winsserver code with a specific return value; bailing out
+		 * here would muck with that.
+		 */
+		max_length = 274;
+	} else {
+		use_compression = !(ndr->flags & LIBNDR_FLAG_NO_COMPRESSION);
+		max_length = 255;
+	}
+
+	if (!(ndr_flags & NDR_SCALARS)) {
+		return NDR_ERR_SUCCESS;
+	}
+
+	while (s && *s) {
+		enum ndr_err_code ndr_err;
+		char *compname;
+		size_t complen;
+		uint32_t offset;
+
+		if (use_compression) {
+			/* see if we have pushed the remaining string already,
+			 * if so we use a label pointer to this string
+			 */
+			ndr_err = ndr_token_retrieve_cmp_fn(string_list, s,
+							    &offset,
+							    (comparison_fn_t)strcmp,
+							    false);
+			if (NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
+				uint8_t b[2];
+
+				if (offset > 0x3FFF) {
+					return ndr_push_error(ndr, NDR_ERR_STRING,
+							      "offset for dns string " \
+							      "label pointer " \
+							      "%u[%08X] > 0x00003FFF",
+							      offset, offset);
+				}
+
+				b[0] = 0xC0 | (offset>>8);
+				b[1] = (offset & 0xFF);
+
+				return ndr_push_bytes(ndr, b, 2);
+			}
+		}
+
+		complen = strcspn(s, ".");
+
+		/* the length must fit into 6 bits (i.e. <= 63) */
+		if (complen > 0x3F) {
+			return ndr_push_error(ndr, NDR_ERR_STRING,
+					      "component length %u[%08X] > " \
+					      "0x0000003F",
+					      (unsigned)complen,
+					      (unsigned)complen);
+		}
+
+		if (complen == 0 && s[complen] == '.') {
+			return ndr_push_error(ndr, NDR_ERR_STRING,
+					      "component length is 0 "
+					      "(consecutive dots)");
+		}
+
+		if (is_nbt && s[complen] == '.' && s[complen + 1] == '\0') {
+			/* nbt names are sometimes usernames, and we need to
+			 * keep a trailing dot to ensure it is byte-identical,
+			 * (not just semantically identical given DNS
+			 * semantics). */
+			complen++;
+		}
+
+		compname = talloc_asprintf(ndr, "%c%*.*s",
+						(unsigned char)complen,
+						(unsigned char)complen,
+						(unsigned char)complen, s);
+		NDR_ERR_HAVE_NO_MEMORY(compname);
+
+		/* remember the current component + the rest of the string
+		 * so it can be reused later
+		 */
+		if (use_compression) {
+			NDR_CHECK(ndr_token_store(ndr, string_list, s,
+						  ndr->offset));
+		}
+
+		/* push just this component into the blob */
+		NDR_CHECK(ndr_push_bytes(ndr, (const uint8_t *)compname,
+					 complen+1));
+		talloc_free(compname);
+
+		s += complen;
+		if (*s == '.') {
+			s++;
+		}
+		if (s - start > max_length) {
+			return ndr_push_error(ndr, NDR_ERR_STRING,
+					      "name > %zu character long",
+					      max_length);
+		}
+	}
+
+	/* if we reach the end of the string and have pushed the last component
+	 * without using a label pointer, we need to terminate the string
+	 */
+	return ndr_push_bytes(ndr, (const uint8_t *)"", 1);
+}
diff --git a/librpc/ndr/ndr_dns_utils.h b/librpc/ndr/ndr_dns_utils.h
new file mode 100644
index 00000000000..71a65433bbb
--- /dev/null
+++ b/librpc/ndr/ndr_dns_utils.h
@@ -0,0 +1,6 @@
+
+enum ndr_err_code ndr_push_dns_string_list(struct ndr_push *ndr,
+					   struct ndr_token_list *string_list,
+					   int ndr_flags,
+					   const char *s,
+					   bool is_nbt);
diff --git a/librpc/ndr/ndr_nbt.c b/librpc/ndr/ndr_nbt.c
index 838f947a168..e8dd7549a53 100644
--- a/librpc/ndr/ndr_nbt.c
+++ b/librpc/ndr/ndr_nbt.c
@@ -25,6 +25,8 @@
 #include "includes.h"
 #include "../libcli/nbt/libnbt.h"
 #include "../libcli/netlogon/netlogon.h"
+#include "ndr_dns_utils.h"
+
 
 /* don't allow an unlimited number of name components */
 #define MAX_COMPONENTS 128
@@ -141,71 +143,11 @@ _PUBLIC_ enum ndr_err_code ndr_pull_nbt_string(struct ndr_pull *ndr, int ndr_fla
 */
 _PUBLIC_ enum ndr_err_code ndr_push_nbt_string(struct ndr_push *ndr, int ndr_flags, const char *s)
 {
-	if (!(ndr_flags & NDR_SCALARS)) {
-		return NDR_ERR_SUCCESS;
-	}
-
-	while (s && *s) {
-		enum ndr_err_code ndr_err;
-		char *compname;
-		size_t complen;
-		uint32_t offset;
-
-		/* see if we have pushed the remaining string already,
-		 * if so we use a label pointer to this string
-		 */
-		ndr_err = ndr_token_retrieve_cmp_fn(&ndr->nbt_string_list, s, &offset, (comparison_fn_t)strcmp, false);
-		if (NDR_ERR_CODE_IS_SUCCESS(ndr_err)) {
-			uint8_t b[2];
-
-			if (offset > 0x3FFF) {
-				return ndr_push_error(ndr, NDR_ERR_STRING,
-						      "offset for nbt string label pointer %u[%08X] > 0x00003FFF",
-						      offset, offset);
-			}
-
-			b[0] = 0xC0 | (offset>>8);
-			b[1] = (offset & 0xFF);
-
-			return ndr_push_bytes(ndr, b, 2);
-		}
-
-		complen = strcspn(s, ".");
-
-		/* we need to make sure the length fits into 6 bytes */
-		if (complen > 0x3F) {
-			return ndr_push_error(ndr, NDR_ERR_STRING,
-					      "component length %u[%08X] > 0x0000003F",
-					      (unsigned)complen, (unsigned)complen);
-		}
-
-		if (s[complen] == '.' && s[complen+1] == '\0') {
-			complen++;


-- 
Samba Shared Repository



More information about the samba-cvs mailing list