[SCM] Samba Shared Repository - branch master updated

Jeremy Allison jra at samba.org
Wed Mar 5 17:00:04 MST 2014


The branch, master has been updated
       via  9869358 s3:smb2_server: avoid talloc_zero_array() in smbd_smb2_request_setup_out()
       via  cf77f16 s3:smb2_server: don't assume that req->out.vector is always a valid talloc pointer
       via  2edc730 s3:smb2_server: avoid talloc_zero_array() in smbd_smb2_request_error_ex()
       via  adaf517 s3:smb2_server: optimize smbd_smb2_generate_outbody() for the common case
       via  d307953 s3:smb2_write: make use of smbd_smb2_generate_outbody()
       via  ec8dedb s3:smb2_tcon: make use of smbd_smb2_generate_outbody()
       via  27222bb s3:smb2_setinfo: make use of smbd_smb2_generate_outbody()
       via  39832ff s3:smb2_sesssetup: make use of smbd_smb2_generate_outbody()
       via  c099797 s3:smb2_read: make use of smbd_smb2_generate_outbody()
       via  b065578 s3:smb2_notify: make use of smbd_smb2_generate_outbody()
       via  59c185b s3:smb2_negprot: make use of smbd_smb2_generate_outbody()
       via  aa70bf5 s3:smb2_lock: make use of smbd_smb2_generate_outbody()
       via  2ddfe40 s3:smb2_keepalive: make use of smbd_smb2_generate_outbody()
       via  a6ee7ce s3:smb2_ioctl: make use of smbd_smb2_generate_outbody()
       via  a021a25 s3:smb2_getinfo: make use of smbd_smb2_generate_outbody()
       via  46840db s3:smb2_flush: make use of smbd_smb2_generate_outbody()
       via  208046b s3:smb2_find: make use of smbd_smb2_generate_outbody()
       via  2c91f05 s3:smb2_create: make use of smbd_smb2_generate_outbody()
       via  2ecd5c9 s3:smb2_close: make use of smbd_smb2_generate_outbody()
       via  c09292e s3:smb2_break: make use of smbd_smb2_generate_outbody()
       via  fd4c82f s3:smb2_server: add smbd_smb2_generate_outbody() helper
       via  a6ce800 s3:smb2_read: avoid 2 talloc* calls when using sendfile()
       via  0ac924b s3:smb2_server: avoid a call to data_blob_clear_free() if not needed
       via  ec498a2 s3:smb2_server: optimize smbd_smb2_request_setup_out()
       via  66877df s3:smb2_server: optimize req->in.vector allocation
      from  032621d s3:smbd: s/BUFFER_SIZE/LARGE_WRITEX_BUFFER_SIZE

http://gitweb.samba.org/?p=samba.git;a=shortlog;h=master


- Log -----------------------------------------------------------------
commit 986935854f6ef4638d544054b9ed79f1d407bbf9
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 15:32:45 2013 +0100

    s3:smb2_server: avoid talloc_zero_array() in smbd_smb2_request_setup_out()
    
    In the common case with just one request, we can use a preallocated
    req->out.vector.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>
    
    Autobuild-User(master): Jeremy Allison <jra at samba.org>
    Autobuild-Date(master): Thu Mar  6 00:59:29 CET 2014 on sn-devel-104

commit cf77f16e3aa60258813b030f8a7f2e0cdd576368
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 15:28:11 2013 +0100

    s3:smb2_server: don't assume that req->out.vector is always a valid talloc pointer
    
    We use 'req' instead as it has the same lifetime.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 2edc7308d6185d724f38e602520617121ef57672
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 15:24:29 2013 +0100

    s3:smb2_server: avoid talloc_zero_array() in smbd_smb2_request_error_ex()
    
    It is only important that the content of info->data stays alive
    for the lifetime of the request, but the DATA_BLOB structure itself
    can be on the stack, while passing it as 'dyn' to smbd_smb2_request_done_ex().
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit adaf517c87db22cb5b74906d43cfbae74a07130c
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 15:05:34 2013 +0100

    s3:smb2_server: optimize smbd_smb2_generate_outbody() for the common case
    
    Use a preallocated buffer for the first response in the compound chain.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit d307953e08038cf4ba0367a85296d9f3b11d51d7
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_write: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit ec8dedb50f8be4c79b1018700b30f035a39650d3
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_tcon: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 27222bb4f47d72e2759aca83e471d50db6321a26
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_setinfo: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 39832ff588e4291df13307ab807130123768d3d6
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_sesssetup: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit c099797238e0671e2c816f9a71b06859595264aa
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_read: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit b065578320b51c8994ff01e79306640cabed1c6f
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_notify: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 59c185bf549b359728183c8e61c165823f6112ef
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_negprot: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit aa70bf5fdcfecf6966e7808d1837bbe134042d5b
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_lock: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 2ddfe40425366dce59b9a23d65044c6a6f93ec81
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_keepalive: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit a6ee7ce31a864db5a46bcf78d190f8955b95415c
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_ioctl: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit a021a25104aa570efd8b69920b26fc2dcc6b5c04
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_getinfo: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 46840db4160bfb4a908c08b065cd9130d63e2d86
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_flush: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 208046b2eb83ca4b5c30b9fa3da69efae439fee3
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_find: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 2c91f0506bca7936c4e25a8151a6b519c92faae9
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_create: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 2ecd5c9693a98b6baefabd915a4a44e8ac3fad37
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_close: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit c09292e20d8f1a6da6d5b56a1155abce4e02acf1
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 14:59:07 2013 +0100

    s3:smb2_break: make use of smbd_smb2_generate_outbody()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit fd4c82f6f50ebe02613c498c4f0070569e9ba10c
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 12:52:21 2013 +0100

    s3:smb2_server: add smbd_smb2_generate_outbody() helper
    
    We can add optimization there later.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit a6ce8001b4d022134e21cdf4c3180596a5a69101
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Dec 4 12:32:36 2013 +0100

    s3:smb2_read: avoid 2 talloc* calls when using sendfile()
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 0ac924b2bb3c256f10cde358b95ea1d8a3833972
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Nov 20 09:56:48 2013 +0100

    s3:smb2_server: avoid a call to data_blob_clear_free() if not needed
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit ec498a2414d96567bfed26f35b60ebe1ac40c68b
Author: Stefan Metzmacher <metze at samba.org>
Date:   Wed Nov 20 09:56:19 2013 +0100

    s3:smb2_server: optimize smbd_smb2_request_setup_out()
    
    We can use a preallocated buffer for the possible error
    response of the first response in the compound chain.
    
    This avoids a talloc_array_zero() call for the common case.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

commit 66877dfaa59561145eba6233dc1f43c282d8cd08
Author: Stefan Metzmacher <metze at samba.org>
Date:   Tue Nov 19 07:42:57 2013 +0100

    s3:smb2_server: optimize req->in.vector allocation
    
    We can avoid a talloc_zero_array() call in the
    common case (without compound requests) and use a
    preallocated array instead.
    
    Signed-off-by: Stefan Metzmacher <metze at samba.org>
    Reviewed-by: Jeremy Allison <jra at samba.org>

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

Summary of changes:
 source3/smbd/globals.h        |    7 ++
 source3/smbd/smb2_break.c     |    2 +-
 source3/smbd/smb2_close.c     |    2 +-
 source3/smbd/smb2_create.c    |    2 +-
 source3/smbd/smb2_find.c      |    2 +-
 source3/smbd/smb2_flush.c     |    2 +-
 source3/smbd/smb2_getinfo.c   |    2 +-
 source3/smbd/smb2_ioctl.c     |    2 +-
 source3/smbd/smb2_keepalive.c |    2 +-
 source3/smbd/smb2_lock.c      |    2 +-
 source3/smbd/smb2_negprot.c   |    2 +-
 source3/smbd/smb2_notify.c    |    2 +-
 source3/smbd/smb2_read.c      |   32 ++++++----
 source3/smbd/smb2_server.c    |  133 ++++++++++++++++++++++++++++------------
 source3/smbd/smb2_sesssetup.c |    4 +-
 source3/smbd/smb2_setinfo.c   |    2 +-
 source3/smbd/smb2_tcon.c      |    4 +-
 source3/smbd/smb2_write.c     |    2 +-
 18 files changed, 136 insertions(+), 70 deletions(-)


Changeset truncated at 500 lines:

diff --git a/source3/smbd/globals.h b/source3/smbd/globals.h
index bae3ed0..3baa048 100644
--- a/source3/smbd/globals.h
+++ b/source3/smbd/globals.h
@@ -225,6 +225,8 @@ void reply_smb20ff(struct smb_request *req, uint16_t choice);
 void smbd_smb2_first_negprot(struct smbd_server_connection *sconn,
 			     uint8_t *inbuf, size_t size);
 
+DATA_BLOB smbd_smb2_generate_outbody(struct smbd_smb2_request *req, size_t size);
+
 NTSTATUS smbd_smb2_request_error_ex(struct smbd_smb2_request *req,
 				    NTSTATUS status,
 				    DATA_BLOB *info,
@@ -586,6 +588,7 @@ struct smbd_smb2_request {
 		 */
 		struct iovec *vector;
 		int vector_count;
+		struct iovec _vector[1 + SMBD_SMB2_NUM_IOV_PER_REQ];
 	} in;
 	struct {
 		/* the NBT header is not allocated */
@@ -610,6 +613,10 @@ struct smbd_smb2_request {
 		 */
 		struct iovec *vector;
 		int vector_count;
+		struct iovec _vector[1 + SMBD_SMB2_NUM_IOV_PER_REQ];
+#define OUTVEC_ALLOC_SIZE (SMB2_HDR_BODY + 9)
+		uint8_t _hdr[OUTVEC_ALLOC_SIZE];
+		uint8_t _body[0x58];
 	} out;
 };
 
diff --git a/source3/smbd/smb2_break.c b/source3/smbd/smb2_break.c
index 945faa1..6446b79 100644
--- a/source3/smbd/smb2_break.c
+++ b/source3/smbd/smb2_break.c
@@ -106,7 +106,7 @@ static void smbd_smb2_request_oplock_break_done(struct tevent_req *subreq)
 	in_file_id_persistent	= BVAL(inbody, 0x08);
 	in_file_id_volatile	= BVAL(inbody, 0x10);
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x18);
+	outbody = smbd_smb2_generate_outbody(req, 0x18);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_close.c b/source3/smbd/smb2_close.c
index dce8cac..3712ffe 100644
--- a/source3/smbd/smb2_close.c
+++ b/source3/smbd/smb2_close.c
@@ -114,7 +114,7 @@ static void smbd_smb2_request_close_done(struct tevent_req *subreq)
 		return;
 	}
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x3C);
+	outbody = smbd_smb2_generate_outbody(req, 0x3C);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_create.c b/source3/smbd/smb2_create.c
index f2fec08..52ed171 100644
--- a/source3/smbd/smb2_create.c
+++ b/source3/smbd/smb2_create.c
@@ -318,7 +318,7 @@ static void smbd_smb2_request_create_done(struct tevent_req *tsubreq)
 		out_context_buffer_offset = SMB2_HDR_BODY + 0x58;
 	}
 
-	outbody = data_blob_talloc(smb2req->out.vector, NULL, 0x58);
+	outbody = smbd_smb2_generate_outbody(smb2req, 0x58);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(smb2req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_find.c b/source3/smbd/smb2_find.c
index 46d0aa4..3f779b8 100644
--- a/source3/smbd/smb2_find.c
+++ b/source3/smbd/smb2_find.c
@@ -162,7 +162,7 @@ static void smbd_smb2_request_find_done(struct tevent_req *subreq)
 
 	out_output_buffer_offset = SMB2_HDR_BODY + 0x08;
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x08);
+	outbody = smbd_smb2_generate_outbody(req, 0x08);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_flush.c b/source3/smbd/smb2_flush.c
index 00a7158..0d4c1a5 100644
--- a/source3/smbd/smb2_flush.c
+++ b/source3/smbd/smb2_flush.c
@@ -84,7 +84,7 @@ static void smbd_smb2_request_flush_done(struct tevent_req *subreq)
 		return;
 	}
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x04);
+	outbody = smbd_smb2_generate_outbody(req, 0x04);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_getinfo.c b/source3/smbd/smb2_getinfo.c
index 449aeb3..ec6181a 100644
--- a/source3/smbd/smb2_getinfo.c
+++ b/source3/smbd/smb2_getinfo.c
@@ -178,7 +178,7 @@ static void smbd_smb2_request_getinfo_done(struct tevent_req *subreq)
 
 	out_output_buffer_offset = SMB2_HDR_BODY + 0x08;
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x08);
+	outbody = smbd_smb2_generate_outbody(req, 0x08);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_ioctl.c b/source3/smbd/smb2_ioctl.c
index be2a798..6a19fcb 100644
--- a/source3/smbd/smb2_ioctl.c
+++ b/source3/smbd/smb2_ioctl.c
@@ -318,7 +318,7 @@ static void smbd_smb2_request_ioctl_done(struct tevent_req *subreq)
 	out_input_offset = SMB2_HDR_BODY + 0x30;
 	out_output_offset = SMB2_HDR_BODY + 0x30;
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x30);
+	outbody = smbd_smb2_generate_outbody(req, 0x30);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_keepalive.c b/source3/smbd/smb2_keepalive.c
index 24a4f8e..b16ff6b 100644
--- a/source3/smbd/smb2_keepalive.c
+++ b/source3/smbd/smb2_keepalive.c
@@ -35,7 +35,7 @@ NTSTATUS smbd_smb2_request_process_keepalive(struct smbd_smb2_request *req)
 
 	/* TODO: update some time stamps */
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x04);
+	outbody = smbd_smb2_generate_outbody(req, 0x04);
 	if (outbody.data == NULL) {
 		return smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 	}
diff --git a/source3/smbd/smb2_lock.c b/source3/smbd/smb2_lock.c
index 671cd6f..4af3d61 100644
--- a/source3/smbd/smb2_lock.c
+++ b/source3/smbd/smb2_lock.c
@@ -146,7 +146,7 @@ static void smbd_smb2_request_lock_done(struct tevent_req *subreq)
 		return;
 	}
 
-	outbody = data_blob_talloc(smb2req->out.vector, NULL, 0x04);
+	outbody = smbd_smb2_generate_outbody(smb2req, 0x04);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(smb2req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_negprot.c b/source3/smbd/smb2_negprot.c
index b1e71e6..6643464 100644
--- a/source3/smbd/smb2_negprot.c
+++ b/source3/smbd/smb2_negprot.c
@@ -320,7 +320,7 @@ NTSTATUS smbd_smb2_request_process_negprot(struct smbd_smb2_request *req)
 		return smbd_smb2_request_error(req, status);
 	}
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x40);
+	outbody = smbd_smb2_generate_outbody(req, 0x40);
 	if (outbody.data == NULL) {
 		return smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 	}
diff --git a/source3/smbd/smb2_notify.c b/source3/smbd/smb2_notify.c
index 228346e..7351d9f 100644
--- a/source3/smbd/smb2_notify.c
+++ b/source3/smbd/smb2_notify.c
@@ -130,7 +130,7 @@ static void smbd_smb2_request_notify_done(struct tevent_req *subreq)
 
 	out_output_buffer_offset = SMB2_HDR_BODY + 0x08;
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x08);
+	outbody = smbd_smb2_generate_outbody(req, 0x08);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
diff --git a/source3/smbd/smb2_read.c b/source3/smbd/smb2_read.c
index 6478326..05563b2 100644
--- a/source3/smbd/smb2_read.c
+++ b/source3/smbd/smb2_read.c
@@ -128,7 +128,7 @@ static void smbd_smb2_request_read_done(struct tevent_req *subreq)
 
 	out_data_offset = SMB2_HDR_BODY + 0x10;
 
-	outbody = data_blob_talloc(req->out.vector, NULL, 0x10);
+	outbody = smbd_smb2_generate_outbody(req, 0x10);
 	if (outbody.data == NULL) {
 		error = smbd_smb2_request_error(req, NT_STATUS_NO_MEMORY);
 		if (!NT_STATUS_IS_OK(error)) {
@@ -167,10 +167,16 @@ struct smbd_smb2_read_state {
 	uint64_t in_offset;
 	uint32_t in_minimum;
 	DATA_BLOB out_headers;
+	uint8_t _out_hdr_buf[NBT_HDR_SIZE + SMB2_HDR_BODY + 0x10];
 	DATA_BLOB out_data;
 	uint32_t out_remaining;
 };
 
+static int smb2_smb2_read_state_deny_destructor(struct smbd_smb2_read_state *state)
+{
+	return -1;
+}
+
 /* struct smbd_smb2_read_state destructor. Send the SMB2_READ data. */
 static int smb2_sendfile_send_data(struct smbd_smb2_read_state *state)
 {
@@ -258,7 +264,6 @@ static int smb2_sendfile_send_data(struct smbd_smb2_read_state *state)
 static NTSTATUS schedule_smb2_sendfile_read(struct smbd_smb2_request *smb2req,
 					struct smbd_smb2_read_state *state)
 {
-	struct smbd_smb2_read_state *state_copy = NULL;
 	files_struct *fsp = state->fsp;
 
 	/*
@@ -293,16 +298,8 @@ static NTSTATUS schedule_smb2_sendfile_read(struct smbd_smb2_request *smb2req,
 	state->out_data.length = state->in_length;
 	state->out_remaining = 0;
 
-	/* Make a copy of state attached to the smb2req. Attach
-	   the destructor here as this will trigger the sendfile
-	   call when the request is destroyed. */
-	state_copy = talloc(smb2req, struct smbd_smb2_read_state);
-	if (!state_copy) {
-		return NT_STATUS_NO_MEMORY;
-	}
-	*state_copy = *state;
-	talloc_set_destructor(state_copy, smb2_sendfile_send_data);
-	state->smb2req->queue_entry.sendfile_header = &state_copy->out_headers;
+	state->out_headers = data_blob_const(state->_out_hdr_buf,
+					     sizeof(state->_out_hdr_buf));
 	return NT_STATUS_OK;
 }
 
@@ -582,6 +579,15 @@ static NTSTATUS smbd_smb2_read_recv(struct tevent_req *req,
 	talloc_steal(mem_ctx, out_data->data);
 	*out_remaining = state->out_remaining;
 
-	tevent_req_received(req);
+	if (state->out_headers.length > 0) {
+		talloc_steal(mem_ctx, state);
+		talloc_set_destructor(state, smb2_smb2_read_state_deny_destructor);
+		tevent_req_received(req);
+		state->smb2req->queue_entry.sendfile_header = &state->out_headers;
+		talloc_set_destructor(state, smb2_sendfile_send_data);
+	} else {
+		tevent_req_received(req);
+	}
+
 	return NT_STATUS_OK;
 }
diff --git a/source3/smbd/smb2_server.c b/source3/smbd/smb2_server.c
index 5e6bfd9..3c46efd 100644
--- a/source3/smbd/smb2_server.c
+++ b/source3/smbd/smb2_server.c
@@ -37,8 +37,6 @@ static void smbd_smb2_connection_handler(struct tevent_context *ev,
 static NTSTATUS smbd_smb2_io_handler(struct smbd_server_connection *sconn,
 				     uint16_t fde_flags);
 
-#define OUTVEC_ALLOC_SIZE (SMB2_HDR_BODY + 9)
-
 static const struct smbd_smb2_dispatch_table {
 	uint16_t opcode;
 	const char *name;
@@ -255,8 +253,12 @@ 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);
+	if (req->first_key.length > 0) {
+		data_blob_clear_free(&req->first_key);
+	}
+	if (req->last_key.length > 0) {
+		data_blob_clear_free(&req->last_key);
+	}
 	return 0;
 }
 
@@ -297,10 +299,11 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
 					       NTTIME now,
 					       uint8_t *buf,
 					       size_t buflen,
-					       TALLOC_CTX *mem_ctx,
+					       struct smbd_smb2_request *req,
 					       struct iovec **piov,
 					       int *pnum_iov)
 {
+	TALLOC_CTX *mem_ctx = req;
 	struct iovec *iov;
 	int num_iov = 1;
 	size_t taken = 0;
@@ -312,10 +315,7 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
 	/*
 	 * Note: index '0' is reserved for the transport protocol
 	 */
-	iov = talloc_zero_array(mem_ctx, struct iovec, num_iov);
-	if (iov == NULL) {
-		return NT_STATUS_NO_MEMORY;
-	}
+	iov = req->in._vector;
 
 	while (taken < buflen) {
 		size_t len = buflen - taken;
@@ -327,7 +327,6 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
 		uint8_t *body = NULL;
 		uint32_t dyn_size;
 		uint8_t *dyn = NULL;
-		struct iovec *iov_tmp;
 
 		if (verified_buflen > taken) {
 			len = verified_buflen - taken;
@@ -458,13 +457,31 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
 		dyn = body + body_size;
 		dyn_size = full_size - (SMB2_HDR_BODY + body_size);
 
-		iov_tmp = talloc_realloc(mem_ctx, iov, struct iovec,
-					 num_iov + SMBD_SMB2_NUM_IOV_PER_REQ);
-		if (iov_tmp == NULL) {
-			TALLOC_FREE(iov);
-			return NT_STATUS_NO_MEMORY;
+		if (num_iov >= ARRAY_SIZE(req->in._vector)) {
+			struct iovec *iov_tmp = NULL;
+			struct iovec *iov_alloc = NULL;
+
+			if (iov != req->in._vector) {
+				iov_alloc = iov;
+			}
+
+			iov_tmp = talloc_realloc(mem_ctx, iov_alloc,
+						 struct iovec,
+						 num_iov +
+						 SMBD_SMB2_NUM_IOV_PER_REQ);
+			if (iov_tmp == NULL) {
+				TALLOC_FREE(iov_alloc);
+				return NT_STATUS_NO_MEMORY;
+			}
+
+			if (iov_alloc == NULL) {
+				memcpy(iov_tmp,
+				       req->in._vector,
+				       sizeof(req->in._vector));
+			}
+
+			iov = iov_tmp;
 		}
-		iov = iov_tmp;
 		cur = &iov[num_iov];
 		num_iov += SMBD_SMB2_NUM_IOV_PER_REQ;
 
@@ -485,7 +502,9 @@ static NTSTATUS smbd_smb2_inbuf_parse_compound(struct smbXsrv_connection *conn,
 	return NT_STATUS_OK;
 
 inval:
-	TALLOC_FREE(iov);
+	if (iov != req->in._vector) {
+		TALLOC_FREE(iov);
+	}
 	return NT_STATUS_INVALID_PARAMETER;
 }
 
@@ -901,16 +920,34 @@ static void smb2_calculate_credits(const struct smbd_smb2_request *inreq,
 	}
 }
 
+DATA_BLOB smbd_smb2_generate_outbody(struct smbd_smb2_request *req, size_t size)
+{
+	if (req->current_idx <= 1) {
+		if (size <= sizeof(req->out._body)) {
+			return data_blob_const(req->out._body, size);
+		}
+	}
+
+	return data_blob_talloc(req, NULL, size);
+}
+
 static NTSTATUS smbd_smb2_request_setup_out(struct smbd_smb2_request *req)
 {
+	TALLOC_CTX *mem_ctx;
 	struct iovec *vector;
 	int count;
 	int idx;
 
 	count = req->in.vector_count;
-	vector = talloc_zero_array(req, struct iovec, count);
-	if (vector == NULL) {
-		return NT_STATUS_NO_MEMORY;
+	if (count <= ARRAY_SIZE(req->out._vector)) {
+		mem_ctx = req;
+		vector = req->out._vector;
+	} else {
+		vector = talloc_zero_array(req, struct iovec, count);
+		if (vector == NULL) {
+			return NT_STATUS_NO_MEMORY;
+		}
+		mem_ctx = vector;
 	}
 
 	vector[0].iov_base	= req->out.nbt_hdr;
@@ -931,10 +968,14 @@ static NTSTATUS smbd_smb2_request_setup_out(struct smbd_smb2_request *req)
 			next_command_ofs = SMB2_HDR_BODY + 9;
 		}
 
-		outhdr = talloc_zero_array(vector, uint8_t,
-				      OUTVEC_ALLOC_SIZE);
-		if (outhdr == NULL) {
-			return NT_STATUS_NO_MEMORY;
+		if (idx == 1) {
+			outhdr = req->out._hdr;
+		} else {
+			outhdr = talloc_zero_array(mem_ctx, uint8_t,
+						   OUTVEC_ALLOC_SIZE);
+			if (outhdr == NULL) {
+				return NT_STATUS_NO_MEMORY;
+			}
 		}
 
 		outbody = outhdr + SMB2_HDR_BODY;
@@ -1324,7 +1365,9 @@ NTSTATUS smbd_smb2_request_pending_queue(struct smbd_smb2_request *req,
 		if (!NT_STATUS_IS_OK(status)) {
 			return status;
 		}
-		data_blob_clear_free(&req->first_key);
+		if (req->first_key.length > 0) {
+			data_blob_clear_free(&req->first_key);
+		}
 
 		req->current_idx = 1;
 
@@ -1355,7 +1398,9 @@ NTSTATUS smbd_smb2_request_pending_queue(struct smbd_smb2_request *req,
 			SIVAL(outhdr, SMB2_HDR_FLAGS, flags);
 		}
 	}
-	data_blob_clear_free(&req->last_key);
+	if (req->last_key.length > 0) {
+		data_blob_clear_free(&req->last_key);
+	}
 
 	defer_endtime = timeval_current_ofs_usec(defer_time);
 	req->async_te = tevent_add_timer(req->sconn->ev_ctx,
@@ -2310,7 +2355,7 @@ static NTSTATUS smbd_smb2_request_reply(struct smbd_smb2_request *req)
 			return NT_STATUS_NO_MEMORY;
 		}
 
-		tf = talloc_zero_array(req->out.vector, uint8_t,
+		tf = talloc_zero_array(req, uint8_t,
 				       SMB2_TF_HDR_SIZE);
 		if (tf == NULL) {
 			return NT_STATUS_NO_MEMORY;
@@ -2345,7 +2390,9 @@ static NTSTATUS smbd_smb2_request_reply(struct smbd_smb2_request *req)
 			return status;
 		}
 	}
-	data_blob_clear_free(&req->last_key);
+	if (req->last_key.length > 0) {
+		data_blob_clear_free(&req->last_key);
+	}
 
 	req->current_idx += SMBD_SMB2_NUM_IOV_PER_REQ;
 
@@ -2419,7 +2466,9 @@ static NTSTATUS smbd_smb2_request_reply(struct smbd_smb2_request *req)
 			return status;
 		}
 	}
-	data_blob_clear_free(&req->first_key);
+	if (req->first_key.length > 0) {
+		data_blob_clear_free(&req->first_key);
+	}
 
 	/* I am a sick, sick man... :-). Sendfile hack ... JRA. */
 	if (req->out.vector_count < (2*SMBD_SMB2_NUM_IOV_PER_REQ) &&
@@ -2540,7 +2589,7 @@ NTSTATUS smbd_smb2_request_done_ex(struct smbd_smb2_request *req,
 			 */
 			uint8_t *pad;
 
-			pad = talloc_zero_array(req->out.vector,
+			pad = talloc_zero_array(req,
 						uint8_t, pad_size);
 			if (pad == NULL) {
 				return smbd_smb2_request_error(req,
@@ -2563,7 +2612,7 @@ NTSTATUS smbd_smb2_request_done_ex(struct smbd_smb2_request *req,
 			old_dyn = SMBD_SMB2_OUT_DYN_PTR(req);
 
 			new_size = old_size + pad_size;
-			new_dyn = talloc_zero_array(req->out.vector,
+			new_dyn = talloc_zero_array(req,
 					       uint8_t, new_size);
 			if (new_dyn == NULL) {
 				return smbd_smb2_request_error(req,
@@ -2590,6 +2639,7 @@ NTSTATUS smbd_smb2_request_error_ex(struct smbd_smb2_request *req,
 				    const char *location)
 {
 	DATA_BLOB body;
+	DATA_BLOB _dyn;
 	uint8_t *outhdr = SMBD_SMB2_OUT_HDR_PTR(req);
 	size_t unread_bytes = smbd_smb2_unread_bytes(req);
 
@@ -2631,12 +2681,7 @@ NTSTATUS smbd_smb2_request_error_ex(struct smbd_smb2_request *req,
 		 * *MUST BE* OUTVEC_ALLOC_SIZE. So we have room for
 		 * 1 byte without having to do an alloc.
 		 */
-		info = talloc_zero_array(req->out.vector,


-- 
Samba Shared Repository


More information about the samba-cvs mailing list