[SCM] Samba Shared Repository - branch master updated
Stefan Metzmacher
metze at samba.org
Fri Aug 17 08:35:03 MDT 2012
The branch, master has been updated
via 1b487ad s3:selftest: add some tests against a share the requires encryption
via 45471f4 s3:smb2_negprot: annouce/negotiate SMB3 encryption support
via 9397d67 s3:smb2_server: add SMB3 encryption support
via 9f1dfd8 s3:smbd: don't disconnect the client when a share has "smb encrypt = required"
via e5d4e8d s3:smbd: lp_smb_encrypt() returns SMB_SIGNING_* values
via 8b3da9a s3:smbd: make use of ENCRYPTION_REQUIRED()
via abf018e libcli/smb: make sure the SMB2_TRANSFORM pdu is complete
via e2b07c0 s4:libcli/smb2: reset trsnport->compound.related when a compound chain is finished
from 6ce362a build: Ensure -Werror=format works with -Wformat=2 on NULL format strings
http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master
- Log -----------------------------------------------------------------
commit 1b487ad3d7f709b0a100ccdc6fc30dcf7d0b778c
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 08:50:21 2012 +0200
s3:selftest: add some tests against a share the requires encryption
metze
Autobuild-User(master): Stefan Metzmacher <metze at samba.org>
Autobuild-Date(master): Fri Aug 17 16:34:26 CEST 2012 on sn-devel-104
commit 45471f4d8f80d80c01197536bcf47d932dcd38e0
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Aug 8 07:07:53 2012 +0200
s3:smb2_negprot: annouce/negotiate SMB3 encryption support
metze
commit 9397d6709f79f2e8837401d32cd7ac584b6c5b24
Author: Stefan Metzmacher <metze at samba.org>
Date: Wed Aug 8 07:07:03 2012 +0200
s3:smb2_server: add SMB3 encryption support
metze
commit 9f1dfd8facaa59370afd93e89cc729de5cc3d9ba
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 09:42:27 2012 +0200
s3:smbd: don't disconnect the client when a share has "smb encrypt = required"
It's not the client fault, if he doesn't know that encryption is required.
We should just return ACCESS_DENIED and let the client work on other
shares and open files on the current SMB connection.
metze
commit e5d4e8df6b8186b71aa72dd7817f5579b44fee2f
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 09:40:52 2012 +0200
s3:smbd: lp_smb_encrypt() returns SMB_SIGNING_* values
metze
commit 8b3da9a1f400040eef14b63ed0b7884a9e82d907
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 09:41:42 2012 +0200
s3:smbd: make use of ENCRYPTION_REQUIRED()
metze
commit abf018e8b64b237aa029978c20bd418524fff3d0
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 08:31:52 2012 +0200
libcli/smb: make sure the SMB2_TRANSFORM pdu is complete
metze
commit e2b07c0adca680d73f20744fd8dbbcb8be818ca3
Author: Stefan Metzmacher <metze at samba.org>
Date: Fri Aug 17 08:25:08 2012 +0200
s4:libcli/smb2: reset trsnport->compound.related when a compound chain is finished
metze
-----------------------------------------------------------------------
Summary of changes:
libcli/smb/smbXcli_base.c | 15 ++-
selftest/knownfail | 5 +
selftest/target/Samba3.pm | 4 +
selftest/target/Samba4.pm | 4 +
source3/include/smb_macros.h | 2 +-
source3/param/loadparm.c | 2 +-
source3/selftest/tests.py | 9 +-
source3/smbd/globals.h | 52 ++++--
source3/smbd/process.c | 10 +-
source3/smbd/smb2_negprot.c | 8 +
source3/smbd/smb2_server.c | 350 +++++++++++++++++++++++++++++++++++----
source3/smbd/trans2.c | 20 +--
source4/libcli/smb2/transport.c | 1 +
13 files changed, 412 insertions(+), 70 deletions(-)
Changeset truncated at 500 lines:
diff --git a/libcli/smb/smbXcli_base.c b/libcli/smb/smbXcli_base.c
index a9adcbb..02d0227 100644
--- a/libcli/smb/smbXcli_base.c
+++ b/libcli/smb/smbXcli_base.c
@@ -3041,6 +3041,7 @@ static NTSTATUS smb2cli_inbuf_parse_compound(struct smbXcli_conn *conn,
struct smbXcli_session *s;
uint64_t uid;
struct iovec tf_iov[2];
+ size_t enc_len;
NTSTATUS status;
if (len < SMB2_TF_HDR_SIZE) {
@@ -3053,9 +3054,16 @@ static NTSTATUS smb2cli_inbuf_parse_compound(struct smbXcli_conn *conn,
taken += tf_len;
hdr = first_hdr + taken;
- len = IVAL(tf, SMB2_TF_MSG_SIZE);
+ enc_len = IVAL(tf, SMB2_TF_MSG_SIZE);
uid = BVAL(tf, SMB2_TF_SESSION_ID);
+ if (len < SMB2_TF_HDR_SIZE + enc_len) {
+ DEBUG(10, ("%d bytes left, expected at least %d\n",
+ (int)len,
+ (int)(SMB2_TF_HDR_SIZE + enc_len)));
+ goto inval;
+ }
+
s = conn->sessions;
for (; s; s = s->next) {
if (s->smb2->session_id != uid) {
@@ -3073,7 +3081,7 @@ static NTSTATUS smb2cli_inbuf_parse_compound(struct smbXcli_conn *conn,
tf_iov[0].iov_base = (void *)tf;
tf_iov[0].iov_len = tf_len;
tf_iov[1].iov_base = (void *)hdr;
- tf_iov[1].iov_len = len;
+ tf_iov[1].iov_len = enc_len;
status = smb2_signing_decrypt_pdu(s->smb2->decryption_key,
conn->protocol,
@@ -3083,7 +3091,8 @@ static NTSTATUS smb2cli_inbuf_parse_compound(struct smbXcli_conn *conn,
return status;
}
- verified_buflen = taken + len;
+ verified_buflen = taken + enc_len;
+ len = enc_len;
}
/*
diff --git a/selftest/knownfail b/selftest/knownfail
index da3d93c..9376264 100644
--- a/selftest/knownfail
+++ b/selftest/knownfail
@@ -21,6 +21,11 @@
^samba3.smbtorture_s3.plain\(dc\).BAD-NBT-SESSION # Fails against the s4 ntvfs server
^samba3.smbtorture_s3.plain\(dc\).SMB2-SESSION-REAUTH # Fails against the s4 ntvfs server
^samba3.smbtorture_s3.plain\(dc\).SMB2-SESSION-RECONNECT # Fails against the s4 ntvfs server
+ ^samba3.smbtorture_s3.crypt_server\(s3dc\).SMB2-SESSION-REAUTH # expected to give ACCESS_DENIED SMB2.1 doesn't have encryption
+^samba3.smbtorture_s3.crypt_server\(s3dc\).SMB2-SESSION-RECONNECT # expected to give CONNECTION_DISCONNECTED, we need to fix the test
+^samba3.smb2.session enc.reconnect # expected to give CONNECTION_DISCONNECTED, we need to fix the test
+^samba3.raw.session enc # expected to give ACCESS_DENIED as SMB1 encryption isn't used
+^samba3.smbtorture_s3.crypt_server # expected to give ACCESS_DENIED as SMB1 encryption isn't used
^samba3.nbt.dgram.*netlogon2\(s3dc\)
^samba3.*rap.sam.*.useradd # Not provided by Samba 3
^samba3.*rap.sam.*.userdelete # Not provided by Samba 3
diff --git a/selftest/target/Samba3.pm b/selftest/target/Samba3.pm
index 149a31e..72b9c19 100755
--- a/selftest/target/Samba3.pm
+++ b/selftest/target/Samba3.pm
@@ -939,6 +939,10 @@ sub provision($$$$$$)
[tmp]
path = $shrdir
comment = smb username is [%U]
+[tmpenc]
+ path = $shrdir
+ comment = encrypt smb username is [%U]
+ smb encrypt = required
[tmpguest]
path = $shrdir
guest ok = yes
diff --git a/selftest/target/Samba4.pm b/selftest/target/Samba4.pm
index b1998a6..17afab2 100644
--- a/selftest/target/Samba4.pm
+++ b/selftest/target/Samba4.pm
@@ -1385,6 +1385,10 @@ sub provision_plugin_s4_dc($$)
my $extra_smbconf_shares = "
+[tmpenc]
+ copy = tmp
+ smb encrypt = required
+
[tmpcase]
copy = tmp
case sensitive = yes
diff --git a/source3/include/smb_macros.h b/source3/include/smb_macros.h
index 73f8fb3..8b9d941 100644
--- a/source3/include/smb_macros.h
+++ b/source3/include/smb_macros.h
@@ -139,7 +139,7 @@
#define smb_len_large(buf) smb_len_tcp(buf)
#define _smb_setlen_large(buf, len) _smb_setlen_tcp(buf, len)
-#define ENCRYPTION_REQUIRED(conn) ((conn) ? ((conn)->encrypt_level == Required) : false)
+#define ENCRYPTION_REQUIRED(conn) ((conn) ? ((conn)->encrypt_level == SMB_SIGNING_REQUIRED) : false)
#define IS_CONN_ENCRYPTED(conn) ((conn) ? (conn)->encrypted_tid : false)
/****************************************************************************
diff --git a/source3/param/loadparm.c b/source3/param/loadparm.c
index d7141ae..bce1c5b 100644
--- a/source3/param/loadparm.c
+++ b/source3/param/loadparm.c
@@ -281,7 +281,7 @@ static struct loadparm_service sDefault =
#else
.iDirectoryNameCacheSize = 100,
#endif
- .ismb_encrypt = Auto,
+ .ismb_encrypt = SMB_SIGNING_DEFAULT,
.param_opt = NULL,
.dummy = ""
};
diff --git a/source3/selftest/tests.py b/source3/selftest/tests.py
index 00ecd6c..f9f2e22 100755
--- a/source3/selftest/tests.py
+++ b/source3/selftest/tests.py
@@ -95,7 +95,11 @@ tests=[ "FDPASS", "LOCK1", "LOCK2", "LOCK3", "LOCK4", "LOCK5", "LOCK6", "LOCK7",
for t in tests:
plantestsuite("samba3.smbtorture_s3.plain(s3dc).%s" % t, "s3dc", [os.path.join(samba3srcdir, "script/tests/test_smbtorture_s3.sh"), t, '//$SERVER_IP/tmp', '$USERNAME', '$PASSWORD', smbtorture3, "", "-l $LOCAL_PATH"])
- plantestsuite("samba3.smbtorture_s3.crypt(s3dc).%s" % t, "s3dc", [os.path.join(samba3srcdir, "script/tests/test_smbtorture_s3.sh"), t, '//$SERVER_IP/tmp', '$USERNAME', '$PASSWORD', smbtorture3, "-e", "-l $LOCAL_PATH"])
+ plantestsuite("samba3.smbtorture_s3.crypt_client(s3dc).%s" % t, "s3dc", [os.path.join(samba3srcdir, "script/tests/test_smbtorture_s3.sh"), t, '//$SERVER_IP/tmp', '$USERNAME', '$PASSWORD', smbtorture3, "-e", "-l $LOCAL_PATH"])
+ if t == "TORTURE":
+ # this is a negative test to verify that the server rejects
+ # access without encryption
+ plantestsuite("samba3.smbtorture_s3.crypt_server(s3dc).%s" % t, "s3dc", [os.path.join(samba3srcdir, "script/tests/test_smbtorture_s3.sh"), t, '//$SERVER_IP/tmpenc', '$USERNAME', '$PASSWORD', smbtorture3, "", "-l $LOCAL_PATH"])
plantestsuite("samba3.smbtorture_s3.plain(dc).%s" % t, "dc", [os.path.join(samba3srcdir, "script/tests/test_smbtorture_s3.sh"), t, '//$SERVER_IP/tmp', '$USERNAME', '$PASSWORD', smbtorture3, "", "-l $LOCAL_PATH"])
posix_tests=[ "POSIX", "POSIX-APPEND"]
@@ -333,7 +337,8 @@ for t in tests:
plansmbtorturetestsuite(t, "secshare", '//$SERVER_IP/tmp -U$USERNAME%$PASSWORD')
plansmbtorturetestsuite(t, "plugin_s4_dc", '//$SERVER/tmp -U$USERNAME%$PASSWORD')
elif t == "raw.session" or t == "smb2.session":
- plansmbtorturetestsuite(t, "s3dc", '//$SERVER_IP/tmp -U$USERNAME%$PASSWORD')
+ plansmbtorturetestsuite(t, "s3dc", '//$SERVER_IP/tmp -U$USERNAME%$PASSWORD', 'plain')
+ plansmbtorturetestsuite(t, "s3dc", '//$SERVER_IP/tmpenc -U$USERNAME%$PASSWORD', 'enc')
plansmbtorturetestsuite(t, "plugin_s4_dc", '//$SERVER/tmp -k no -U$USERNAME%$PASSWORD', 'ntlm')
plansmbtorturetestsuite(t, "plugin_s4_dc", '//$SERVER/tmp -k yes -U$USERNAME%$PASSWORD', 'krb5')
elif t == "rpc.lsa":
diff --git a/source3/smbd/globals.h b/source3/smbd/globals.h
index ac8a1b2..b024fb3 100644
--- a/source3/smbd/globals.h
+++ b/source3/smbd/globals.h
@@ -462,7 +462,12 @@ struct smbd_smb2_request {
bool compound_related;
/*
- * the signing/encryption key for the last
+ * the encryption key for the whole
+ * compound chain
+ */
+ DATA_BLOB first_key;
+ /*
+ * the signing key for the last
* request/response of a compound chain
*/
DATA_BLOB last_key;
@@ -481,15 +486,18 @@ struct smbd_smb2_request {
*/
struct tevent_req *subreq;
-#define SMBD_SMB2_HDR_IOV_OFS 0
-#define SMBD_SMB2_BODY_IOV_OFS 1
-#define SMBD_SMB2_DYN_IOV_OFS 2
+#define SMBD_SMB2_TF_IOV_OFS 0
+#define SMBD_SMB2_HDR_IOV_OFS 1
+#define SMBD_SMB2_BODY_IOV_OFS 2
+#define SMBD_SMB2_DYN_IOV_OFS 3
-#define SMBD_SMB2_NUM_IOV_PER_REQ 3
+#define SMBD_SMB2_NUM_IOV_PER_REQ 4
#define SMBD_SMB2_IOV_IDX_OFS(req,dir,idx,ofs) \
(&req->dir.vector[(idx)+(ofs)])
+#define SMBD_SMB2_IDX_TF_IOV(req,dir,idx) \
+ SMBD_SMB2_IOV_IDX_OFS(req,dir,idx,SMBD_SMB2_TF_IOV_OFS)
#define SMBD_SMB2_IDX_HDR_IOV(req,dir,idx) \
SMBD_SMB2_IOV_IDX_OFS(req,dir,idx,SMBD_SMB2_HDR_IOV_OFS)
#define SMBD_SMB2_IDX_BODY_IOV(req,dir,idx) \
@@ -497,6 +505,8 @@ struct smbd_smb2_request {
#define SMBD_SMB2_IDX_DYN_IOV(req,dir,idx) \
SMBD_SMB2_IOV_IDX_OFS(req,dir,idx,SMBD_SMB2_DYN_IOV_OFS)
+#define SMBD_SMB2_IN_TF_IOV(req) SMBD_SMB2_IDX_TF_IOV(req,in,req->current_idx)
+#define SMBD_SMB2_IN_TF_PTR(req) (uint8_t *)(SMBD_SMB2_IN_TF_IOV(req)->iov_base)
#define SMBD_SMB2_IN_HDR_IOV(req) SMBD_SMB2_IDX_HDR_IOV(req,in,req->current_idx)
#define SMBD_SMB2_IN_HDR_PTR(req) (uint8_t *)(SMBD_SMB2_IN_HDR_IOV(req)->iov_base)
#define SMBD_SMB2_IN_BODY_IOV(req) SMBD_SMB2_IDX_BODY_IOV(req,in,req->current_idx)
@@ -506,6 +516,8 @@ struct smbd_smb2_request {
#define SMBD_SMB2_IN_DYN_PTR(req) (uint8_t *)(SMBD_SMB2_IN_DYN_IOV(req)->iov_base)
#define SMBD_SMB2_IN_DYN_LEN(req) (SMBD_SMB2_IN_DYN_IOV(req)->iov_len)
+#define SMBD_SMB2_OUT_TF_IOV(req) SMBD_SMB2_IDX_TF_IOV(req,out,req->current_idx)
+#define SMBD_SMB2_OUT_TF_PTR(req) (uint8_t *)(SMBD_SMB2_OUT_TF_IOV(req)->iov_base)
#define SMBD_SMB2_OUT_HDR_IOV(req) SMBD_SMB2_IDX_HDR_IOV(req,out,req->current_idx)
#define SMBD_SMB2_OUT_HDR_PTR(req) (uint8_t *)(SMBD_SMB2_OUT_HDR_IOV(req)->iov_base)
#define SMBD_SMB2_OUT_BODY_IOV(req) SMBD_SMB2_IDX_BODY_IOV(req,out,req->current_idx)
@@ -517,17 +529,19 @@ struct smbd_smb2_request {
struct {
/*
- * vector[0] TRANSPORT HEADER
+ * vector[0] TRANSPORT HEADER (empty)
* .
- * vector[1] SMB2
- * vector[2] fixed body
- * vector[3] dynamic body
+ * vector[1] SMB2_TRANSFORM (optional)
+ * vector[2] SMB2
+ * vector[3] fixed body
+ * vector[4] dynamic body
* .
* .
* .
- * vector[4] SMB2
- * vector[5] fixed body
- * vector[6] dynamic body
+ * vector[5] SMB2_TRANSFORM (optional)
+ * vector[6] SMB2
+ * vector[7] fixed body
+ * vector[8] dynamic body
* .
* .
* .
@@ -541,15 +555,17 @@ struct smbd_smb2_request {
/*
* vector[0] TRANSPORT HEADER
* .
- * vector[1] SMB2
- * vector[2] fixed body
- * vector[3] dynamic body
+ * vector[1] SMB2_TRANSFORM (optional)
+ * vector[2] SMB2
+ * vector[3] fixed body
+ * vector[4] dynamic body
* .
* .
* .
- * vector[4] SMB2
- * vector[5] fixed body
- * vector[6] dynamic body
+ * vector[5] SMB2_TRANSFORM (empty)
+ * vector[6] SMB2
+ * vector[7] fixed body
+ * vector[8] dynamic body
* .
* .
* .
diff --git a/source3/smbd/process.c b/source3/smbd/process.c
index dd26a27..fd2c6a4 100644
--- a/source3/smbd/process.c
+++ b/source3/smbd/process.c
@@ -1492,11 +1492,15 @@ static connection_struct *switch_message(uint8 type, struct smb_request *req)
if (req->encrypted) {
conn->encrypted_tid = true;
/* encrypted required from now on. */
- conn->encrypt_level = Required;
+ conn->encrypt_level = SMB_SIGNING_REQUIRED;
} else if (ENCRYPTION_REQUIRED(conn)) {
if (req->cmd != SMBtrans2 && req->cmd != SMBtranss2) {
- exit_server_cleanly("encryption required "
- "on connection");
+ DEBUG(1,("service[%s] requires encryption"
+ "%s ACCESS_DENIED. mid=%llu\n",
+ lp_servicename(talloc_tos(), SNUM(conn)),
+ smb_fn_name(type),
+ (unsigned long long)req->mid));
+ reply_nterror(req, NT_STATUS_ACCESS_DENIED);
return conn;
}
}
diff --git a/source3/smbd/smb2_negprot.c b/source3/smbd/smb2_negprot.c
index d086566..11ec2a5 100644
--- a/source3/smbd/smb2_negprot.c
+++ b/source3/smbd/smb2_negprot.c
@@ -254,6 +254,14 @@ NTSTATUS smbd_smb2_request_process_negprot(struct smbd_smb2_request *req)
capabilities |= SMB2_CAP_DFS;
}
+ if ((protocol >= PROTOCOL_SMB2_24) &&
+ (lp_smb_encrypt(-1) != SMB_SIGNING_OFF))
+ {
+ if (in_capabilities & SMB2_CAP_ENCRYPTION) {
+ capabilities |= SMB2_CAP_ENCRYPTION;
+ }
+ }
+
/*
* 0x10000 (65536) is the maximum allowed message size
* for SMB 2.0
diff --git a/source3/smbd/smb2_server.c b/source3/smbd/smb2_server.c
index ff4ee60..106e6ac 100644
--- a/source3/smbd/smb2_server.c
+++ b/source3/smbd/smb2_server.c
@@ -256,6 +256,7 @@ static void smb2_setup_nbt_length(struct iovec *vector, int count)
static int smbd_smb2_request_destructor(struct smbd_smb2_request *req)
{
+ data_blob_clear_free(&req->first_key);
data_blob_clear_free(&req->last_key);
return 0;
}
@@ -303,6 +304,9 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
int num_iov = 1;
size_t taken = 0;
uint8_t *first_hdr = buf;
+ size_t verified_buflen = 0;
+ uint8_t *tf = NULL;
+ size_t tf_len = 0;
/*
* Note: index '0' is reserved for the transport protocol
@@ -324,6 +328,87 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
uint8_t *dyn = NULL;
struct iovec *iov_tmp;
+ if (verified_buflen > taken) {
+ len = verified_buflen - taken;
+ } else {
+ tf = NULL;
+ tf_len = 0;
+ }
+
+ if (len < 4) {
+ DEBUG(10, ("%d bytes left, expected at least %d\n",
+ (int)len, 4));
+ goto inval;
+ }
+ if (IVAL(hdr, 0) == SMB2_TF_MAGIC) {
+ struct smbXsrv_session *s = NULL;
+ uint64_t uid;
+ struct iovec tf_iov[2];
+ NTSTATUS status;
+ size_t enc_len;
+
+ if (conn->protocol < PROTOCOL_SMB2_24) {
+ DEBUG(10, ("Got SMB2_TRANSFORM header, "
+ "but dialect[0x%04X] is used\n",
+ conn->smb2.server.dialect));
+ goto inval;
+ }
+
+ if (!(conn->smb2.server.capabilities & SMB2_CAP_ENCRYPTION)) {
+ DEBUG(10, ("Got SMB2_TRANSFORM header, "
+ "but not negotiated "
+ "client[0x%08X] server[0x%08X]\n",
+ conn->smb2.client.capabilities,
+ conn->smb2.server.capabilities));
+ goto inval;
+ }
+
+ if (len < SMB2_TF_HDR_SIZE) {
+ DEBUG(1, ("%d bytes left, expected at least %d\n",
+ (int)len, SMB2_TF_HDR_SIZE));
+ goto inval;
+ }
+ tf = hdr;
+ tf_len = SMB2_TF_HDR_SIZE;
+ taken += tf_len;
+
+ hdr = first_hdr + taken;
+ enc_len = IVAL(tf, SMB2_TF_MSG_SIZE);
+ uid = BVAL(tf, SMB2_TF_SESSION_ID);
+
+ if (len < SMB2_TF_HDR_SIZE + enc_len) {
+ DEBUG(1, ("%d bytes left, expected at least %d\n",
+ (int)len,
+ (int)(SMB2_TF_HDR_SIZE + enc_len)));
+ goto inval;
+ }
+
+ status = smb2srv_session_lookup(conn, uid, now, &s);
+ if (s == NULL) {
+ DEBUG(1, ("invalid session[%llu] in "
+ "SMB2_TRANSFORM header\n",
+ (unsigned long long)uid));
+ TALLOC_FREE(iov);
+ return NT_STATUS_USER_SESSION_DELETED;
+ }
+
+ tf_iov[0].iov_base = (void *)tf;
+ tf_iov[0].iov_len = tf_len;
+ tf_iov[1].iov_base = (void *)hdr;
+ tf_iov[1].iov_len = enc_len;
+
+ status = smb2_signing_decrypt_pdu(s->global->decryption_key,
+ conn->protocol,
+ tf_iov, 2);
+ if (!NT_STATUS_IS_OK(status)) {
+ TALLOC_FREE(iov);
+ return status;
+ }
+
+ verified_buflen = taken + enc_len;
+ len = enc_len;
+ }
+
/*
* We need the header plus the body length field
*/
@@ -382,6 +467,8 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
cur = &iov[num_iov];
num_iov += SMBD_SMB2_NUM_IOV_PER_REQ;
+ cur[SMBD_SMB2_TF_IOV_OFS].iov_base = tf;
+ cur[SMBD_SMB2_TF_IOV_OFS].iov_len = tf_len;
cur[SMBD_SMB2_HDR_IOV_OFS].iov_base = hdr;
cur[SMBD_SMB2_HDR_IOV_OFS].iov_len = SMB2_HDR_BODY;
cur[SMBD_SMB2_BODY_IOV_OFS].iov_base = body;
@@ -891,6 +978,12 @@ static NTSTATUS smbd_smb2_request_setup_out(struct smbd_smb2_request *req)
outbody = outhdr + SMB2_HDR_BODY;
+ /*
+ * SMBD_SMB2_TF_IOV_OFS might be used later
+ */
+ current[SMBD_SMB2_TF_IOV_OFS].iov_base = NULL;
+ current[SMBD_SMB2_TF_IOV_OFS].iov_len = 0;
+
current[SMBD_SMB2_HDR_IOV_OFS].iov_base = (void *)outhdr;
current[SMBD_SMB2_HDR_IOV_OFS].iov_len = SMB2_HDR_BODY;
@@ -949,10 +1042,12 @@ void smbd_server_connection_terminate_ex(struct smbd_server_connection *sconn,
exit_server_cleanly(reason);
}
-static bool dup_smb2_vec3(TALLOC_CTX *ctx,
+static bool dup_smb2_vec4(TALLOC_CTX *ctx,
struct iovec *outvec,
const struct iovec *srcvec)
{
+ const uint8_t *srctf;
+ size_t srctf_len;
const uint8_t *srchdr;
size_t srchdr_len;
const uint8_t *srcbody;
@@ -961,10 +1056,13 @@ static bool dup_smb2_vec3(TALLOC_CTX *ctx,
const uint8_t *srcdyn;
size_t srcdyn_len;
const uint8_t *expected_srcdyn;
+ uint8_t *dsttf;
uint8_t *dsthdr;
uint8_t *dstbody;
uint8_t *dstdyn;
+ srctf = (const uint8_t *)srcvec[SMBD_SMB2_TF_IOV_OFS].iov_base;
+ srctf_len = srcvec[SMBD_SMB2_TF_IOV_OFS].iov_len;
srchdr = (const uint8_t *)srcvec[SMBD_SMB2_HDR_IOV_OFS].iov_base;
srchdr_len = srcvec[SMBD_SMB2_HDR_IOV_OFS].iov_len;
srcbody = (const uint8_t *)srcvec[SMBD_SMB2_BODY_IOV_OFS].iov_base;
@@ -974,10 +1072,25 @@ static bool dup_smb2_vec3(TALLOC_CTX *ctx,
srcdyn_len = srcvec[SMBD_SMB2_DYN_IOV_OFS].iov_len;
expected_srcdyn = srcbody + 8;
+ if ((srctf_len != SMB2_TF_HDR_SIZE) && (srctf_len != 0)) {
+ return false;
+ }
+
if (srchdr_len != SMB2_HDR_BODY) {
return false;
}
+ if (srctf_len == SMB2_TF_HDR_SIZE) {
+ dsttf = talloc_memdup(ctx, srctf, SMB2_TF_HDR_SIZE);
+ if (dsttf == NULL) {
+ return false;
+ }
+ } else {
+ dsttf = NULL;
+ }
+ outvec[SMBD_SMB2_TF_IOV_OFS].iov_base = (void *)dsttf;
+ outvec[SMBD_SMB2_TF_IOV_OFS].iov_len = srctf_len;
+
/* vec[SMBD_SMB2_HDR_IOV_OFS] is always boilerplate and must
* be allocated with size OUTVEC_ALLOC_SIZE. */
@@ -1061,7 +1174,7 @@ static struct smbd_smb2_request *dup_smb2_req(const struct smbd_smb2_request *re
/* Setup the vectors identically to the ones in req. */
for (i = 1; i < count; i += SMBD_SMB2_NUM_IOV_PER_REQ) {
- if (!dup_smb2_vec3(outvec, &outvec[i], &req->out.vector[i])) {
+ if (!dup_smb2_vec4(outvec, &outvec[i], &req->out.vector[i])) {
break;
}
}
@@ -1083,6 +1196,8 @@ static void smbd_smb2_request_writev_done(struct tevent_req *subreq);
static NTSTATUS smb2_send_async_interim_response(const struct smbd_smb2_request *req)
{
struct smbXsrv_connection *conn = req->sconn->conn;
+ int first_idx = 1;
--
Samba Shared Repository
More information about the samba-cvs
mailing list