Merge ~ahasenack/ubuntu/+source/samba:jammy-samba-kb5028166-2027716 into ubuntu/+source/samba:ubuntu/jammy-devel

Proposed by Andreas Hasenack
Status: Merged
Approved by: git-ubuntu bot
Approved revision: not available
Merged at revision: 1b97ed30dceab15beb88db4498e217cfb7f83bca
Proposed branch: ~ahasenack/ubuntu/+source/samba:jammy-samba-kb5028166-2027716
Merge into: ubuntu/+source/samba:ubuntu/jammy-devel
Diff against target: 805 lines (+753/-1)
6 files modified
debian/changelog (+18/-0)
debian/patches/secure-channel-faulty-kb5028166.patch (+215/-0)
debian/patches/series (+1/-0)
debian/tests/control (+4/-0)
debian/tests/samba-ad-dc-provisioning-internal-dns (+404/-0)
debian/tests/util (+111/-1)
Reviewer Review Type Date Requested Status
git-ubuntu bot Approve
Lucas Kanashiro (community) Approve
Canonical Server Reporter Pending
Review via email: mp+447459@code.launchpad.net

Description of the change

PPA: https://launchpad.net/~ahasenack/+archive/ubuntu/samba-kb5028166/

Bug fix for #2027716. SRU template is filled in, including a test case.

I split the patch in two commits: one that introduces the upstream patch, pristine, and another that removes the hunks that changed the upstream test suite. We don't run that test suite, and I think a smaller patch is easier to review, specially when comparing to the other ubuntu releases which needed a small backport change.

I tried to make incremental changes to this branch when compared to lunar, so it's easier to review. But range-diff is still a bit noisy, because the patch that fixes the problem needed a small backport.

The DEP8 test also needed tweaking for jammy, and I tried to keep the differences as additional commits.

DEP8 is green. It doesn't exercise this bug in particular, but does exercise a domain join with linux<->linux, which is a good regression test.

To post a comment you must log in.
Revision history for this message
Lucas Kanashiro (lucaskanashiro) wrote :
Download full text (14.4 KiB)

Thanks for this MP Andreas! The packaging changes look good to me. I tried to build the package locally to run the DEP-8 test you are introducing locally and I got the following build error:

[2984/4247] Compiling source4/torture/smb2/sessid.c
20:35:19 runner ['/usr/bin/gcc', '-D_SAMBA_BUILD_=4', '-DHAVE_CONFIG_H=1', '-g', '-O2', '-ffile-prefix-map=/<<PKGBUILDDIR>>=.', '-flto=auto', '-ffat-lto-objects', '-flto=auto', '-ffat-lto-objects', '-fstack-protector-strong', '-Wformat', '-Werror=format-security', '-MMD', '-D_GNU_SOURCE=1', '-D_XOPEN_SOURCE_EXTENDED=1', '-DHAVE_CONFIG_H=1', '-fPIC', '-D__STDC_WANT_LIB_EXT1__=1', '-D_REENTRANT', '-DCTDB_HELPER_BINDIR="/usr/lib/x86_64-linux-gnu/ctdb"', '-DLOGDIR="/var/log/ctdb"', '-DCTDB_DATADIR="/usr/share/ctdb"', '-DCTDB_ETCDIR="/etc/ctdb"', '-DCTDB_VARDIR="/var/lib/ctdb"', '-DCTDB_RUNDIR="/var/run/ctdb"', '-fstack-protector-strong', '-fstack-clash-protection', '-DSTATIC_TORTURE_SMB2_MODULES=NULL', '-DSTATIC_TORTURE_SMB2_MODULES_PROTO=extern void __TORTURE_SMB2_dummy_module_proto(void)', '-Isource4/torture/smb2', '-I../../source4/torture/smb2', '-Iinclude/public', '-I../../include/public', '-Isource4', '-I../../source4', '-Ilib', '-I../../lib', '-Isource4/lib', '-I../../source4/lib', '-Isource4/include', '-I../../source4/include', '-Iinclude', '-I../../include', '-Ilib/replace', '-I../../lib/replace', '-Ictdb/include', '-I../../ctdb/include', '-Ictdb', '-I../../ctdb', '-I.', '-I../..', '-Ilib/torture', '-I../../lib/torture', '-Ilibrpc', '-I../../librpc', '-Ilib/tsocket', '-I../../lib/tsocket', '-Iauth', '-I../../auth', '-Ilib/util/<<PKGBUILDDIR>>/third_party/gpfs', '-I../../lib/util/<<PKGBUILDDIR>>/third_party/gpfs', '-Ilib/ldb-samba', '-I../../lib/ldb-samba', '-Ilibcli/util', '-I../../libcli/util', '-Ilib/dbwrap', '-I../../lib/dbwrap', '-Isource4/auth/kerberos', '-I../../source4/auth/kerberos', '-Iauth/credentials', '-I../../auth/credentials', '-Isource4/heimdal/lib/asn1', '-I../../source4/heimdal/lib/asn1', '-Isource4/heimdal_build', '-I../../source4/heimdal_build', '-Ilibcli/auth', '-I../../libcli/auth', '-Isource4/heimdal/lib/roken', '-I../../source4/heimdal/lib/roken', '-Isource4/heimdal/include', '-I../../source4/heimdal/include', '-Isource4/heimdal_build/include', '-I../../source4/heimdal_build/include', '-Isource4/auth', '-I../../source4/auth', '-Isource4/libcli/smb2', '-I../../source4/libcli/smb2', '-Isource4/dsdb', '-I../../source4/dsdb', '-Isource4/heimdal/lib/gssapi', '-I../../source4/heimdal/lib/gssapi', '-Isource4/heimdal/lib/gssapi/gssapi', '-I../../source4/heimdal/lib/gssapi/gssapi', '-Isource4/heimdal/lib/gssapi/spnego', '-I../../source4/heimdal/lib/gssapi/spnego', '-Isource4/heimdal/lib/gssapi/krb5', '-I../../source4/heimdal/lib/gssapi/krb5', '-Isource4/heimdal/lib/gssapi/mech', '-I../../source4/heimdal/lib/gssapi/mech', '-Isource4/heimdal/lib/hx509', '-I../../source4/heimdal/lib/hx509', '-Ilib/param', '-I../../lib/param', '-Isource4/libcli', '-I../../source4/libcli', '-Iauth/gensec', '-I../../auth/gensec', '-Isource3', '-I../../source3', '-Isource3/include', '-I../../source3/include', '-Isource3/lib', '-I../../source3/lib', '-Isource4/heimdal/lib/com_err', '-I../../source4/heimdal/lib...

review: Needs Information
Revision history for this message
Lucas Kanashiro (lucaskanashiro) wrote :

Argh, it built fine locally now, not sure exactly what happened, but there is this DEP-8 test failing locally for me:

autopkgtest [18:17:02]: test samba-ad-dc-provisioning-internal-dns: - - - - - - - - - - results - - - - - - - - - -
samba-ad-dc-provisioning-internal-dns FAIL non-zero exit status 253

Summary of a local autopkgtest run:

autopkgtest [19:09:04]: @@@@@@@@@@@@@@@@@@@@ summary
cifs-share-access PASS
cifs-share-access-uring PASS
python-smoke PASS
smbclient-anonymous-share-list PASS
smbclient-authenticated-share-list PASS
smbclient-share-access PASS
smbclient-share-access-uring PASS
samba-ad-dc-provisioning-internal-dns FAIL non-zero exit status 253

Revision history for this message
Andreas Hasenack (ahasenack) wrote :

Hm, that's odd:

660s Error loading module '/usr/lib/x86_64-linux-gnu/samba/vfs/acl_xattr.so': /usr/lib/x86_64-linux-gnu/samba/vfs/acl_xattr.so: cannot open shared object file: No such file or directory

Looks like jammy also needs the samba-vfs-modules package added to the test dependency, just like I found out for focal. Not sure how I didn't see this before.

Revision history for this message
Andreas Hasenack (ahasenack) wrote :

PPA rebuilt (jammy), all tests re-triggered, let's see tomorrow what we get.

Revision history for this message
Andreas Hasenack (ahasenack) wrote :

And this time it's green all around:
Results: (from http://autopkgtest.ubuntu.com/results/autopkgtest-jammy-ahasenack-samba-kb5028166/?format=plain)
  samba @ amd64:
    26.07.23 00:00:56 Log 🗒️ ✅ Triggers: samba/2:4.15.13+dfsg-0ubuntu1.3~ppa2
  samba @ arm64:
    26.07.23 00:40:52 Log 🗒️ ✅ Triggers: samba/2:4.15.13+dfsg-0ubuntu1.3~ppa2
  samba @ armhf:
    26.07.23 00:01:31 Log 🗒️ ✅ Triggers: samba/2:4.15.13+dfsg-0ubuntu1.3~ppa2
  samba @ ppc64el:
    26.07.23 00:15:03 Log 🗒️ ✅ Triggers: samba/2:4.15.13+dfsg-0ubuntu1.3~ppa2
  samba @ s390x:
    26.07.23 00:18:25 Log 🗒️ ✅ Triggers: samba/2:4.15.13+dfsg-0ubuntu1.3~ppa2

Revision history for this message
Lucas Kanashiro (lucaskanashiro) wrote :

Awesome! Now, LGTM, +1.

review: Approve
Revision history for this message
git-ubuntu bot (git-ubuntu-bot) wrote :

Approvers: ahasenack, lucaskanashiro
Uploaders: ahasenack, lucaskanashiro
MP auto-approved

review: Approve
Revision history for this message
Andreas Hasenack (ahasenack) wrote :

Thanks, uploaded with rich history:

Uploading samba_4.15.13+dfsg-0ubuntu1.3.dsc
Uploading samba_4.15.13+dfsg-0ubuntu1.3.debian.tar.xz
Uploading samba_4.15.13+dfsg-0ubuntu1.3_source.buildinfo
Uploading samba_4.15.13+dfsg-0ubuntu1.3_source.changes

Preview Diff

[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1diff --git a/debian/changelog b/debian/changelog
2index b951fb0..5e12a5e 100644
3--- a/debian/changelog
4+++ b/debian/changelog
5@@ -1,3 +1,21 @@
6+samba (2:4.15.13+dfsg-0ubuntu1.3) jammy; urgency=medium
7+
8+ * d/p/secure-channel-faulty-kb5028166.patch: fix domain membership
9+ after Windows KB5028166 update (LP: #2027716)
10+ * Cherry pick samba AD DC provisioning DEP8 test from later Ubuntu
11+ releases (LP: #1977746, LP: #2011745):
12+ - d/t/control, d/t/util, d/t/samba-ad-dc-provisioning-internal-dns:
13+ samba AD DC provisioning and domain join tests with internal DNS
14+ + d/t/control: adjust package dependencies
15+ + d/t/samba-ad-dc-provisioning-internal-dns: handle the case where
16+ libnss-winbind does not automatically add winbind to
17+ /etc/nsswitch.conf (that is done only in Lunar and later)
18+ + d/t/samba-ad-dc-provisioning-internal-dns: use case insensitive
19+ match when inspecting kerberos tickets, as the hostname may be
20+ capitalized
21+
22+ -- Andreas Hasenack <andreas@canonical.com> Sun, 23 Jul 2023 17:09:59 -0300
23+
24 samba (2:4.15.13+dfsg-0ubuntu1.2) jammy-security; urgency=medium
25
26 * SECURITY UPDATE: Out-Of-Bounds read in winbind AUTH_CRAP
27diff --git a/debian/patches/secure-channel-faulty-kb5028166.patch b/debian/patches/secure-channel-faulty-kb5028166.patch
28new file mode 100644
29index 0000000..c1367f7
30--- /dev/null
31+++ b/debian/patches/secure-channel-faulty-kb5028166.patch
32@@ -0,0 +1,215 @@
33+From 2150e7f3dc409b415ca8b6a541729a49932c5073 Mon Sep 17 00:00:00 2001
34+From: Stefan Metzmacher <metze@samba.org>
35+Date: Sat, 15 Jul 2023 17:20:32 +0200
36+Subject: [PATCH 1/4] netlogon.idl: add support for netr_LogonGetCapabilities
37+ response level 2
38+
39+We don't have any documentation about this yet, but tests against
40+a Windows Server 2022 patched with KB5028166 revealed that
41+the response for query_level=2 is exactly the same as
42+for querey_level=1.
43+
44+Until we know the reason for query_level=2 we won't
45+use it as client nor support it in the server, but
46+we want ndrdump to work.
47+
48+BUG: https://bugzilla.samba.org/show_bug.cgi?id=15418
49+
50+Signed-off-by: Stefan Metzmacher <metze@samba.org>
51+Reviewed-by: Andrew Bartlett <abartlet@samba.org>
52+(cherry picked from commit 5f87888ed53320538cf773d64868390d8641a40e)
53+---
54+ librpc/idl/netlogon.idl | 1 +
55+ 1 file changed, 1 insertion(+)
56+
57+Ubuntu patch note: removed the parts that changed the upstream test suite
58+
59+Origin: backport, https://bugzilla.samba.org/attachment.cgi?id=17987
60+Bug: https://bugzilla.samba.org/show_bug.cgi?id=15418
61+Bug-Ubuntu: https://bugs.launchpad.net/ubuntu/+source/samba/+bug/2027716
62+Last-Update: 2023-07-17
63+
64+diff --git a/librpc/idl/netlogon.idl b/librpc/idl/netlogon.idl
65+index d956a661fff7..b51767136d3c 100644
66+--- a/librpc/idl/netlogon.idl
67++++ b/librpc/idl/netlogon.idl
68+@@ -1241,6 +1241,7 @@ interface netlogon
69+ /* Function 0x15 */
70+ typedef [switch_type(uint32)] union {
71+ [case(1)] netr_NegotiateFlags server_capabilities;
72++ [case(2)] netr_NegotiateFlags server_capabilities;
73+ } netr_Capabilities;
74+
75+ NTSTATUS netr_LogonGetCapabilities(
76+--
77+2.34.1
78+
79+
80+From fa71e7b4b027dc8224fda7125f1faaefa4e71eae Mon Sep 17 00:00:00 2001
81+From: Stefan Metzmacher <metze@samba.org>
82+Date: Sat, 15 Jul 2023 16:11:48 +0200
83+Subject: [PATCH 3/4] s4:rpc_server:netlogon: generate FAULT_INVALID_TAG for
84+ invalid netr_LogonGetCapabilities levels
85+
86+This is important as Windows clients with KB5028166 seem to
87+call netr_LogonGetCapabilities with query_level=2 after
88+a call with query_level=1.
89+
90+An unpatched Windows Server returns DCERPC_NCA_S_FAULT_INVALID_TAG
91+for query_level values other than 1.
92+While Samba tries to return NT_STATUS_NOT_SUPPORTED, but
93+later fails to marshall the response, which results
94+in DCERPC_FAULT_BAD_STUB_DATA instead.
95+
96+Because we don't have any documentation for level 2 yet,
97+we just try to behave like an unpatched server and
98+generate DCERPC_NCA_S_FAULT_INVALID_TAG instead of
99+DCERPC_FAULT_BAD_STUB_DATA.
100+Which allows patched Windows clients to keep working
101+against a Samba DC.
102+
103+BUG: https://bugzilla.samba.org/show_bug.cgi?id=15418
104+
105+Signed-off-by: Stefan Metzmacher <metze@samba.org>
106+Reviewed-by: Andrew Bartlett <abartlet@samba.org>
107+(cherry picked from commit d5f1097b6220676d56ed5fc6707acf667b704518)
108+---
109+ .../knownfail.d/netr_LogonGetCapabilities | 2 --
110+ source4/rpc_server/netlogon/dcerpc_netlogon.c | 28 ++++++++++++++++---
111+ 2 files changed, 24 insertions(+), 6 deletions(-)
112+
113+diff --git a/source4/rpc_server/netlogon/dcerpc_netlogon.c b/source4/rpc_server/netlogon/dcerpc_netlogon.c
114+index 6a3e044eb9da..26be4f567513 100644
115+--- a/source4/rpc_server/netlogon/dcerpc_netlogon.c
116++++ b/source4/rpc_server/netlogon/dcerpc_netlogon.c
117+@@ -2399,6 +2399,30 @@ static NTSTATUS dcesrv_netr_LogonGetCapabilities(struct dcesrv_call_state *dce_c
118+ struct netlogon_creds_CredentialState *creds;
119+ NTSTATUS status;
120+
121++ switch (r->in.query_level) {
122++ case 1:
123++ break;
124++ case 2:
125++ /*
126++ * Until we know the details behind KB5028166
127++ * just return DCERPC_NCA_S_FAULT_INVALID_TAG
128++ * like an unpatched Windows Server.
129++ */
130++ FALL_THROUGH;
131++ default:
132++ /*
133++ * There would not be a way to marshall the
134++ * the response. Which would mean our final
135++ * ndr_push would fail an we would return
136++ * an RPC-level fault with DCERPC_FAULT_BAD_STUB_DATA.
137++ *
138++ * But it's important to match a Windows server
139++ * especially before KB5028166, see also our bug #15418
140++ * Otherwise Windows client would stop talking to us.
141++ */
142++ DCESRV_FAULT(DCERPC_NCA_S_FAULT_INVALID_TAG);
143++ }
144++
145+ status = dcesrv_netr_creds_server_step_check(dce_call,
146+ mem_ctx,
147+ r->in.computer_name,
148+@@ -2410,10 +2434,6 @@ static NTSTATUS dcesrv_netr_LogonGetCapabilities(struct dcesrv_call_state *dce_c
149+ }
150+ NT_STATUS_NOT_OK_RETURN(status);
151+
152+- if (r->in.query_level != 1) {
153+- return NT_STATUS_NOT_SUPPORTED;
154+- }
155+-
156+ r->out.capabilities->server_capabilities = creds->negotiate_flags;
157+
158+ return NT_STATUS_OK;
159+--
160+2.34.1
161+
162+
163+From 05f110e1a4d4b38bfbaaa3a92fda7a9127b3b456 Mon Sep 17 00:00:00 2001
164+From: Stefan Metzmacher <metze@samba.org>
165+Date: Sat, 15 Jul 2023 16:11:48 +0200
166+Subject: [PATCH 4/4] s3:rpc_server:netlogon: generate FAULT_INVALID_TAG for
167+ invalid netr_LogonGetCapabilities levels
168+
169+This is important as Windows clients with KB5028166 seem to
170+call netr_LogonGetCapabilities with query_level=2 after
171+a call with query_level=1.
172+
173+An unpatched Windows Server returns DCERPC_NCA_S_FAULT_INVALID_TAG
174+for query_level values other than 1.
175+While Samba tries to return NT_STATUS_NOT_SUPPORTED, but
176+later fails to marshall the response, which results
177+in DCERPC_FAULT_BAD_STUB_DATA instead.
178+
179+Because we don't have any documentation for level 2 yet,
180+we just try to behave like an unpatched server and
181+generate DCERPC_NCA_S_FAULT_INVALID_TAG instead of
182+DCERPC_FAULT_BAD_STUB_DATA.
183+Which allows patched Windows clients to keep working
184+against a Samba DC.
185+
186+BUG: https://bugzilla.samba.org/show_bug.cgi?id=15418
187+
188+Signed-off-by: Stefan Metzmacher <metze@samba.org>
189+Reviewed-by: Andrew Bartlett <abartlet@samba.org>
190+
191+Autobuild-User(master): Stefan Metzmacher <metze@samba.org>
192+Autobuild-Date(master): Mon Jul 17 07:35:09 UTC 2023 on atb-devel-224
193+
194+(cherry picked from commit dfeabce44fbb78083fbbb2aa634fc4172cf83db9)
195+---
196+ .../knownfail.d/netr_LogonGetCapabilities | 1 -
197+ source3/rpc_server/netlogon/srv_netlog_nt.c | 29 ++++++++++++++++---
198+ 2 files changed, 25 insertions(+), 5 deletions(-)
199+ delete mode 100644 selftest/knownfail.d/netr_LogonGetCapabilities
200+
201+diff --git a/source3/rpc_server/netlogon/srv_netlog_nt.c b/source3/rpc_server/netlogon/srv_netlog_nt.c
202+index 5906464a9f3..35433ec6781 100644
203+--- a/source3/rpc_server/netlogon/srv_netlog_nt.c
204++++ b/source3/rpc_server/netlogon/srv_netlog_nt.c
205+@@ -2421,6 +2421,31 @@ NTSTATUS _netr_LogonGetCapabilities(struct pipes_struct *p,
206+ struct netlogon_creds_CredentialState *creds;
207+ NTSTATUS status;
208+
209++ switch (r->in.query_level) {
210++ case 1:
211++ break;
212++ case 2:
213++ /*
214++ * Until we know the details behind KB5028166
215++ * just return DCERPC_NCA_S_FAULT_INVALID_TAG
216++ * like an unpatched Windows Server.
217++ */
218++ FALL_THROUGH;
219++ default:
220++ /*
221++ * There would not be a way to marshall the
222++ * the response. Which would mean our final
223++ * ndr_push would fail an we would return
224++ * an RPC-level fault with DCERPC_FAULT_BAD_STUB_DATA.
225++ *
226++ * But it's important to match a Windows server
227++ * especially before KB5028166, see also our bug #15418
228++ * Otherwise Windows client would stop talking to us.
229++ */
230++ p->fault_state = DCERPC_NCA_S_FAULT_INVALID_TAG;
231++ return NT_STATUS_NOT_SUPPORTED;
232++ }
233++
234+ become_root();
235+ status = netr_creds_server_step_check(p, p->mem_ctx,
236+ r->in.computer_name,
237+@@ -2432,10 +2457,6 @@ NTSTATUS _netr_LogonGetCapabilities(struct pipes_struct *p,
238+ return status;
239+ }
240+
241+- if (r->in.query_level != 1) {
242+- return NT_STATUS_NOT_SUPPORTED;
243+- }
244+-
245+ r->out.capabilities->server_capabilities = creds->negotiate_flags;
246+
247+ return NT_STATUS_OK;
248diff --git a/debian/patches/series b/debian/patches/series
249index 5791d76..0a6a142 100644
250--- a/debian/patches/series
251+++ b/debian/patches/series
252@@ -64,3 +64,4 @@ CVE-2023-34968-09.patch
253 CVE-2023-34968-10.patch
254 CVE-2023-34968-11.patch
255 CVE-2023-34968-12.patch
256+secure-channel-faulty-kb5028166.patch
257diff --git a/debian/tests/control b/debian/tests/control
258index 3ecb853..6814243 100644
259--- a/debian/tests/control
260+++ b/debian/tests/control
261@@ -24,3 +24,7 @@ Restrictions: needs-root, allow-stderr, isolation-container
262 Tests: smbclient-share-access-uring
263 Depends: samba, samba-vfs-modules, smbclient, coreutils, systemd, passwd
264 Restrictions: needs-root, allow-stderr, isolation-container, skippable
265+
266+Tests: samba-ad-dc-provisioning-internal-dns
267+Depends: samba, samba-dsdb-modules, samba-vfs-modules, winbind, smbclient, krb5-user, bind9-dnsutils, lxd | snapd, lsb-release, dctrl-tools
268+Restrictions: needs-root, isolation-machine, allow-stderr, breaks-testbed
269diff --git a/debian/tests/samba-ad-dc-provisioning-internal-dns b/debian/tests/samba-ad-dc-provisioning-internal-dns
270new file mode 100755
271index 0000000..592a608
272--- /dev/null
273+++ b/debian/tests/samba-ad-dc-provisioning-internal-dns
274@@ -0,0 +1,404 @@
275+#!/bin/bash
276+
277+set -e
278+set -o pipefail
279+
280+source debian/tests/util
281+
282+declare -r domain="EXAMPLE"
283+declare -r realm="EXAMPLE.FAKE"
284+declare -r adminpass="Passw0rd"
285+declare -r test_user="test_user_${RANDOM}"
286+declare -r test_pw="test_user_secret_${RANDOM}"
287+declare -A user_pass
288+user_pass[Administrator]="${adminpass}"
289+user_pass[${test_user}]="${test_pw}"
290+declare -A join_method_deps
291+# Minimum set of deps: let realmd install the extra dependencies
292+# as needed, depending on the join method.
293+join_method_deps[realmd_sssd]="realmd krb5-user smbclient"
294+join_method_deps[realmd_winbind]="realmd krb5-user smbclient"
295+
296+
297+cleanup() {
298+ rc=$?
299+ set +e # so we don't exit midcleanup
300+ if [ ${rc} -ne 0 ]; then
301+ echo "## Something failed, gathering logs"
302+ echo
303+ echo "## smb.conf"
304+ cat /etc/samba/smb.conf
305+ echo
306+ echo "## resolv.conf"
307+ cat /etc/resolv.conf
308+ echo
309+ echo "## resolvectl status"
310+ resolvectl status
311+ echo "## journal for samba-ad-dc.service"
312+ journalctl -u samba-ad-dc.service --lines 500
313+ echo
314+ for log in /var/log/samba/log.*; do
315+ # skip compressed logrotated files
316+ if [ "${log%.gz}" != "${log}" ]; then
317+ continue
318+ fi
319+ [ -s "${log}" ] || continue
320+ echo "## $(basename ${log}):"
321+ tail -n 500 "${log}"
322+ echo
323+ done
324+ echo "## syslog"
325+ tail -n 500 /var/log/syslog
326+ fi
327+}
328+
329+trap cleanup EXIT
330+
331+assert_testparm() {
332+ local parameter="${1}"
333+ local expected_value="${2}"
334+ local current_value=""
335+ local -i retval=0
336+
337+ echo -n "Asserting ${parameter} is ${expected_value}: "
338+ current_value=$(testparm -s --parameter-name "${parameter}" 2>/dev/null) || {
339+ retval=$?
340+ echo "FAIL"
341+ return ${retval}
342+ }
343+ if [ "${current_value}" = "${expected_value}" ]; then
344+ echo "OK"
345+ return 0
346+ else
347+ echo "FAIL"
348+ return 1
349+ fi
350+}
351+
352+basic_config_tests() {
353+ echo "## Basic config tests"
354+ testparm -s > /dev/null
355+ assert_testparm "realm" "${realm}"
356+ assert_testparm "workgroup" "${domain}"
357+ assert_testparm "server role" "active directory domain controller"
358+ echo
359+}
360+
361+dns_tests() {
362+ echo "## DNS tests"
363+ echo "Obtaining administrator kerberos ticket"
364+ echo "${adminpass}" | timeout --verbose 30 kinit Administrator
365+ echo
366+ echo "Querying server info"
367+ samba-tool dns serverinfo "$(hostname)"
368+ echo
369+ echo "Checking we got a service ticket of type host/"
370+ klist | grep -i "host/$(hostname)"
371+ echo
372+ echo "Checking specific DNS records"
373+ for srv in _ldap._tcp _kerberos._tcp _kerberos._udp _kpasswd._udp; do
374+ echo -n "${srv}.${realm,,}: "
375+ dig @localhost +short -t SRV ${srv}.${realm,,}
376+ echo
377+ done
378+ echo
379+ echo -n "Checking that our hostname \"$(hostname)\" is in DNS: "
380+ myip=$(dig @localhost +short -t A "$(hostname).${realm,,}")
381+ echo "${myip}"
382+ echo
383+}
384+
385+user_creation_tests() {
386+ echo "## User creation tests"
387+ samba-tool domain passwordsettings set --complexity=off
388+ echo "Creating user \"${test_user}\" with password ${test_pw}"
389+ samba-tool user add "${test_user}" "${test_pw}"
390+ echo
391+ echo "Attempting to obtain kerberos ticket for user \"${test_user}\""
392+ # just in case it ends up waiting at a prompt, we use "timeout"
393+ echo "${test_pw}" | timeout --verbose 30 kinit "${test_user}"
394+ echo "Ticket obtained"
395+ klist
396+ echo
397+}
398+
399+smbclient_tests() {
400+ echo "## smbclient tests"
401+ kdestroy || :
402+ echo
403+ echo "Obtaining a TGT for ${test_user}"
404+ echo "${test_pw}" | timeout --verbose 30 kinit "${test_user}"
405+ klist | grep krbtgt
406+ echo
407+ echo "Attempting password-less authentication with smbclient"
408+ echo
409+ echo "Listing shares"
410+ smbclient -L "$(hostname)" --use-kerberos=required -k
411+ echo
412+ echo "Listing the sysvol share"
413+ smbclient "//$(hostname)/sysvol" --use-kerberos=required -k -c "ls"
414+ echo
415+ echo "Listing policies"
416+ # lowercase the ${realm}
417+ smbclient "//$(hostname)/sysvol" --use-kerberos=required -k -c "ls ${realm,,}/Policies/*"
418+ echo
419+ echo "Checking that we have a ticket for the cifs service after all these commands"
420+ klist | grep cifs/
421+ echo
422+}
423+
424+server_join_tests() {
425+ local member_server
426+ # the join methods are the keys of the join_method_deps dict
427+ local -a methods=("${!join_method_deps[@]}")
428+ local member_server="member-server"
429+
430+ echo "## Server join tests"
431+ echo "## Initializing lxd"
432+ setup_lxd "${realm,,}"
433+
434+ for method in "${methods[@]}"; do
435+ echo "## Setting up member server to join a domain using method ${method}"
436+ setup_member_server "${member_server}" "${method}"
437+ echo "## Joining domain with method ${method}"
438+ join_domain "${member_server}" "${method}"
439+ echo
440+ echo "## Verifying join with method ${method}"
441+ verify_join "${member_server}" "${method}"
442+ echo
443+ echo "## Leaving domain with method ${method}"
444+ leave_domain "${member_server}" "${method}"
445+ echo
446+ echo "## Destroying member server"
447+ lxc delete --force "${member_server}"
448+ done
449+}
450+
451+setup_member_server() {
452+ local container_name="${1}"
453+ local method="${2}"
454+ local release
455+
456+ release="$(lsb_release -cs)"
457+ if [ -z "${join_method_deps[${method}]}" ]; then
458+ echo "## INTERNAL ERROR, invalid join method: ${method}"
459+ return 1
460+ fi
461+ echo "## Got test dependencies: ${join_method_deps[${method}]}"
462+ # can't use cloud-init here to install packages, because we first need to
463+ # sync the apt config from the host to the container
464+ echo "## Launching ${release} container"
465+ lxc launch "ubuntu-daily:${release}" "${container_name}" -q
466+ wait_container_ready "${container_name}"
467+ send_apt_config "${container_name}"
468+ copy_local_apt_files "${container_name}"
469+ echo "## Installing dependencies in test container"
470+ install_packages_in_container "${container_name}" ${join_method_deps[${method}]}
471+}
472+
473+join_domain_realmd_winbind() {
474+ local server="${1}"
475+ local discover_cmd="realm discover -v --membership-software=samba --client-software=winbind ${realm,,}"
476+ local join_cmd="realm join -v --membership-software=samba --client-software=winbind ${realm,,}"
477+
478+ echo "## Domain information"
479+ lxc exec "${server}" -- ${discover_cmd}
480+ echo
481+ echo "## Running join command: ${join_cmd}"
482+ echo "${adminpass}" | lxc exec "${server}" -- ${join_cmd}
483+ # LP: #1980246
484+ # So far, only lunar and later automatically add winbind to /etc/nsswitch.conf.
485+ lxc exec "${server}" -- sed -r -i \
486+ -e '/^(passwd|group):.*[[:space:]]winbind\b/b' \
487+ -e 's/^(passwd|group):.*/& winbind/' \
488+ /etc/nsswitch.conf
489+}
490+
491+verify_join_realmd_winbind() {
492+ local server="${1}"
493+ local member_domain
494+
495+ echo -n "## Verifying member server joined domain name: "
496+ member_domain=$(lxc exec "${server}" -- wbinfo --own-domain)
497+ echo "${member_domain}"
498+ if [ "${member_domain}" != "${domain}" ]; then
499+ echo "ERROR: expected member server domain to match the joined domain:"
500+ echo "member server domain: ${member_domain}"
501+ echo "AD domain: ${domain}"
502+ return 1
503+ fi
504+ echo
505+ # we just want to see the output, not parse it
506+ echo "## Domain status in member server"
507+ lxc exec "${server}" -- wbinfo --domain-info "${member_domain}"
508+ echo
509+ echo "## User status in member server"
510+ for u in "${!user_pass[@]}"; do
511+ echo "## User \"${u}@${realm}\" information:"
512+ lxc exec "${server}" -- wbinfo --user-info "${u}@${realm}"
513+ echo
514+ echo "## id ${u}@${realm}"
515+ lxc exec "${server}" -- id ${u}@${realm}
516+ echo
517+ echo "## kinit authentication check for user \"${u}@${realm}\" inside member server"
518+ echo "${user_pass[${u}]}" | lxc exec "${server}" -- timeout --verbose 30 kinit "${u}@${realm}"
519+ lxc exec "${server}" -- klist
520+ echo
521+ echo "## Listing shares with the obtained kerberos ticket"
522+ lxc exec "${server}" -- smbclient -L "$(hostname)" --use-kerberos=required -k
523+ lxc exec "${server}" -- kdestroy
524+ echo
525+ echo "## wbinfo authentication check for user \"${u}@${realm}\" inside member server"
526+ # non-interactive format for username is user%password
527+ lxc exec "${server}" -- wbinfo --authenticate="${u}@${realm}%${user_pass[${u}]}"
528+ echo
529+ echo "## wbinfo kerberos authentication check for user \"${u}@${realm}\" inside member server"
530+ lxc exec "${server}" -- wbinfo --krb5auth="${u}@${realm}%${user_pass[${u}]}"
531+ echo
532+ echo "## Listing shares with the obtained kerberos ticket"
533+ lxc exec "${server}" -- smbclient -L "$(hostname)" --use-kerberos=required -k
534+ lxc exec "${server}" -- kdestroy
535+ done
536+}
537+
538+leave_domain_realmd_winbind() {
539+ local server="${1}"
540+ local leave_cmd="realm leave -v --remove --client-software=winbind"
541+
542+ echo "## Running leave command: ${leave_cmd}"
543+ echo "${adminpass}" | lxc exec "${server}" -- ${leave_cmd}
544+}
545+
546+join_domain_realmd_sssd() {
547+ local server="${1}"
548+ local discover_cmd="realm discover -v --membership-software=adcli --client-software=sssd ${realm,,}"
549+ local join_cmd="realm join -v --membership-software=adcli --client-software=sssd ${realm,,}"
550+
551+ echo "## Domain information"
552+ lxc exec "${server}" -- ${discover_cmd}
553+ echo
554+ echo "## Running join command: ${join_cmd}"
555+ echo "${adminpass}" | lxc exec "${server}" -- ${join_cmd}
556+ echo
557+}
558+
559+verify_join_realmd_sssd() {
560+ local server="${1}"
561+ local samba_domain
562+
563+ echo -n "## Verifying member server joined domain name: "
564+ samba_domain=$(lxc exec "${server}" -- sssctl domain-list)
565+ echo "${samba_domain}"
566+ if [ "${samba_domain}" != "${realm,,}" ]; then
567+ echo "ERROR: expected member server domain to match the joined domain:"
568+ echo "member server domain: ${samba_domain}"
569+ echo "AD domain: ${realm,,}"
570+ return 1
571+ fi
572+ echo
573+ # we just want to see the output, not parse it
574+ echo "## Domain status in member server"
575+ lxc exec "${server}" -- sssctl domain-status "${realm}"
576+ echo
577+ echo "## User status in member server"
578+ for u in "${!user_pass[@]}"; do
579+ echo "## User \"${u}@${realm}\" information:"
580+ lxc exec "${server}" -- sssctl user-checks "${u}@${realm}"
581+ echo
582+ echo "## id ${u}@${realm}"
583+ lxc exec "${server}" -- id "${u}@${realm}"
584+ echo
585+ echo "## kinit authentication check for user \"${u}@${realm}\" inside member server"
586+ echo "${user_pass[${u}]}" | lxc exec "${server}" -- timeout --verbose 30 kinit "${u}@${realm}"
587+ lxc exec "${server}" -- klist
588+ echo
589+ echo "## Listing shares with the obtained kerberos ticket"
590+ lxc exec "${server}" -- smbclient -L "$(hostname)" --use-kerberos=required -k
591+ lxc exec "${server}" -- kdestroy
592+ done
593+}
594+
595+leave_domain_realmd_sssd() {
596+ local server="${1}"
597+ local leave_cmd="realm leave -v --remove --client-software=sssd"
598+
599+ echo "## Running leave command: ${leave_cmd}"
600+ echo "${adminpass}" | lxc exec "${server}" -- ${leave_cmd}
601+}
602+
603+join_domain() {
604+ local server="${1}"
605+ local m="${2}"
606+
607+ join_domain_${m} "${server}"
608+}
609+
610+verify_join() {
611+ local server="${1}"
612+ local m="${2}"
613+
614+ verify_join_${m} "${server}"
615+}
616+
617+leave_domain() {
618+ local server="${1}"
619+ local m="${2}"
620+
621+ leave_domain_${m} "${server}"
622+}
623+
624+systemctl stop smbd nmbd winbind
625+systemctl disable smbd nmbd winbind
626+systemctl mask smbd nmbd winbind
627+
628+systemctl unmask samba-ad-dc
629+systemctl enable samba-ad-dc
630+
631+if [ -f /etc/samba/smb.conf ]; then
632+ mv /etc/samba/smb.conf{,.orig}
633+fi
634+
635+# make sure we are starting fresh, as previous tests might left things around
636+
637+rm -rf /var/lib/samba/* /var/cache/samba/* /run/samba/*
638+kdestroy || :
639+
640+samba-tool domain provision \
641+ --domain="${domain}" \
642+ --realm="${realm}" \
643+ --adminpass="${adminpass}" \
644+ --server-role=dc \
645+ --use-rfc2307 \
646+ --dns-backend=SAMBA_INTERNAL
647+
648+current_dns=$(resolvectl status | grep "^Current DNS Server:" | awk '{print $4}')
649+
650+if [ -n "${current_dns}" ]; then
651+ echo "## Setting dns forwarder to ${current_dns} in smb.conf"
652+ sed -r -i "s,dns forwarder = .*,dns forwarder = ${current_dns}," \
653+ /etc/samba/smb.conf
654+ unlink /etc/resolv.conf
655+ echo "nameserver 127.0.0.1" > /etc/resolv.conf
656+ # lowercase substitution
657+ echo "search ${realm,,}" >> /etc/resolv.conf
658+ systemctl stop systemd-resolved
659+ systemctl disable systemd-resolved
660+else
661+ echo "## Warning, couldn't detect the current DNS server to use as forwarder in smb.conf"
662+ echo "## resolvectl status:"
663+ resolvectl status
664+ echo "## Continuing, and hoping for the best"
665+fi
666+
667+cp -f /var/lib/samba/private/krb5.conf /etc/krb5.conf
668+
669+systemctl start samba-ad-dc
670+
671+# give it some time, it's a lot of services to start
672+sleep 5s
673+
674+basic_config_tests
675+dns_tests
676+user_creation_tests
677+smbclient_tests
678+server_join_tests
679diff --git a/debian/tests/util b/debian/tests/util
680index 87a2ccd..af7a0aa 100644
681--- a/debian/tests/util
682+++ b/debian/tests/util
683@@ -16,7 +16,7 @@ EOFEOF
684 if [ -n "${vfs}" ]; then
685 echo "vfs objects = ${vfs}" >> /etc/samba/smb.conf
686 fi
687- systemctl restart smbd.service
688+ systemctl reload smbd.service
689 else
690 echo "Share [${share}] already exists, continuing"
691 fi
692@@ -63,3 +63,113 @@ check_kernel_version() {
693 return 1
694 fi
695 }
696+
697+wait_container_ready() {
698+ local container="${1}"
699+ local -i limit=120 # seconds
700+ local -i i=0
701+ local -i result=0
702+ local ip
703+ local output
704+
705+ while /bin/true; do
706+ ip=$(lxc list "${container}" -c 4 --format=compact | tail -1 | awk '{print $1}')
707+ if [ -n "${ip}" ]; then
708+ break
709+ fi
710+ i=$((i+1))
711+ if [ ${i} -ge ${limit} ]; then
712+ return 1
713+ fi
714+ sleep 1s
715+ echo -n "."
716+ done
717+ while ! nc -z "${ip}" 22; do
718+ echo -n "."
719+ i=$((i+1))
720+ if [ ${i} -ge ${limit} ]; then
721+ return 1
722+ fi
723+ sleep 1s
724+ done
725+ # cloud-init might still be doing things...
726+ # this call blocks, so wrap it in its own little timeout
727+ output=$(lxc exec "${container}" -- timeout --verbose $((limit-i)) cloud-init status --wait) || {
728+ result=$?
729+ echo "cloud-init status --wait failed on container ${container}"
730+ echo "${output}"
731+ return ${result}
732+ }
733+ echo
734+}
735+
736+install_lxd() {
737+ if ! command -v lxd > /dev/null 2>&1; then
738+ # the test depends has "lxd | snapd", so if we don't have lxd, we must
739+ # install the snap
740+ snap list lxd > /dev/null 2>&1 || {
741+ echo "Installing the LXD snap..."
742+ snap install lxd
743+ }
744+ fi
745+}
746+
747+setup_lxd() {
748+ local dns_domain="${1}"
749+ local network
750+ local nic
751+ local dns_ip
752+
753+ install_lxd
754+ # Stop samba while lxd is setup, to avoid conflicts on lxdbr0:53
755+ systemctl stop samba-ad-dc
756+ lxd init --auto
757+ lxd waitready --timeout 600
758+ network=$(lxc network list --format=compact | grep -E "bridge.*YES.*CREATED")
759+ nic=$(echo "${network}" | awk '{print $1}')
760+ dns_ip=$(echo "${network}" | awk '{print $4}' | cut -d / -f 1) # strip the cidr
761+ # port=0 effectively disables dnsmasq's DNS, so it doesn't conflict with samba's DNS
762+ lxc network set "${nic:-lxdbr0}" ipv6.address=none dns.domain="${dns_domain}" raw.dnsmasq="$(echo -e port=0\\ndhcp-option=option:dns-server,${dns_ip})"
763+ if [ -n "${http_proxy}" ]; then
764+ lxc config set core.proxy_http "${http_proxy}"
765+ fi
766+ if [ -n "${https_proxy}" ]; then
767+ lxc config set core.proxy_https "${https_proxy}"
768+ fi
769+ if [ -n "${noproxy}" ]; then
770+ lxc config set core.proxy_ignore_hosts "${noproxy}"
771+ fi
772+ systemctl start samba-ad-dc
773+ # give it some time, it's a lot of services to start
774+ sleep 5s
775+}
776+
777+# Copy the local apt package archive over to the lxd container.
778+copy_local_apt_files() {
779+ local container_name="${1:-docker}"
780+
781+ for local_source in $(apt-get indextargets | grep-dctrl -F URI -e '^file:/' -sURI | awk '{print $2}'); do
782+ local_source=${local_source#file:}
783+ local_dir=$(dirname "${local_source}")
784+ lxc exec "${container_name}" -- mkdir -p "${local_dir}"
785+ tar -cC "${local_dir}" . | lxc exec "${container_name}" -- tar -xC "${local_dir}"
786+ done
787+}
788+
789+send_apt_config() {
790+ echo "Copying over /etc/apt to container ${1}"
791+ lxc exec "${1}" -- rm -rf /etc/apt
792+ lxc exec "${1}" -- mkdir -p /etc/apt
793+ tar -cC /etc/apt . | lxc exec "${1}" -- tar -xC /etc/apt
794+}
795+
796+install_packages_in_container() {
797+ local container="${1}"
798+ shift
799+ local packages="${*}"
800+
801+ echo "### Installing dependencies in member server container: ${packages}"
802+ lxc exec "${container}" --env DEBIAN_FRONTEND=noninteractive -- apt-get update -q
803+ lxc exec "${container}" --env DEBIAN_FRONTEND=noninteractive -- apt-get dist-upgrade -q -y
804+ lxc exec "${container}" --env DEBIAN_FRONTEND=noninteractive -- apt-get install -q -y ${packages}
805+}

Subscribers

People subscribed via source and target branches