2 Unix SMB/CIFS implementation.
3 Infrastructure for async SMB client requests
4 Copyright (C) Volker Lendecke 2008
5 Copyright (C) Stefan Metzmacher 2011
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
22 #include "system/network.h"
23 #include "../lib/async_req/async_sock.h"
24 #include "../lib/util/tevent_ntstatus.h"
25 #include "../lib/util/tevent_unix.h"
26 #include "lib/util/util_net.h"
27 #include "lib/util/dlinklist.h"
28 #include "lib/util/iov_buf.h"
29 #include "../libcli/smb/smb_common.h"
30 #include "../libcli/smb/smb_seal.h"
31 #include "../libcli/smb/smb_signing.h"
32 #include "../libcli/smb/read_smb.h"
33 #include "smbXcli_base.h"
34 #include "librpc/ndr/libndr.h"
35 #include "libcli/smb/smb2_negotiate_context.h"
36 #include "libcli/smb/smb2_signing.h"
38 #include "lib/crypto/gnutls_helpers.h"
39 #include <gnutls/gnutls.h>
40 #include <gnutls/crypto.h>
44 struct smbXcli_session
;
49 struct sockaddr_storage local_ss
;
50 struct sockaddr_storage remote_ss
;
51 const char *remote_name
;
53 struct tevent_queue
*outgoing
;
54 struct tevent_req
**pending
;
55 struct tevent_req
*read_smb_req
;
56 struct tevent_req
*suicide_req
;
58 enum protocol_types min_protocol
;
59 enum protocol_types max_protocol
;
60 enum protocol_types protocol
;
63 bool mandatory_signing
;
66 * The incoming dispatch function should return:
67 * - NT_STATUS_RETRY, if more incoming PDUs are expected.
68 * - NT_STATUS_OK, if no more processing is desired, e.g.
69 * the dispatch function called
71 * - All other return values disconnect the connection.
73 NTSTATUS (*dispatch_incoming
)(struct smbXcli_conn
*conn
,
79 uint32_t capabilities
;
84 uint32_t capabilities
;
87 uint16_t security_mode
;
96 const char *workgroup
;
102 uint32_t capabilities
;
107 struct smb1_signing_state
*signing
;
108 struct smb_trans_enc_state
*trans_enc
;
110 struct tevent_req
*read_braw_req
;
115 uint32_t capabilities
;
116 uint16_t security_mode
;
118 struct smb311_capabilities smb3_capabilities
;
122 uint32_t capabilities
;
123 uint16_t security_mode
;
125 uint32_t max_trans_size
;
126 uint32_t max_read_size
;
127 uint32_t max_write_size
;
137 uint16_t cur_credits
;
138 uint16_t max_credits
;
140 uint32_t cc_chunk_len
;
141 uint32_t cc_max_chunks
;
145 bool force_channel_sequence
;
147 uint8_t preauth_sha512
[64];
150 struct smbXcli_session
*sessions
;
153 struct smb2cli_session
{
155 uint16_t session_flags
;
156 struct smb2_signing_key
*application_key
;
157 struct smb2_signing_key
*signing_key
;
160 struct smb2_signing_key
*encryption_key
;
161 struct smb2_signing_key
*decryption_key
;
162 uint64_t nonce_high_random
;
163 uint64_t nonce_high_max
;
166 uint16_t channel_sequence
;
168 bool require_signed_response
;
171 struct smbXcli_session
{
172 struct smbXcli_session
*prev
, *next
;
173 struct smbXcli_conn
*conn
;
178 DATA_BLOB application_key
;
182 struct smb2cli_session
*smb2
;
185 struct smb2_signing_key
*signing_key
;
186 uint8_t preauth_sha512
[64];
190 * this should be a short term hack
191 * until the upper layers have implemented
194 bool disconnect_expired
;
197 struct smbXcli_tcon
{
199 uint32_t fs_attributes
;
203 uint16_t optional_support
;
204 uint32_t maximal_access
;
205 uint32_t guest_maximal_access
;
214 uint32_t capabilities
;
215 uint32_t maximal_access
;
221 struct smbXcli_req_state
{
222 struct tevent_context
*ev
;
223 struct smbXcli_conn
*conn
;
224 struct smbXcli_session
*session
; /* maybe NULL */
225 struct smbXcli_tcon
*tcon
; /* maybe NULL */
227 uint8_t length_hdr
[4];
233 struct tevent_req
*write_req
;
235 struct timeval endtime
;
238 /* Space for the header including the wct */
239 uint8_t hdr
[HDR_VWV
];
242 * For normal requests, smb1cli_req_send chooses a mid.
243 * SecondaryV trans requests need to use the mid of the primary
244 * request, so we need a place to store it.
245 * Assume it is set if != 0.
250 uint8_t bytecount_buf
[2];
252 #define MAX_SMB_IOV 10
253 /* length_hdr, hdr, words, byte_count, buffers */
254 struct iovec iov
[1 + 3 + MAX_SMB_IOV
];
259 struct tevent_req
**chained_requests
;
262 NTSTATUS recv_status
;
263 /* always an array of 3 talloc elements */
264 struct iovec
*recv_iov
;
268 const uint8_t *fixed
;
273 uint8_t transform
[SMB2_TF_HDR_SIZE
];
274 uint8_t hdr
[SMB2_HDR_BODY
];
275 uint8_t pad
[7]; /* padding space for compounding */
278 * always an array of 3 talloc elements
279 * (without a SMB2_TRANSFORM header!)
283 struct iovec
*recv_iov
;
286 * the expected max for the response dyn_len
288 uint32_t max_dyn_len
;
290 uint16_t credit_charge
;
294 uint64_t encryption_session_id
;
296 bool signing_skipped
;
297 bool require_signed_response
;
300 uint16_t cancel_flags
;
306 static int smbXcli_conn_destructor(struct smbXcli_conn
*conn
)
309 * NT_STATUS_OK, means we do not notify the callers
311 smbXcli_conn_disconnect(conn
, NT_STATUS_OK
);
313 while (conn
->sessions
) {
314 conn
->sessions
->conn
= NULL
;
315 DLIST_REMOVE(conn
->sessions
, conn
->sessions
);
318 if (conn
->smb1
.trans_enc
) {
319 TALLOC_FREE(conn
->smb1
.trans_enc
);
325 struct smbXcli_conn
*smbXcli_conn_create(TALLOC_CTX
*mem_ctx
,
327 const char *remote_name
,
328 enum smb_signing_setting signing_state
,
329 uint32_t smb1_capabilities
,
330 struct GUID
*client_guid
,
331 uint32_t smb2_capabilities
,
332 const struct smb311_capabilities
*smb3_capabilities
)
334 struct smbXcli_conn
*conn
= NULL
;
336 struct sockaddr
*sa
= NULL
;
340 if (smb3_capabilities
!= NULL
) {
341 const struct smb3_signing_capabilities
*sign_algos
=
342 &smb3_capabilities
->signing
;
343 const struct smb3_encryption_capabilities
*ciphers
=
344 &smb3_capabilities
->encryption
;
346 SMB_ASSERT(sign_algos
->num_algos
<= SMB3_SIGNING_CAPABILITIES_MAX_ALGOS
);
347 SMB_ASSERT(ciphers
->num_algos
<= SMB3_ENCRYTION_CAPABILITIES_MAX_ALGOS
);
350 conn
= talloc_zero(mem_ctx
, struct smbXcli_conn
);
355 ret
= set_blocking(fd
, false);
361 conn
->remote_name
= talloc_strdup(conn
, remote_name
);
362 if (conn
->remote_name
== NULL
) {
366 ss
= (void *)&conn
->local_ss
;
367 sa
= (struct sockaddr
*)ss
;
368 sa_length
= sizeof(conn
->local_ss
);
369 ret
= getsockname(fd
, sa
, &sa_length
);
373 ss
= (void *)&conn
->remote_ss
;
374 sa
= (struct sockaddr
*)ss
;
375 sa_length
= sizeof(conn
->remote_ss
);
376 ret
= getpeername(fd
, sa
, &sa_length
);
381 conn
->outgoing
= tevent_queue_create(conn
, "smbXcli_outgoing");
382 if (conn
->outgoing
== NULL
) {
385 conn
->pending
= NULL
;
387 conn
->min_protocol
= PROTOCOL_NONE
;
388 conn
->max_protocol
= PROTOCOL_NONE
;
389 conn
->protocol
= PROTOCOL_NONE
;
391 switch (signing_state
) {
392 case SMB_SIGNING_OFF
:
394 conn
->allow_signing
= false;
395 conn
->desire_signing
= false;
396 conn
->mandatory_signing
= false;
398 case SMB_SIGNING_DEFAULT
:
399 case SMB_SIGNING_IF_REQUIRED
:
400 /* if the server requires it */
401 conn
->allow_signing
= true;
402 conn
->desire_signing
= false;
403 conn
->mandatory_signing
= false;
405 case SMB_SIGNING_DESIRED
:
406 /* if the server desires it */
407 conn
->allow_signing
= true;
408 conn
->desire_signing
= true;
409 conn
->mandatory_signing
= false;
411 case SMB_SIGNING_IPC_DEFAULT
:
412 case SMB_SIGNING_REQUIRED
:
414 conn
->allow_signing
= true;
415 conn
->desire_signing
= true;
416 conn
->mandatory_signing
= true;
420 conn
->smb1
.client
.capabilities
= smb1_capabilities
;
421 conn
->smb1
.client
.max_xmit
= UINT16_MAX
;
423 conn
->smb1
.capabilities
= conn
->smb1
.client
.capabilities
;
424 conn
->smb1
.max_xmit
= 1024;
428 /* initialise signing */
429 conn
->smb1
.signing
= smb1_signing_init(conn
,
431 conn
->desire_signing
,
432 conn
->mandatory_signing
);
433 if (!conn
->smb1
.signing
) {
437 conn
->smb2
.client
.security_mode
= SMB2_NEGOTIATE_SIGNING_ENABLED
;
438 if (conn
->mandatory_signing
) {
439 conn
->smb2
.client
.security_mode
|= SMB2_NEGOTIATE_SIGNING_REQUIRED
;
442 conn
->smb2
.client
.guid
= *client_guid
;
444 conn
->smb2
.client
.capabilities
= smb2_capabilities
;
445 if (smb3_capabilities
!= NULL
) {
446 conn
->smb2
.client
.smb3_capabilities
= *smb3_capabilities
;
449 conn
->smb2
.cur_credits
= 1;
450 conn
->smb2
.max_credits
= 0;
451 conn
->smb2
.io_priority
= 1;
454 * Samba and Windows servers accept a maximum of 16 MiB with a maximum
455 * chunk length of 1 MiB.
457 conn
->smb2
.cc_chunk_len
= 1024 * 1024;
458 conn
->smb2
.cc_max_chunks
= 16;
460 talloc_set_destructor(conn
, smbXcli_conn_destructor
);
468 bool smbXcli_conn_is_connected(struct smbXcli_conn
*conn
)
474 if (conn
->sock_fd
== -1) {
481 enum protocol_types
smbXcli_conn_protocol(struct smbXcli_conn
*conn
)
483 return conn
->protocol
;
486 bool smbXcli_conn_use_unicode(struct smbXcli_conn
*conn
)
488 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
492 if (conn
->smb1
.capabilities
& CAP_UNICODE
) {
499 bool smbXcli_conn_signing_mandatory(struct smbXcli_conn
*conn
)
501 return conn
->mandatory_signing
;
504 bool smbXcli_conn_have_posix(struct smbXcli_conn
*conn
)
506 if (conn
->protocol
>= PROTOCOL_SMB3_11
) {
507 return conn
->smb2
.server
.smb311_posix
;
509 if (conn
->protocol
<= PROTOCOL_NT1
) {
510 return (conn
->smb1
.capabilities
& CAP_UNIX
);
516 * [MS-SMB] 2.2.2.3.5 - SMB1 support for passing through
517 * query/set commands to the file system
519 bool smbXcli_conn_support_passthrough(struct smbXcli_conn
*conn
)
521 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
525 if (conn
->smb1
.capabilities
& CAP_W2K_SMBS
) {
532 void smbXcli_conn_set_sockopt(struct smbXcli_conn
*conn
, const char *options
)
534 set_socket_options(conn
->sock_fd
, options
);
537 const struct sockaddr_storage
*smbXcli_conn_local_sockaddr(struct smbXcli_conn
*conn
)
539 return &conn
->local_ss
;
542 const struct sockaddr_storage
*smbXcli_conn_remote_sockaddr(struct smbXcli_conn
*conn
)
544 return &conn
->remote_ss
;
547 const char *smbXcli_conn_remote_name(struct smbXcli_conn
*conn
)
549 return conn
->remote_name
;
552 uint16_t smbXcli_conn_max_requests(struct smbXcli_conn
*conn
)
554 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
561 return conn
->smb1
.server
.max_mux
;
564 NTTIME
smbXcli_conn_server_system_time(struct smbXcli_conn
*conn
)
566 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
567 return conn
->smb2
.server
.system_time
;
570 return conn
->smb1
.server
.system_time
;
573 const DATA_BLOB
*smbXcli_conn_server_gss_blob(struct smbXcli_conn
*conn
)
575 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
576 return &conn
->smb2
.server
.gss_blob
;
579 return &conn
->smb1
.server
.gss_blob
;
582 const struct GUID
*smbXcli_conn_server_guid(struct smbXcli_conn
*conn
)
584 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
585 return &conn
->smb2
.server
.guid
;
588 return &conn
->smb1
.server
.guid
;
591 bool smbXcli_conn_get_force_channel_sequence(struct smbXcli_conn
*conn
)
593 return conn
->smb2
.force_channel_sequence
;
596 void smbXcli_conn_set_force_channel_sequence(struct smbXcli_conn
*conn
,
599 conn
->smb2
.force_channel_sequence
= v
;
602 struct smbXcli_conn_samba_suicide_state
{
603 struct smbXcli_conn
*conn
;
606 struct tevent_req
*write_req
;
609 static void smbXcli_conn_samba_suicide_cleanup(struct tevent_req
*req
,
610 enum tevent_req_state req_state
);
611 static void smbXcli_conn_samba_suicide_done(struct tevent_req
*subreq
);
613 struct tevent_req
*smbXcli_conn_samba_suicide_send(TALLOC_CTX
*mem_ctx
,
614 struct tevent_context
*ev
,
615 struct smbXcli_conn
*conn
,
618 struct tevent_req
*req
, *subreq
;
619 struct smbXcli_conn_samba_suicide_state
*state
;
621 req
= tevent_req_create(mem_ctx
, &state
,
622 struct smbXcli_conn_samba_suicide_state
);
627 SIVAL(state
->buf
, 4, SMB_SUICIDE_PACKET
);
628 SCVAL(state
->buf
, 8, exitcode
);
629 _smb_setlen_nbt(state
->buf
, sizeof(state
->buf
)-4);
631 if (conn
->suicide_req
!= NULL
) {
632 tevent_req_nterror(req
, NT_STATUS_INVALID_PARAMETER
);
633 return tevent_req_post(req
, ev
);
636 state
->iov
.iov_base
= state
->buf
;
637 state
->iov
.iov_len
= sizeof(state
->buf
);
639 subreq
= writev_send(state
, ev
, conn
->outgoing
, conn
->sock_fd
,
640 false, &state
->iov
, 1);
641 if (tevent_req_nomem(subreq
, req
)) {
642 return tevent_req_post(req
, ev
);
644 tevent_req_set_callback(subreq
, smbXcli_conn_samba_suicide_done
, req
);
645 state
->write_req
= subreq
;
647 tevent_req_set_cleanup_fn(req
, smbXcli_conn_samba_suicide_cleanup
);
650 * We need to use tevent_req_defer_callback()
651 * in order to allow smbXcli_conn_disconnect()
652 * to do a safe cleanup.
654 tevent_req_defer_callback(req
, ev
);
655 conn
->suicide_req
= req
;
660 static void smbXcli_conn_samba_suicide_cleanup(struct tevent_req
*req
,
661 enum tevent_req_state req_state
)
663 struct smbXcli_conn_samba_suicide_state
*state
= tevent_req_data(
664 req
, struct smbXcli_conn_samba_suicide_state
);
666 TALLOC_FREE(state
->write_req
);
668 if (state
->conn
== NULL
) {
672 if (state
->conn
->suicide_req
== req
) {
673 state
->conn
->suicide_req
= NULL
;
678 static void smbXcli_conn_samba_suicide_done(struct tevent_req
*subreq
)
680 struct tevent_req
*req
= tevent_req_callback_data(
681 subreq
, struct tevent_req
);
682 struct smbXcli_conn_samba_suicide_state
*state
= tevent_req_data(
683 req
, struct smbXcli_conn_samba_suicide_state
);
687 state
->write_req
= NULL
;
689 nwritten
= writev_recv(subreq
, &err
);
691 if (nwritten
== -1) {
692 /* here, we need to notify all pending requests */
693 NTSTATUS status
= map_nt_error_from_unix_common(err
);
694 smbXcli_conn_disconnect(state
->conn
, status
);
697 tevent_req_done(req
);
700 NTSTATUS
smbXcli_conn_samba_suicide_recv(struct tevent_req
*req
)
702 return tevent_req_simple_recv_ntstatus(req
);
705 NTSTATUS
smbXcli_conn_samba_suicide(struct smbXcli_conn
*conn
,
708 TALLOC_CTX
*frame
= talloc_stackframe();
709 struct tevent_context
*ev
;
710 struct tevent_req
*req
;
711 NTSTATUS status
= NT_STATUS_NO_MEMORY
;
714 if (smbXcli_conn_has_async_calls(conn
)) {
716 * Can't use sync call while an async call is in flight
718 status
= NT_STATUS_INVALID_PARAMETER_MIX
;
721 ev
= samba_tevent_context_init(frame
);
725 req
= smbXcli_conn_samba_suicide_send(frame
, ev
, conn
, exitcode
);
729 ok
= tevent_req_poll_ntstatus(req
, ev
, &status
);
733 status
= smbXcli_conn_samba_suicide_recv(req
);
739 uint32_t smb1cli_conn_capabilities(struct smbXcli_conn
*conn
)
741 return conn
->smb1
.capabilities
;
744 uint32_t smb1cli_conn_max_xmit(struct smbXcli_conn
*conn
)
746 return conn
->smb1
.max_xmit
;
749 bool smb1cli_conn_req_possible(struct smbXcli_conn
*conn
)
751 size_t pending
= talloc_array_length(conn
->pending
);
752 uint16_t possible
= conn
->smb1
.server
.max_mux
;
754 if (pending
>= possible
) {
761 uint32_t smb1cli_conn_server_session_key(struct smbXcli_conn
*conn
)
763 return conn
->smb1
.server
.session_key
;
766 const uint8_t *smb1cli_conn_server_challenge(struct smbXcli_conn
*conn
)
768 return conn
->smb1
.server
.challenge
;
771 uint16_t smb1cli_conn_server_security_mode(struct smbXcli_conn
*conn
)
773 return conn
->smb1
.server
.security_mode
;
776 bool smb1cli_conn_server_readbraw(struct smbXcli_conn
*conn
)
778 return conn
->smb1
.server
.readbraw
;
781 bool smb1cli_conn_server_writebraw(struct smbXcli_conn
*conn
)
783 return conn
->smb1
.server
.writebraw
;
786 bool smb1cli_conn_server_lockread(struct smbXcli_conn
*conn
)
788 return conn
->smb1
.server
.lockread
;
791 bool smb1cli_conn_server_writeunlock(struct smbXcli_conn
*conn
)
793 return conn
->smb1
.server
.writeunlock
;
796 int smb1cli_conn_server_time_zone(struct smbXcli_conn
*conn
)
798 return conn
->smb1
.server
.time_zone
;
801 bool smb1cli_conn_activate_signing(struct smbXcli_conn
*conn
,
802 const DATA_BLOB user_session_key
,
803 const DATA_BLOB response
)
805 return smb1_signing_activate(conn
->smb1
.signing
,
810 bool smb1cli_conn_check_signing(struct smbXcli_conn
*conn
,
811 const uint8_t *buf
, uint32_t seqnum
)
813 const uint8_t *hdr
= buf
+ NBT_HDR_SIZE
;
814 size_t len
= smb_len_nbt(buf
);
816 return smb1_signing_check_pdu(conn
->smb1
.signing
, hdr
, len
, seqnum
);
819 bool smb1cli_conn_signing_is_active(struct smbXcli_conn
*conn
)
821 return smb1_signing_is_active(conn
->smb1
.signing
);
824 void smb1cli_conn_set_encryption(struct smbXcli_conn
*conn
,
825 struct smb_trans_enc_state
*es
)
827 /* Replace the old state, if any. */
828 if (conn
->smb1
.trans_enc
) {
829 TALLOC_FREE(conn
->smb1
.trans_enc
);
831 conn
->smb1
.trans_enc
= es
;
834 bool smb1cli_conn_encryption_on(struct smbXcli_conn
*conn
)
836 return common_encryption_on(conn
->smb1
.trans_enc
);
840 static NTSTATUS
smb1cli_pull_raw_error(const uint8_t *hdr
)
842 uint32_t flags2
= SVAL(hdr
, HDR_FLG2
);
843 NTSTATUS status
= NT_STATUS(IVAL(hdr
, HDR_RCLS
));
845 if (NT_STATUS_IS_OK(status
)) {
849 if (flags2
& FLAGS2_32_BIT_ERROR_CODES
) {
853 return NT_STATUS_DOS(CVAL(hdr
, HDR_RCLS
), SVAL(hdr
, HDR_ERR
));
857 * Is the SMB command able to hold an AND_X successor
858 * @param[in] cmd The SMB command in question
859 * @retval Can we add a chained request after "cmd"?
861 bool smb1cli_is_andx_req(uint8_t cmd
)
881 static uint16_t smb1cli_alloc_mid(struct smbXcli_conn
*conn
)
883 size_t num_pending
= talloc_array_length(conn
->pending
);
886 if (conn
->protocol
== PROTOCOL_NONE
) {
888 * This is what windows sends on the SMB1 Negprot request
889 * and some vendors reuse the SMB1 MID as SMB2 sequence number.
897 result
= conn
->smb1
.mid
++;
898 if ((result
== 0) || (result
== 0xffff)) {
902 for (i
=0; i
<num_pending
; i
++) {
903 if (result
== smb1cli_req_mid(conn
->pending
[i
])) {
908 if (i
== num_pending
) {
914 static NTSTATUS
smbXcli_req_cancel_write_req(struct tevent_req
*req
)
916 struct smbXcli_req_state
*state
=
918 struct smbXcli_req_state
);
919 struct smbXcli_conn
*conn
= state
->conn
;
920 size_t num_pending
= talloc_array_length(conn
->pending
);
925 if (state
->write_req
== NULL
) {
930 * Check if it's possible to cancel the request.
931 * If the result is true it's not too late.
932 * See writev_cancel().
934 ok
= tevent_req_cancel(state
->write_req
);
936 TALLOC_FREE(state
->write_req
);
938 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
940 * SMB2 has a sane signing state.
945 if (num_pending
> 1) {
947 * We have more pending requests following us. This
948 * means the signing state will be broken for them.
950 * As a solution we could add the requests directly to
951 * our outgoing queue and do the signing in the trigger
952 * function and then use writev_send() without passing a
953 * queue. That way we'll only sign packets we're most
954 * likely send to the wire.
956 return NT_STATUS_REQUEST_OUT_OF_SEQUENCE
;
960 * If we're the only request that's
961 * pending, we're able to recover the signing
964 smb1_signing_cancel_reply(conn
->smb1
.signing
,
965 state
->smb1
.one_way_seqnum
);
969 ret
= writev_recv(state
->write_req
, &err
);
970 TALLOC_FREE(state
->write_req
);
972 return map_nt_error_from_unix_common(err
);
978 void smbXcli_req_unset_pending(struct tevent_req
*req
)
980 struct smbXcli_req_state
*state
=
982 struct smbXcli_req_state
);
983 struct smbXcli_conn
*conn
= state
->conn
;
984 size_t num_pending
= talloc_array_length(conn
->pending
);
986 NTSTATUS cancel_status
;
988 cancel_status
= smbXcli_req_cancel_write_req(req
);
990 if (state
->smb1
.mid
!= 0) {
992 * This is a [nt]trans[2] request which waits
993 * for more than one reply.
995 if (!NT_STATUS_IS_OK(cancel_status
)) {
997 * If the write_req cancel didn't work
998 * we can't use the connection anymore.
1000 smbXcli_conn_disconnect(conn
, cancel_status
);
1006 tevent_req_set_cleanup_fn(req
, NULL
);
1008 if (num_pending
== 1) {
1010 * The pending read_smb tevent_req is a child of
1011 * conn->pending. So if nothing is pending anymore, we need to
1012 * delete the socket read fde.
1014 /* TODO: smbXcli_conn_cancel_read_req */
1015 TALLOC_FREE(conn
->pending
);
1016 conn
->read_smb_req
= NULL
;
1018 if (!NT_STATUS_IS_OK(cancel_status
)) {
1020 * If the write_req cancel didn't work
1021 * we can't use the connection anymore.
1023 smbXcli_conn_disconnect(conn
, cancel_status
);
1029 for (i
=0; i
<num_pending
; i
++) {
1030 if (req
== conn
->pending
[i
]) {
1034 if (i
== num_pending
) {
1036 * Something's seriously broken. Just returning here is the
1037 * right thing nevertheless, the point of this routine is to
1038 * remove ourselves from conn->pending.
1041 if (!NT_STATUS_IS_OK(cancel_status
)) {
1043 * If the write_req cancel didn't work
1044 * we can't use the connection anymore.
1046 smbXcli_conn_disconnect(conn
, cancel_status
);
1053 * Remove ourselves from the conn->pending array
1055 for (; i
< (num_pending
- 1); i
++) {
1056 conn
->pending
[i
] = conn
->pending
[i
+1];
1060 * No NULL check here, we're shrinking by sizeof(void *), and
1061 * talloc_realloc just adjusts the size for this.
1063 conn
->pending
= talloc_realloc(NULL
, conn
->pending
, struct tevent_req
*,
1066 if (!NT_STATUS_IS_OK(cancel_status
)) {
1068 * If the write_req cancel didn't work
1069 * we can't use the connection anymore.
1071 smbXcli_conn_disconnect(conn
, cancel_status
);
1077 static void smbXcli_req_cleanup(struct tevent_req
*req
,
1078 enum tevent_req_state req_state
)
1080 struct smbXcli_req_state
*state
=
1081 tevent_req_data(req
,
1082 struct smbXcli_req_state
);
1083 struct smbXcli_conn
*conn
= state
->conn
;
1084 NTSTATUS cancel_status
;
1086 switch (req_state
) {
1087 case TEVENT_REQ_RECEIVED
:
1089 * Make sure we really remove it from
1090 * the pending array on destruction.
1092 * smbXcli_req_unset_pending() calls
1093 * smbXcli_req_cancel_write_req() internal
1095 state
->smb1
.mid
= 0;
1096 smbXcli_req_unset_pending(req
);
1099 cancel_status
= smbXcli_req_cancel_write_req(req
);
1100 if (!NT_STATUS_IS_OK(cancel_status
)) {
1102 * If the write_req cancel didn't work
1103 * we can't use the connection anymore.
1105 smbXcli_conn_disconnect(conn
, cancel_status
);
1112 static bool smb1cli_req_cancel(struct tevent_req
*req
);
1113 static bool smb2cli_req_cancel(struct tevent_req
*req
);
1115 static bool smbXcli_req_cancel(struct tevent_req
*req
)
1117 struct smbXcli_req_state
*state
=
1118 tevent_req_data(req
,
1119 struct smbXcli_req_state
);
1121 if (!smbXcli_conn_is_connected(state
->conn
)) {
1125 if (state
->conn
->protocol
== PROTOCOL_NONE
) {
1129 if (state
->conn
->protocol
>= PROTOCOL_SMB2_02
) {
1130 return smb2cli_req_cancel(req
);
1133 return smb1cli_req_cancel(req
);
1136 static bool smbXcli_conn_receive_next(struct smbXcli_conn
*conn
);
1138 bool smbXcli_req_set_pending(struct tevent_req
*req
)
1140 struct smbXcli_req_state
*state
=
1141 tevent_req_data(req
,
1142 struct smbXcli_req_state
);
1143 struct smbXcli_conn
*conn
;
1144 struct tevent_req
**pending
;
1149 if (!smbXcli_conn_is_connected(conn
)) {
1153 num_pending
= talloc_array_length(conn
->pending
);
1155 pending
= talloc_realloc(conn
, conn
->pending
, struct tevent_req
*,
1157 if (pending
== NULL
) {
1160 pending
[num_pending
] = req
;
1161 conn
->pending
= pending
;
1162 tevent_req_set_cleanup_fn(req
, smbXcli_req_cleanup
);
1163 tevent_req_set_cancel_fn(req
, smbXcli_req_cancel
);
1165 if (!smbXcli_conn_receive_next(conn
)) {
1167 * the caller should notify the current request
1169 * And all other pending requests get notified
1170 * by smbXcli_conn_disconnect().
1172 smbXcli_req_unset_pending(req
);
1173 smbXcli_conn_disconnect(conn
, NT_STATUS_NO_MEMORY
);
1180 static void smbXcli_conn_received(struct tevent_req
*subreq
);
1182 static bool smbXcli_conn_receive_next(struct smbXcli_conn
*conn
)
1184 size_t num_pending
= talloc_array_length(conn
->pending
);
1185 struct tevent_req
*req
;
1186 struct smbXcli_req_state
*state
;
1188 if (conn
->read_smb_req
!= NULL
) {
1192 if (num_pending
== 0) {
1193 if (conn
->smb2
.mid
< UINT64_MAX
) {
1194 /* no more pending requests, so we are done for now */
1199 * If there are no more SMB2 requests possible,
1200 * because we are out of message ids,
1201 * we need to disconnect.
1203 smbXcli_conn_disconnect(conn
, NT_STATUS_CONNECTION_ABORTED
);
1207 req
= conn
->pending
[0];
1208 state
= tevent_req_data(req
, struct smbXcli_req_state
);
1211 * We're the first ones, add the read_smb request that waits for the
1212 * answer from the server
1214 conn
->read_smb_req
= read_smb_send(conn
->pending
,
1217 if (conn
->read_smb_req
== NULL
) {
1220 tevent_req_set_callback(conn
->read_smb_req
, smbXcli_conn_received
, conn
);
1224 void smbXcli_conn_disconnect(struct smbXcli_conn
*conn
, NTSTATUS status
)
1226 struct smbXcli_session
*session
;
1227 int sock_fd
= conn
->sock_fd
;
1229 tevent_queue_stop(conn
->outgoing
);
1233 session
= conn
->sessions
;
1234 if (talloc_array_length(conn
->pending
) == 0) {
1236 * if we do not have pending requests
1237 * there is no need to update the channel_sequence
1241 for (; session
; session
= session
->next
) {
1242 smb2cli_session_increment_channel_sequence(session
);
1245 if (conn
->suicide_req
!= NULL
) {
1247 * smbXcli_conn_samba_suicide_send()
1248 * used tevent_req_defer_callback() already.
1250 if (!NT_STATUS_IS_OK(status
)) {
1251 tevent_req_nterror(conn
->suicide_req
, status
);
1253 conn
->suicide_req
= NULL
;
1257 * Cancel all pending requests. We do not do a for-loop walking
1258 * conn->pending because that array changes in
1259 * smbXcli_req_unset_pending.
1261 while (conn
->pending
!= NULL
&&
1262 talloc_array_length(conn
->pending
) > 0) {
1263 struct tevent_req
*req
;
1264 struct smbXcli_req_state
*state
;
1265 struct tevent_req
**chain
;
1269 req
= conn
->pending
[0];
1270 state
= tevent_req_data(req
, struct smbXcli_req_state
);
1272 if (state
->smb1
.chained_requests
== NULL
) {
1276 * We're dead. No point waiting for trans2
1279 state
->smb1
.mid
= 0;
1281 smbXcli_req_unset_pending(req
);
1283 if (NT_STATUS_IS_OK(status
)) {
1284 /* do not notify the callers */
1288 in_progress
= tevent_req_is_in_progress(req
);
1297 * we need to defer the callback, because we may notify
1298 * more then one caller.
1300 tevent_req_defer_callback(req
, state
->ev
);
1301 tevent_req_nterror(req
, status
);
1305 chain
= talloc_move(conn
, &state
->smb1
.chained_requests
);
1306 num_chained
= talloc_array_length(chain
);
1308 for (i
=0; i
<num_chained
; i
++) {
1312 state
= tevent_req_data(req
, struct smbXcli_req_state
);
1315 * We're dead. No point waiting for trans2
1318 state
->smb1
.mid
= 0;
1320 smbXcli_req_unset_pending(req
);
1322 if (NT_STATUS_IS_OK(status
)) {
1323 /* do not notify the callers */
1327 in_progress
= tevent_req_is_in_progress(req
);
1336 * we need to defer the callback, because we may notify
1337 * more than one caller.
1339 tevent_req_defer_callback(req
, state
->ev
);
1340 tevent_req_nterror(req
, status
);
1345 if (sock_fd
!= -1) {
1351 * Fetch a smb request's mid. Only valid after the request has been sent by
1352 * smb1cli_req_send().
1354 uint16_t smb1cli_req_mid(struct tevent_req
*req
)
1356 struct smbXcli_req_state
*state
=
1357 tevent_req_data(req
,
1358 struct smbXcli_req_state
);
1360 if (state
->smb1
.mid
!= 0) {
1361 return state
->smb1
.mid
;
1364 return SVAL(state
->smb1
.hdr
, HDR_MID
);
1367 void smb1cli_req_set_mid(struct tevent_req
*req
, uint16_t mid
)
1369 struct smbXcli_req_state
*state
=
1370 tevent_req_data(req
,
1371 struct smbXcli_req_state
);
1373 state
->smb1
.mid
= mid
;
1376 uint32_t smb1cli_req_seqnum(struct tevent_req
*req
)
1378 struct smbXcli_req_state
*state
=
1379 tevent_req_data(req
,
1380 struct smbXcli_req_state
);
1382 return state
->smb1
.seqnum
;
1385 void smb1cli_req_set_seqnum(struct tevent_req
*req
, uint32_t seqnum
)
1387 struct smbXcli_req_state
*state
=
1388 tevent_req_data(req
,
1389 struct smbXcli_req_state
);
1391 state
->smb1
.seqnum
= seqnum
;
1394 static size_t smbXcli_iov_len(const struct iovec
*iov
, int count
)
1396 ssize_t ret
= iov_buflen(iov
, count
);
1398 /* Ignore the overflow case for now ... */
1402 static void smb1cli_req_flags(enum protocol_types protocol
,
1403 uint32_t smb1_capabilities
,
1404 uint8_t smb_command
,
1405 uint8_t additional_flags
,
1406 uint8_t clear_flags
,
1408 uint16_t additional_flags2
,
1409 uint16_t clear_flags2
,
1413 uint16_t flags2
= 0;
1415 if (protocol
>= PROTOCOL_LANMAN1
) {
1416 flags
|= FLAG_CASELESS_PATHNAMES
;
1417 flags
|= FLAG_CANONICAL_PATHNAMES
;
1420 if (protocol
>= PROTOCOL_LANMAN2
) {
1421 flags2
|= FLAGS2_LONG_PATH_COMPONENTS
;
1422 flags2
|= FLAGS2_EXTENDED_ATTRIBUTES
;
1425 if (protocol
>= PROTOCOL_NT1
) {
1426 flags2
|= FLAGS2_IS_LONG_NAME
;
1428 if (smb1_capabilities
& CAP_UNICODE
) {
1429 flags2
|= FLAGS2_UNICODE_STRINGS
;
1431 if (smb1_capabilities
& CAP_STATUS32
) {
1432 flags2
|= FLAGS2_32_BIT_ERROR_CODES
;
1434 if (smb1_capabilities
& CAP_EXTENDED_SECURITY
) {
1435 flags2
|= FLAGS2_EXTENDED_SECURITY
;
1439 flags
|= additional_flags
;
1440 flags
&= ~clear_flags
;
1441 flags2
|= additional_flags2
;
1442 flags2
&= ~clear_flags2
;
1448 static void smb1cli_req_cancel_done(struct tevent_req
*subreq
);
1450 static bool smb1cli_req_cancel(struct tevent_req
*req
)
1452 struct smbXcli_req_state
*state
=
1453 tevent_req_data(req
,
1454 struct smbXcli_req_state
);
1459 struct tevent_req
*subreq
;
1462 flags
= CVAL(state
->smb1
.hdr
, HDR_FLG
);
1463 flags2
= SVAL(state
->smb1
.hdr
, HDR_FLG2
);
1464 pid
= SVAL(state
->smb1
.hdr
, HDR_PID
);
1465 pid
|= SVAL(state
->smb1
.hdr
, HDR_PIDHIGH
)<<16;
1466 mid
= SVAL(state
->smb1
.hdr
, HDR_MID
);
1468 subreq
= smb1cli_req_create(state
, state
->ev
,
1478 0, NULL
); /* bytes */
1479 if (subreq
== NULL
) {
1482 smb1cli_req_set_mid(subreq
, mid
);
1484 status
= smb1cli_req_chain_submit(&subreq
, 1);
1485 if (!NT_STATUS_IS_OK(status
)) {
1486 TALLOC_FREE(subreq
);
1489 smb1cli_req_set_mid(subreq
, 0);
1491 tevent_req_set_callback(subreq
, smb1cli_req_cancel_done
, NULL
);
1496 static void smb1cli_req_cancel_done(struct tevent_req
*subreq
)
1498 /* we do not care about the result */
1499 TALLOC_FREE(subreq
);
1502 struct tevent_req
*smb1cli_req_create(TALLOC_CTX
*mem_ctx
,
1503 struct tevent_context
*ev
,
1504 struct smbXcli_conn
*conn
,
1505 uint8_t smb_command
,
1506 uint8_t additional_flags
,
1507 uint8_t clear_flags
,
1508 uint16_t additional_flags2
,
1509 uint16_t clear_flags2
,
1510 uint32_t timeout_msec
,
1512 struct smbXcli_tcon
*tcon
,
1513 struct smbXcli_session
*session
,
1514 uint8_t wct
, uint16_t *vwv
,
1516 struct iovec
*bytes_iov
)
1518 struct tevent_req
*req
;
1519 struct smbXcli_req_state
*state
;
1521 uint16_t flags2
= 0;
1526 if (iov_count
> MAX_SMB_IOV
) {
1528 * Should not happen :-)
1533 req
= tevent_req_create(mem_ctx
, &state
,
1534 struct smbXcli_req_state
);
1540 state
->session
= session
;
1544 uid
= session
->smb1
.session_id
;
1548 tid
= tcon
->smb1
.tcon_id
;
1550 if (tcon
->fs_attributes
& FILE_CASE_SENSITIVE_SEARCH
) {
1551 clear_flags
|= FLAG_CASELESS_PATHNAMES
;
1553 /* Default setting, case insensitive. */
1554 additional_flags
|= FLAG_CASELESS_PATHNAMES
;
1557 if (smbXcli_conn_dfs_supported(conn
) &&
1558 smbXcli_tcon_is_dfs_share(tcon
))
1560 additional_flags2
|= FLAGS2_DFS_PATHNAMES
;
1564 state
->smb1
.recv_cmd
= 0xFF;
1565 state
->smb1
.recv_status
= NT_STATUS_INTERNAL_ERROR
;
1566 state
->smb1
.recv_iov
= talloc_zero_array(state
, struct iovec
, 3);
1567 if (state
->smb1
.recv_iov
== NULL
) {
1572 smb1cli_req_flags(conn
->protocol
,
1573 conn
->smb1
.capabilities
,
1582 SIVAL(state
->smb1
.hdr
, 0, SMB_MAGIC
);
1583 SCVAL(state
->smb1
.hdr
, HDR_COM
, smb_command
);
1584 SIVAL(state
->smb1
.hdr
, HDR_RCLS
, NT_STATUS_V(NT_STATUS_OK
));
1585 SCVAL(state
->smb1
.hdr
, HDR_FLG
, flags
);
1586 SSVAL(state
->smb1
.hdr
, HDR_FLG2
, flags2
);
1587 SSVAL(state
->smb1
.hdr
, HDR_PIDHIGH
, pid
>> 16);
1588 SSVAL(state
->smb1
.hdr
, HDR_TID
, tid
);
1589 SSVAL(state
->smb1
.hdr
, HDR_PID
, pid
);
1590 SSVAL(state
->smb1
.hdr
, HDR_UID
, uid
);
1591 SSVAL(state
->smb1
.hdr
, HDR_MID
, 0); /* this comes later */
1592 SCVAL(state
->smb1
.hdr
, HDR_WCT
, wct
);
1594 state
->smb1
.vwv
= vwv
;
1596 num_bytes
= iov_buflen(bytes_iov
, iov_count
);
1597 if (num_bytes
== -1) {
1599 * I'd love to add a check for num_bytes<=UINT16_MAX here, but
1600 * the smbclient->samba connections can lie and transfer more.
1606 SSVAL(state
->smb1
.bytecount_buf
, 0, num_bytes
);
1608 state
->smb1
.iov
[0].iov_base
= (void *)state
->length_hdr
;
1609 state
->smb1
.iov
[0].iov_len
= sizeof(state
->length_hdr
);
1610 state
->smb1
.iov
[1].iov_base
= (void *)state
->smb1
.hdr
;
1611 state
->smb1
.iov
[1].iov_len
= sizeof(state
->smb1
.hdr
);
1612 state
->smb1
.iov
[2].iov_base
= (void *)state
->smb1
.vwv
;
1613 state
->smb1
.iov
[2].iov_len
= wct
* sizeof(uint16_t);
1614 state
->smb1
.iov
[3].iov_base
= (void *)state
->smb1
.bytecount_buf
;
1615 state
->smb1
.iov
[3].iov_len
= sizeof(uint16_t);
1617 if (iov_count
!= 0) {
1618 memcpy(&state
->smb1
.iov
[4], bytes_iov
,
1619 iov_count
* sizeof(*bytes_iov
));
1621 state
->smb1
.iov_count
= iov_count
+ 4;
1623 if (timeout_msec
> 0) {
1624 state
->endtime
= timeval_current_ofs_msec(timeout_msec
);
1625 if (!tevent_req_set_endtime(req
, ev
, state
->endtime
)) {
1630 switch (smb_command
) {
1634 state
->one_way
= true;
1637 state
->one_way
= true;
1638 state
->smb1
.one_way_seqnum
= true;
1642 (CVAL(vwv
+3, 0) == LOCKING_ANDX_OPLOCK_RELEASE
)) {
1643 state
->one_way
= true;
1651 static NTSTATUS
smb1cli_conn_signv(struct smbXcli_conn
*conn
,
1652 struct iovec
*iov
, int iov_count
,
1654 bool one_way_seqnum
)
1656 TALLOC_CTX
*frame
= NULL
;
1661 * Obvious optimization: Make cli_calculate_sign_mac work with struct
1662 * iovec directly. MD5Update would do that just fine.
1665 if (iov_count
< 4) {
1666 return NT_STATUS_INVALID_PARAMETER_MIX
;
1668 if (iov
[0].iov_len
!= NBT_HDR_SIZE
) {
1669 return NT_STATUS_INVALID_PARAMETER_MIX
;
1671 if (iov
[1].iov_len
!= (MIN_SMB_SIZE
-sizeof(uint16_t))) {
1672 return NT_STATUS_INVALID_PARAMETER_MIX
;
1674 if (iov
[2].iov_len
> (0xFF * sizeof(uint16_t))) {
1675 return NT_STATUS_INVALID_PARAMETER_MIX
;
1677 if (iov
[3].iov_len
!= sizeof(uint16_t)) {
1678 return NT_STATUS_INVALID_PARAMETER_MIX
;
1681 frame
= talloc_stackframe();
1683 buf
= iov_concat(frame
, &iov
[1], iov_count
- 1);
1685 return NT_STATUS_NO_MEMORY
;
1688 *seqnum
= smb1_signing_next_seqnum(conn
->smb1
.signing
,
1690 status
= smb1_signing_sign_pdu(conn
->smb1
.signing
,
1692 talloc_get_size(buf
),
1694 if (!NT_STATUS_IS_OK(status
)) {
1697 memcpy(iov
[1].iov_base
, buf
, iov
[1].iov_len
);
1700 return NT_STATUS_OK
;
1703 static void smb1cli_req_writev_done(struct tevent_req
*subreq
);
1704 static NTSTATUS
smb1cli_conn_dispatch_incoming(struct smbXcli_conn
*conn
,
1705 TALLOC_CTX
*tmp_mem
,
1708 static NTSTATUS
smb1cli_req_writev_submit(struct tevent_req
*req
,
1709 struct smbXcli_req_state
*state
,
1710 struct iovec
*iov
, int iov_count
)
1712 struct tevent_req
*subreq
;
1718 if (!smbXcli_conn_is_connected(state
->conn
)) {
1719 return NT_STATUS_CONNECTION_DISCONNECTED
;
1722 if (state
->conn
->protocol
> PROTOCOL_NT1
) {
1723 DBG_ERR("called for dialect[%s] server[%s]\n",
1724 smb_protocol_types_string(state
->conn
->protocol
),
1725 smbXcli_conn_remote_name(state
->conn
));
1726 return NT_STATUS_REVISION_MISMATCH
;
1729 if (iov_count
< 4) {
1730 return NT_STATUS_INVALID_PARAMETER_MIX
;
1732 if (iov
[0].iov_len
!= NBT_HDR_SIZE
) {
1733 return NT_STATUS_INVALID_PARAMETER_MIX
;
1735 if (iov
[1].iov_len
!= (MIN_SMB_SIZE
-sizeof(uint16_t))) {
1736 return NT_STATUS_INVALID_PARAMETER_MIX
;
1738 if (iov
[2].iov_len
> (0xFF * sizeof(uint16_t))) {
1739 return NT_STATUS_INVALID_PARAMETER_MIX
;
1741 if (iov
[3].iov_len
!= sizeof(uint16_t)) {
1742 return NT_STATUS_INVALID_PARAMETER_MIX
;
1745 cmd
= CVAL(iov
[1].iov_base
, HDR_COM
);
1746 if (cmd
== SMBreadBraw
) {
1747 if (smbXcli_conn_has_async_calls(state
->conn
)) {
1748 return NT_STATUS_INVALID_PARAMETER_MIX
;
1750 state
->conn
->smb1
.read_braw_req
= req
;
1753 if (state
->smb1
.mid
!= 0) {
1754 mid
= state
->smb1
.mid
;
1756 mid
= smb1cli_alloc_mid(state
->conn
);
1758 SSVAL(iov
[1].iov_base
, HDR_MID
, mid
);
1760 nbtlen
= iov_buflen(&iov
[1], iov_count
-1);
1761 if ((nbtlen
== -1) || (nbtlen
> 0x1FFFF)) {
1762 return NT_STATUS_INVALID_PARAMETER_MIX
;
1765 _smb_setlen_nbt(iov
[0].iov_base
, nbtlen
);
1767 status
= smb1cli_conn_signv(state
->conn
, iov
, iov_count
,
1768 &state
->smb1
.seqnum
,
1769 state
->smb1
.one_way_seqnum
);
1771 if (!NT_STATUS_IS_OK(status
)) {
1776 * If we supported multiple encryption contexts
1777 * here we'd look up based on tid.
1779 if (common_encryption_on(state
->conn
->smb1
.trans_enc
)) {
1780 char *buf
, *enc_buf
;
1782 buf
= (char *)iov_concat(talloc_tos(), iov
, iov_count
);
1784 return NT_STATUS_NO_MEMORY
;
1786 status
= common_encrypt_buffer(state
->conn
->smb1
.trans_enc
,
1787 (char *)buf
, &enc_buf
);
1789 if (!NT_STATUS_IS_OK(status
)) {
1790 DEBUG(0, ("Error in encrypting client message: %s\n",
1791 nt_errstr(status
)));
1794 buf
= (char *)talloc_memdup(state
, enc_buf
,
1795 smb_len_nbt(enc_buf
)+4);
1798 return NT_STATUS_NO_MEMORY
;
1800 iov
[0].iov_base
= (void *)buf
;
1801 iov
[0].iov_len
= talloc_get_size(buf
);
1805 if (state
->conn
->dispatch_incoming
== NULL
) {
1806 state
->conn
->dispatch_incoming
= smb1cli_conn_dispatch_incoming
;
1809 if (!smbXcli_req_set_pending(req
)) {
1810 return NT_STATUS_NO_MEMORY
;
1813 tevent_req_set_cancel_fn(req
, smbXcli_req_cancel
);
1815 subreq
= writev_send(state
, state
->ev
, state
->conn
->outgoing
,
1816 state
->conn
->sock_fd
, false, iov
, iov_count
);
1817 if (subreq
== NULL
) {
1818 return NT_STATUS_NO_MEMORY
;
1820 tevent_req_set_callback(subreq
, smb1cli_req_writev_done
, req
);
1821 state
->write_req
= subreq
;
1823 return NT_STATUS_OK
;
1826 struct tevent_req
*smb1cli_req_send(TALLOC_CTX
*mem_ctx
,
1827 struct tevent_context
*ev
,
1828 struct smbXcli_conn
*conn
,
1829 uint8_t smb_command
,
1830 uint8_t additional_flags
,
1831 uint8_t clear_flags
,
1832 uint16_t additional_flags2
,
1833 uint16_t clear_flags2
,
1834 uint32_t timeout_msec
,
1836 struct smbXcli_tcon
*tcon
,
1837 struct smbXcli_session
*session
,
1838 uint8_t wct
, uint16_t *vwv
,
1840 const uint8_t *bytes
)
1842 struct tevent_req
*req
;
1846 iov
.iov_base
= discard_const_p(void, bytes
);
1847 iov
.iov_len
= num_bytes
;
1849 req
= smb1cli_req_create(mem_ctx
, ev
, conn
, smb_command
,
1850 additional_flags
, clear_flags
,
1851 additional_flags2
, clear_flags2
,
1858 if (!tevent_req_is_in_progress(req
)) {
1859 return tevent_req_post(req
, ev
);
1861 status
= smb1cli_req_chain_submit(&req
, 1);
1862 if (tevent_req_nterror(req
, status
)) {
1863 return tevent_req_post(req
, ev
);
1868 static void smb1cli_req_writev_done(struct tevent_req
*subreq
)
1870 struct tevent_req
*req
=
1871 tevent_req_callback_data(subreq
,
1873 struct smbXcli_req_state
*state
=
1874 tevent_req_data(req
,
1875 struct smbXcli_req_state
);
1879 state
->write_req
= NULL
;
1881 nwritten
= writev_recv(subreq
, &err
);
1882 TALLOC_FREE(subreq
);
1883 if (nwritten
== -1) {
1884 /* here, we need to notify all pending requests */
1885 NTSTATUS status
= map_nt_error_from_unix_common(err
);
1886 smbXcli_conn_disconnect(state
->conn
, status
);
1890 if (state
->one_way
) {
1891 state
->inbuf
= NULL
;
1892 tevent_req_done(req
);
1897 static void smbXcli_conn_received(struct tevent_req
*subreq
)
1899 struct smbXcli_conn
*conn
=
1900 tevent_req_callback_data(subreq
,
1901 struct smbXcli_conn
);
1902 TALLOC_CTX
*frame
= talloc_stackframe();
1908 if (subreq
!= conn
->read_smb_req
) {
1909 DEBUG(1, ("Internal error: cli_smb_received called with "
1910 "unexpected subreq\n"));
1911 smbXcli_conn_disconnect(conn
, NT_STATUS_INTERNAL_ERROR
);
1915 conn
->read_smb_req
= NULL
;
1917 received
= read_smb_recv(subreq
, frame
, &inbuf
, &err
);
1918 TALLOC_FREE(subreq
);
1919 if (received
== -1) {
1920 status
= map_nt_error_from_unix_common(err
);
1921 smbXcli_conn_disconnect(conn
, status
);
1926 status
= conn
->dispatch_incoming(conn
, frame
, inbuf
);
1928 if (NT_STATUS_IS_OK(status
)) {
1930 * We should not do any more processing
1931 * as the dispatch function called
1932 * tevent_req_done().
1937 if (!NT_STATUS_EQUAL(status
, NT_STATUS_RETRY
)) {
1939 * We got an error, so notify all pending requests
1941 smbXcli_conn_disconnect(conn
, status
);
1946 * We got NT_STATUS_RETRY, so we may ask for a
1947 * next incoming pdu.
1949 if (!smbXcli_conn_receive_next(conn
)) {
1950 smbXcli_conn_disconnect(conn
, NT_STATUS_NO_MEMORY
);
1954 static NTSTATUS
smb1cli_inbuf_parse_chain(uint8_t *buf
, TALLOC_CTX
*mem_ctx
,
1955 struct iovec
**piov
, int *pnum_iov
)
1966 size_t min_size
= MIN_SMB_SIZE
;
1968 buflen
= smb_len_tcp(buf
);
1971 hdr
= buf
+ NBT_HDR_SIZE
;
1973 status
= smb1cli_pull_raw_error(hdr
);
1974 if (NT_STATUS_IS_ERR(status
)) {
1976 * This is an ugly hack to support OS/2
1977 * which skips the byte_count in the DATA block
1978 * on some error responses.
1982 min_size
-= sizeof(uint16_t);
1985 if (buflen
< min_size
) {
1986 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
1990 * This returns iovec elements in the following order:
2005 iov
= talloc_array(mem_ctx
, struct iovec
, num_iov
);
2007 return NT_STATUS_NO_MEMORY
;
2009 iov
[0].iov_base
= hdr
;
2010 iov
[0].iov_len
= HDR_WCT
;
2013 cmd
= CVAL(hdr
, HDR_COM
);
2017 size_t len
= buflen
- taken
;
2019 struct iovec
*iov_tmp
;
2026 * we need at least WCT
2028 needed
= sizeof(uint8_t);
2030 DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
2031 __location__
, (int)len
, (int)needed
));
2036 * Now we check if the specified words are there
2038 wct
= CVAL(hdr
, wct_ofs
);
2039 needed
+= wct
* sizeof(uint16_t);
2041 DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
2042 __location__
, (int)len
, (int)needed
));
2046 if ((num_iov
== 1) &&
2048 NT_STATUS_IS_ERR(status
))
2051 * This is an ugly hack to support OS/2
2052 * which skips the byte_count in the DATA block
2053 * on some error responses.
2057 iov_tmp
= talloc_realloc(mem_ctx
, iov
, struct iovec
,
2059 if (iov_tmp
== NULL
) {
2061 return NT_STATUS_NO_MEMORY
;
2064 cur
= &iov
[num_iov
];
2068 cur
[0].iov_base
= hdr
+ (wct_ofs
+ sizeof(uint8_t));
2070 cur
[1].iov_base
= cur
[0].iov_base
;
2077 * we need at least BCC
2079 needed
+= sizeof(uint16_t);
2081 DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
2082 __location__
, (int)len
, (int)needed
));
2087 * Now we check if the specified bytes are there
2089 bcc_ofs
= wct_ofs
+ sizeof(uint8_t) + wct
* sizeof(uint16_t);
2090 bcc
= SVAL(hdr
, bcc_ofs
);
2091 needed
+= bcc
* sizeof(uint8_t);
2093 DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
2094 __location__
, (int)len
, (int)needed
));
2099 * we allocate 2 iovec structures for words and bytes
2101 iov_tmp
= talloc_realloc(mem_ctx
, iov
, struct iovec
,
2103 if (iov_tmp
== NULL
) {
2105 return NT_STATUS_NO_MEMORY
;
2108 cur
= &iov
[num_iov
];
2111 cur
[0].iov_len
= wct
* sizeof(uint16_t);
2112 cur
[0].iov_base
= hdr
+ (wct_ofs
+ sizeof(uint8_t));
2113 cur
[1].iov_len
= bcc
* sizeof(uint8_t);
2114 cur
[1].iov_base
= hdr
+ (bcc_ofs
+ sizeof(uint16_t));
2118 if (!smb1cli_is_andx_req(cmd
)) {
2120 * If the current command does not have AndX chanining
2126 if (wct
== 0 && bcc
== 0) {
2128 * An empty response also ends the chain,
2129 * most likely with an error.
2135 DEBUG(10, ("%s: wct[%d] < 2 for cmd[0x%02X]\n",
2136 __location__
, (int)wct
, (int)cmd
));
2139 cmd
= CVAL(cur
[0].iov_base
, 0);
2142 * If it is the end of the chain we are also done.
2146 wct_ofs
= SVAL(cur
[0].iov_base
, 2);
2148 if (wct_ofs
< taken
) {
2151 if (wct_ofs
> buflen
) {
2156 * we consumed everything up to the start of the next
2162 remaining
= buflen
- taken
;
2164 if (remaining
> 0 && num_iov
>= 3) {
2166 * The last DATA block gets the remaining
2167 * bytes, this is needed to support
2168 * CAP_LARGE_WRITEX and CAP_LARGE_READX.
2170 iov
[num_iov
-1].iov_len
+= remaining
;
2174 *pnum_iov
= num_iov
;
2175 return NT_STATUS_OK
;
2179 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
2182 static NTSTATUS
smb1cli_conn_dispatch_incoming(struct smbXcli_conn
*conn
,
2183 TALLOC_CTX
*tmp_mem
,
2186 struct tevent_req
*req
;
2187 struct smbXcli_req_state
*state
;
2194 uint8_t *inhdr
= inbuf
+ NBT_HDR_SIZE
;
2195 size_t len
= smb_len_tcp(inbuf
);
2196 struct iovec
*iov
= NULL
;
2198 struct tevent_req
**chain
= NULL
;
2199 size_t num_chained
= 0;
2200 size_t num_responses
= 0;
2202 if (conn
->smb1
.read_braw_req
!= NULL
) {
2203 req
= conn
->smb1
.read_braw_req
;
2204 conn
->smb1
.read_braw_req
= NULL
;
2205 state
= tevent_req_data(req
, struct smbXcli_req_state
);
2207 smbXcli_req_unset_pending(req
);
2209 if (state
->smb1
.recv_iov
== NULL
) {
2211 * For requests with more than
2212 * one response, we have to readd the
2215 state
->smb1
.recv_iov
= talloc_zero_array(state
,
2218 if (tevent_req_nomem(state
->smb1
.recv_iov
, req
)) {
2219 return NT_STATUS_OK
;
2223 state
->smb1
.recv_iov
[0].iov_base
= (void *)(inhdr
);
2224 state
->smb1
.recv_iov
[0].iov_len
= len
;
2225 ZERO_STRUCT(state
->smb1
.recv_iov
[1]);
2226 ZERO_STRUCT(state
->smb1
.recv_iov
[2]);
2228 state
->smb1
.recv_cmd
= SMBreadBraw
;
2229 state
->smb1
.recv_status
= NT_STATUS_OK
;
2230 state
->inbuf
= talloc_move(state
->smb1
.recv_iov
, &inbuf
);
2232 tevent_req_done(req
);
2233 return NT_STATUS_OK
;
2236 if ((IVAL(inhdr
, 0) != SMB_MAGIC
) /* 0xFF"SMB" */
2237 && (SVAL(inhdr
, 0) != 0x45ff)) /* 0xFF"E" */ {
2238 DEBUG(10, ("Got non-SMB PDU\n"));
2239 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
2243 * If we supported multiple encryption contexts
2244 * here we'd look up based on tid.
2246 if (common_encryption_on(conn
->smb1
.trans_enc
)
2247 && (CVAL(inbuf
, 0) == 0)) {
2248 uint16_t enc_ctx_num
;
2250 status
= get_enc_ctx_num(inbuf
, &enc_ctx_num
);
2251 if (!NT_STATUS_IS_OK(status
)) {
2252 DEBUG(10, ("get_enc_ctx_num returned %s\n",
2253 nt_errstr(status
)));
2257 if (enc_ctx_num
!= conn
->smb1
.trans_enc
->enc_ctx_num
) {
2258 DEBUG(10, ("wrong enc_ctx %d, expected %d\n",
2260 conn
->smb1
.trans_enc
->enc_ctx_num
));
2261 return NT_STATUS_INVALID_HANDLE
;
2264 status
= common_decrypt_buffer(conn
->smb1
.trans_enc
,
2266 if (!NT_STATUS_IS_OK(status
)) {
2267 DEBUG(10, ("common_decrypt_buffer returned %s\n",
2268 nt_errstr(status
)));
2271 inhdr
= inbuf
+ NBT_HDR_SIZE
;
2272 len
= smb_len_nbt(inbuf
);
2275 mid
= SVAL(inhdr
, HDR_MID
);
2276 num_pending
= talloc_array_length(conn
->pending
);
2278 for (i
=0; i
<num_pending
; i
++) {
2279 if (mid
== smb1cli_req_mid(conn
->pending
[i
])) {
2283 if (i
== num_pending
) {
2284 /* Dump unexpected reply */
2285 return NT_STATUS_RETRY
;
2288 oplock_break
= false;
2290 if (mid
== 0xffff) {
2292 * Paranoia checks that this is really an oplock break request.
2294 oplock_break
= (len
== 51); /* hdr + 8 words */
2295 oplock_break
&= ((CVAL(inhdr
, HDR_FLG
) & FLAG_REPLY
) == 0);
2296 oplock_break
&= (CVAL(inhdr
, HDR_COM
) == SMBlockingX
);
2297 oplock_break
&= (SVAL(inhdr
, HDR_VWV
+VWV(6)) == 0);
2298 oplock_break
&= (SVAL(inhdr
, HDR_VWV
+VWV(7)) == 0);
2300 if (!oplock_break
) {
2301 /* Dump unexpected reply */
2302 return NT_STATUS_RETRY
;
2306 req
= conn
->pending
[i
];
2307 state
= tevent_req_data(req
, struct smbXcli_req_state
);
2309 if (!oplock_break
/* oplock breaks are not signed */
2310 && !smb1_signing_check_pdu(conn
->smb1
.signing
,
2311 inhdr
, len
, state
->smb1
.seqnum
+1)) {
2312 DEBUG(10, ("cli_check_sign_mac failed\n"));
2313 return NT_STATUS_ACCESS_DENIED
;
2316 status
= smb1cli_inbuf_parse_chain(inbuf
, tmp_mem
,
2318 if (!NT_STATUS_IS_OK(status
)) {
2319 DEBUG(10,("smb1cli_inbuf_parse_chain - %s\n",
2320 nt_errstr(status
)));
2324 cmd
= CVAL(inhdr
, HDR_COM
);
2325 status
= smb1cli_pull_raw_error(inhdr
);
2327 if (NT_STATUS_EQUAL(status
, NT_STATUS_NETWORK_SESSION_EXPIRED
) &&
2328 (state
->session
!= NULL
) && state
->session
->disconnect_expired
)
2331 * this should be a short term hack
2332 * until the upper layers have implemented
2333 * re-authentication.
2338 if (state
->smb1
.chained_requests
== NULL
) {
2340 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
2343 smbXcli_req_unset_pending(req
);
2345 if (state
->smb1
.recv_iov
== NULL
) {
2347 * For requests with more than
2348 * one response, we have to readd the
2351 state
->smb1
.recv_iov
= talloc_zero_array(state
,
2354 if (tevent_req_nomem(state
->smb1
.recv_iov
, req
)) {
2355 return NT_STATUS_OK
;
2359 state
->smb1
.recv_cmd
= cmd
;
2360 state
->smb1
.recv_status
= status
;
2361 state
->inbuf
= talloc_move(state
->smb1
.recv_iov
, &inbuf
);
2363 state
->smb1
.recv_iov
[0] = iov
[0];
2364 state
->smb1
.recv_iov
[1] = iov
[1];
2365 state
->smb1
.recv_iov
[2] = iov
[2];
2367 if (talloc_array_length(conn
->pending
) == 0) {
2368 tevent_req_done(req
);
2369 return NT_STATUS_OK
;
2372 tevent_req_defer_callback(req
, state
->ev
);
2373 tevent_req_done(req
);
2374 return NT_STATUS_RETRY
;
2377 chain
= talloc_move(tmp_mem
, &state
->smb1
.chained_requests
);
2378 num_chained
= talloc_array_length(chain
);
2379 num_responses
= (num_iov
- 1)/2;
2381 if (num_responses
> num_chained
) {
2382 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
2385 for (i
=0; i
<num_chained
; i
++) {
2386 size_t iov_idx
= 1 + (i
*2);
2387 struct iovec
*cur
= &iov
[iov_idx
];
2391 state
= tevent_req_data(req
, struct smbXcli_req_state
);
2393 smbXcli_req_unset_pending(req
);
2396 * as we finish multiple requests here
2397 * we need to defer the callbacks as
2398 * they could destroy our current stack state.
2400 tevent_req_defer_callback(req
, state
->ev
);
2402 if (i
>= num_responses
) {
2403 tevent_req_nterror(req
, NT_STATUS_REQUEST_ABORTED
);
2407 if (state
->smb1
.recv_iov
== NULL
) {
2409 * For requests with more than
2410 * one response, we have to readd the
2413 state
->smb1
.recv_iov
= talloc_zero_array(state
,
2416 if (tevent_req_nomem(state
->smb1
.recv_iov
, req
)) {
2421 state
->smb1
.recv_cmd
= cmd
;
2423 if (i
== (num_responses
- 1)) {
2425 * The last request in the chain gets the status
2427 state
->smb1
.recv_status
= status
;
2429 cmd
= CVAL(cur
[0].iov_base
, 0);
2430 state
->smb1
.recv_status
= NT_STATUS_OK
;
2433 state
->inbuf
= inbuf
;
2436 * Note: here we use talloc_reference() in a way
2437 * that does not expose it to the caller.
2439 inbuf_ref
= talloc_reference(state
->smb1
.recv_iov
, inbuf
);
2440 if (tevent_req_nomem(inbuf_ref
, req
)) {
2444 /* copy the related buffers */
2445 state
->smb1
.recv_iov
[0] = iov
[0];
2446 state
->smb1
.recv_iov
[1] = cur
[0];
2447 state
->smb1
.recv_iov
[2] = cur
[1];
2449 tevent_req_done(req
);
2452 return NT_STATUS_RETRY
;
2455 NTSTATUS
smb1cli_req_recv(struct tevent_req
*req
,
2456 TALLOC_CTX
*mem_ctx
,
2457 struct iovec
**piov
,
2461 uint32_t *pvwv_offset
,
2462 uint32_t *pnum_bytes
,
2464 uint32_t *pbytes_offset
,
2466 const struct smb1cli_req_expected_response
*expected
,
2467 size_t num_expected
)
2469 struct smbXcli_req_state
*state
=
2470 tevent_req_data(req
,
2471 struct smbXcli_req_state
);
2472 NTSTATUS status
= NT_STATUS_OK
;
2473 struct iovec
*recv_iov
= NULL
;
2474 uint8_t *hdr
= NULL
;
2476 uint32_t vwv_offset
= 0;
2477 uint16_t *vwv
= NULL
;
2478 uint32_t num_bytes
= 0;
2479 uint32_t bytes_offset
= 0;
2480 uint8_t *bytes
= NULL
;
2482 bool found_status
= false;
2483 bool found_size
= false;
2497 if (pvwv_offset
!= NULL
) {
2500 if (pnum_bytes
!= NULL
) {
2503 if (pbytes
!= NULL
) {
2506 if (pbytes_offset
!= NULL
) {
2509 if (pinbuf
!= NULL
) {
2513 if (state
->inbuf
!= NULL
) {
2514 recv_iov
= state
->smb1
.recv_iov
;
2515 state
->smb1
.recv_iov
= NULL
;
2516 if (state
->smb1
.recv_cmd
!= SMBreadBraw
) {
2517 hdr
= (uint8_t *)recv_iov
[0].iov_base
;
2518 wct
= recv_iov
[1].iov_len
/2;
2519 vwv
= (uint16_t *)recv_iov
[1].iov_base
;
2520 vwv_offset
= PTR_DIFF(vwv
, hdr
);
2521 num_bytes
= recv_iov
[2].iov_len
;
2522 bytes
= (uint8_t *)recv_iov
[2].iov_base
;
2523 bytes_offset
= PTR_DIFF(bytes
, hdr
);
2527 if (tevent_req_is_nterror(req
, &status
)) {
2528 for (i
=0; i
< num_expected
; i
++) {
2529 if (NT_STATUS_EQUAL(status
, expected
[i
].status
)) {
2530 found_status
= true;
2536 return NT_STATUS_UNEXPECTED_NETWORK_ERROR
;
2542 if (num_expected
== 0) {
2543 found_status
= true;
2547 status
= state
->smb1
.recv_status
;
2549 for (i
=0; i
< num_expected
; i
++) {
2550 if (!NT_STATUS_EQUAL(status
, expected
[i
].status
)) {
2554 found_status
= true;
2555 if (expected
[i
].wct
== 0) {
2560 if (expected
[i
].wct
== wct
) {
2566 if (!found_status
) {
2571 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
2575 *piov
= talloc_move(mem_ctx
, &recv_iov
);
2587 if (pvwv_offset
!= NULL
) {
2588 *pvwv_offset
= vwv_offset
;
2590 if (pnum_bytes
!= NULL
) {
2591 *pnum_bytes
= num_bytes
;
2593 if (pbytes
!= NULL
) {
2596 if (pbytes_offset
!= NULL
) {
2597 *pbytes_offset
= bytes_offset
;
2599 if (pinbuf
!= NULL
) {
2600 *pinbuf
= state
->inbuf
;
2606 size_t smb1cli_req_wct_ofs(struct tevent_req
**reqs
, int num_reqs
)
2613 for (i
=0; i
<num_reqs
; i
++) {
2614 struct smbXcli_req_state
*state
;
2615 state
= tevent_req_data(reqs
[i
], struct smbXcli_req_state
);
2616 wct_ofs
+= smbXcli_iov_len(state
->smb1
.iov
+2,
2617 state
->smb1
.iov_count
-2);
2618 wct_ofs
= (wct_ofs
+ 3) & ~3;
2623 NTSTATUS
smb1cli_req_chain_submit(struct tevent_req
**reqs
, int num_reqs
)
2625 struct smbXcli_req_state
*first_state
=
2626 tevent_req_data(reqs
[0],
2627 struct smbXcli_req_state
);
2628 struct smbXcli_req_state
*state
;
2630 size_t chain_padding
= 0;
2632 struct iovec
*iov
= NULL
;
2633 struct iovec
*this_iov
;
2637 if (num_reqs
== 1) {
2638 return smb1cli_req_writev_submit(reqs
[0], first_state
,
2639 first_state
->smb1
.iov
,
2640 first_state
->smb1
.iov_count
);
2644 for (i
=0; i
<num_reqs
; i
++) {
2645 if (!tevent_req_is_in_progress(reqs
[i
])) {
2646 return NT_STATUS_INTERNAL_ERROR
;
2649 state
= tevent_req_data(reqs
[i
], struct smbXcli_req_state
);
2651 if (state
->smb1
.iov_count
< 4) {
2652 return NT_STATUS_INVALID_PARAMETER_MIX
;
2657 * The NBT and SMB header
2670 iovlen
+= state
->smb1
.iov_count
- 2;
2673 iov
= talloc_zero_array(first_state
, struct iovec
, iovlen
);
2675 return NT_STATUS_NO_MEMORY
;
2678 first_state
->smb1
.chained_requests
= (struct tevent_req
**)talloc_memdup(
2679 first_state
, reqs
, sizeof(*reqs
) * num_reqs
);
2680 if (first_state
->smb1
.chained_requests
== NULL
) {
2682 return NT_STATUS_NO_MEMORY
;
2685 wct_offset
= HDR_WCT
;
2688 for (i
=0; i
<num_reqs
; i
++) {
2689 size_t next_padding
= 0;
2692 state
= tevent_req_data(reqs
[i
], struct smbXcli_req_state
);
2694 if (i
< num_reqs
-1) {
2695 if (!smb1cli_is_andx_req(CVAL(state
->smb1
.hdr
, HDR_COM
))
2696 || CVAL(state
->smb1
.hdr
, HDR_WCT
) < 2) {
2698 TALLOC_FREE(first_state
->smb1
.chained_requests
);
2699 return NT_STATUS_INVALID_PARAMETER_MIX
;
2703 wct_offset
+= smbXcli_iov_len(state
->smb1
.iov
+2,
2704 state
->smb1
.iov_count
-2) + 1;
2705 if ((wct_offset
% 4) != 0) {
2706 next_padding
= 4 - (wct_offset
% 4);
2708 wct_offset
+= next_padding
;
2709 vwv
= state
->smb1
.vwv
;
2711 if (i
< num_reqs
-1) {
2712 struct smbXcli_req_state
*next_state
=
2713 tevent_req_data(reqs
[i
+1],
2714 struct smbXcli_req_state
);
2715 SCVAL(vwv
+0, 0, CVAL(next_state
->smb1
.hdr
, HDR_COM
));
2717 SSVAL(vwv
+1, 0, wct_offset
);
2718 } else if (smb1cli_is_andx_req(CVAL(state
->smb1
.hdr
, HDR_COM
))) {
2719 /* properly end the chain */
2720 SCVAL(vwv
+0, 0, 0xff);
2721 SCVAL(vwv
+0, 1, 0xff);
2727 * The NBT and SMB header
2729 this_iov
[0] = state
->smb1
.iov
[0];
2730 this_iov
[1] = state
->smb1
.iov
[1];
2734 * This one is a bit subtle. We have to add
2735 * chain_padding bytes between the requests, and we
2736 * have to also include the wct field of the
2737 * subsequent requests. We use the subsequent header
2738 * for the padding, it contains the wct field in its
2741 this_iov
[0].iov_len
= chain_padding
+1;
2742 this_iov
[0].iov_base
= (void *)&state
->smb1
.hdr
[
2743 sizeof(state
->smb1
.hdr
) - this_iov
[0].iov_len
];
2744 memset(this_iov
[0].iov_base
, 0, this_iov
[0].iov_len
-1);
2749 * copy the words and bytes
2751 memcpy(this_iov
, state
->smb1
.iov
+2,
2752 sizeof(struct iovec
) * (state
->smb1
.iov_count
-2));
2753 this_iov
+= state
->smb1
.iov_count
- 2;
2754 chain_padding
= next_padding
;
2757 nbt_len
= iov_buflen(&iov
[1], iovlen
-1);
2758 if ((nbt_len
== -1) || (nbt_len
> first_state
->conn
->smb1
.max_xmit
)) {
2760 TALLOC_FREE(first_state
->smb1
.chained_requests
);
2761 return NT_STATUS_INVALID_PARAMETER_MIX
;
2764 status
= smb1cli_req_writev_submit(reqs
[0], first_state
, iov
, iovlen
);
2765 if (!NT_STATUS_IS_OK(status
)) {
2767 TALLOC_FREE(first_state
->smb1
.chained_requests
);
2771 return NT_STATUS_OK
;
2774 struct tevent_queue
*smbXcli_conn_send_queue(struct smbXcli_conn
*conn
)
2776 return conn
->outgoing
;
2779 bool smbXcli_conn_has_async_calls(struct smbXcli_conn
*conn
)
2781 return ((tevent_queue_length(conn
->outgoing
) != 0)
2782 || (talloc_array_length(conn
->pending
) != 0));
2785 bool smbXcli_conn_dfs_supported(struct smbXcli_conn
*conn
)
2787 if (conn
->protocol
>= PROTOCOL_SMB2_02
) {
2788 return (smb2cli_conn_server_capabilities(conn
) & SMB2_CAP_DFS
);
2791 return (smb1cli_conn_capabilities(conn
) & CAP_DFS
);
2794 bool smb2cli_conn_req_possible(struct smbXcli_conn
*conn
, uint32_t *max_dyn_len
)
2796 uint16_t credits
= 1;
2798 if (conn
->smb2
.cur_credits
== 0) {
2799 if (max_dyn_len
!= NULL
) {
2805 if (conn
->smb2
.server
.capabilities
& SMB2_CAP_LARGE_MTU
) {
2806 credits
= conn
->smb2
.cur_credits
;
2809 if (max_dyn_len
!= NULL
) {
2810 *max_dyn_len
= credits
* 65536;
2816 uint32_t smb2cli_conn_server_capabilities(struct smbXcli_conn
*conn
)
2818 return conn
->smb2
.server
.capabilities
;
2821 uint16_t smb2cli_conn_server_security_mode(struct smbXcli_conn
*conn
)
2823 return conn
->smb2
.server
.security_mode
;
2826 uint16_t smb2cli_conn_server_signing_algo(struct smbXcli_conn
*conn
)
2828 return conn
->smb2
.server
.sign_algo
;
2831 uint16_t smb2cli_conn_server_encryption_algo(struct smbXcli_conn
*conn
)
2833 return conn
->smb2
.server
.cipher
;
2836 uint32_t smb2cli_conn_max_trans_size(struct smbXcli_conn
*conn
)
2838 return conn
->smb2
.server
.max_trans_size
;
2841 uint32_t smb2cli_conn_max_read_size(struct smbXcli_conn
*conn
)
2843 return conn
->smb2
.server
.max_read_size
;
2846 uint32_t smb2cli_conn_max_write_size(struct smbXcli_conn
*conn
)
2848 return conn
->smb2
.server
.max_write_size
;
2851 void smb2cli_conn_set_max_credits(struct smbXcli_conn
*conn
,
2852 uint16_t max_credits
)
2854 conn
->smb2
.max_credits
= max_credits
;
2857 uint16_t smb2cli_conn_get_cur_credits(struct smbXcli_conn
*conn
)
2859 return conn
->smb2
.cur_credits
;
2862 uint8_t smb2cli_conn_get_io_priority(struct smbXcli_conn
*conn
)
2864 if (conn
->protocol
< PROTOCOL_SMB3_11
) {
2868 return conn
->smb2
.io_priority
;
2871 void smb2cli_conn_set_io_priority(struct smbXcli_conn
*conn
,
2872 uint8_t io_priority
)
2874 conn
->smb2
.io_priority
= io_priority
;
2877 uint32_t smb2cli_conn_cc_chunk_len(struct smbXcli_conn
*conn
)
2879 return conn
->smb2
.cc_chunk_len
;
2882 void smb2cli_conn_set_cc_chunk_len(struct smbXcli_conn
*conn
,
2885 conn
->smb2
.cc_chunk_len
= chunk_len
;
2888 uint32_t smb2cli_conn_cc_max_chunks(struct smbXcli_conn
*conn
)
2890 return conn
->smb2
.cc_max_chunks
;
2893 void smb2cli_conn_set_cc_max_chunks(struct smbXcli_conn
*conn
,
2894 uint32_t max_chunks
)
2896 conn
->smb2
.cc_max_chunks
= max_chunks
;
2899 static void smb2cli_req_cancel_done(struct tevent_req
*subreq
);
2901 static bool smb2cli_req_cancel(struct tevent_req
*req
)
2903 struct smbXcli_req_state
*state
=
2904 tevent_req_data(req
,
2905 struct smbXcli_req_state
);
2906 struct smbXcli_tcon
*tcon
= state
->tcon
;
2907 struct smbXcli_session
*session
= state
->session
;
2908 uint8_t *fixed
= state
->smb2
.pad
;
2909 uint16_t fixed_len
= 4;
2910 struct tevent_req
*subreq
;
2911 struct smbXcli_req_state
*substate
;
2914 if (state
->smb2
.cancel_mid
== UINT64_MAX
) {
2916 * We already send a cancel,
2917 * make sure we don't do it
2918 * twice, otherwise we may
2919 * expose the same NONCE for
2920 * AES-128-GMAC signing
2925 SSVAL(fixed
, 0, 0x04);
2928 subreq
= smb2cli_req_create(state
, state
->ev
,
2936 if (subreq
== NULL
) {
2939 substate
= tevent_req_data(subreq
, struct smbXcli_req_state
);
2941 substate
->smb2
.cancel_mid
= BVAL(state
->smb2
.hdr
, SMB2_HDR_MESSAGE_ID
);
2943 SIVAL(substate
->smb2
.hdr
, SMB2_HDR_FLAGS
, state
->smb2
.cancel_flags
);
2944 SBVAL(substate
->smb2
.hdr
, SMB2_HDR_MESSAGE_ID
, state
->smb2
.cancel_mid
);
2945 SBVAL(substate
->smb2
.hdr
, SMB2_HDR_ASYNC_ID
, state
->smb2
.cancel_aid
);
2948 * remember that we don't send a cancel again
2950 state
->smb2
.cancel_mid
= UINT64_MAX
;
2952 status
= smb2cli_req_compound_submit(&subreq
, 1);
2953 if (!NT_STATUS_IS_OK(status
)) {
2954 TALLOC_FREE(subreq
);
2958 tevent_req_set_callback(subreq
, smb2cli_req_cancel_done
, NULL
);
2963 static void smb2cli_req_cancel_done(struct tevent_req
*subreq
)
2965 /* we do not care about the result */
2966 TALLOC_FREE(subreq
);
2969 struct timeval
smbXcli_req_endtime(struct tevent_req
*req
)
2971 struct smbXcli_req_state
*state
= tevent_req_data(
2972 req
, struct smbXcli_req_state
);
2974 return state
->endtime
;
2977 struct tevent_req
*smb2cli_req_create(TALLOC_CTX
*mem_ctx
,
2978 struct tevent_context
*ev
,
2979 struct smbXcli_conn
*conn
,
2981 uint32_t additional_flags
,
2982 uint32_t clear_flags
,
2983 uint32_t timeout_msec
,
2984 struct smbXcli_tcon
*tcon
,
2985 struct smbXcli_session
*session
,
2986 const uint8_t *fixed
,
2990 uint32_t max_dyn_len
)
2992 struct tevent_req
*req
;
2993 struct smbXcli_req_state
*state
;
2997 bool use_channel_sequence
= conn
->smb2
.force_channel_sequence
;
2998 uint16_t channel_sequence
= 0;
2999 bool use_replay_flag
= false;
3000 enum protocol_types proto
= smbXcli_conn_protocol(conn
);
3002 req
= tevent_req_create(mem_ctx
, &state
,
3003 struct smbXcli_req_state
);
3008 if ((proto
> PROTOCOL_NONE
) && (proto
< PROTOCOL_SMB2_02
)) {
3009 tevent_req_nterror(req
, NT_STATUS_INVALID_PARAMETER
);
3015 state
->session
= session
;
3018 if (conn
->smb2
.server
.capabilities
& SMB2_CAP_PERSISTENT_HANDLES
) {
3019 use_channel_sequence
= true;
3020 } else if (conn
->smb2
.server
.capabilities
& SMB2_CAP_MULTI_CHANNEL
) {
3021 use_channel_sequence
= true;
3024 if (smbXcli_conn_protocol(conn
) >= PROTOCOL_SMB3_00
) {
3025 use_replay_flag
= true;
3028 if (smbXcli_conn_protocol(conn
) >= PROTOCOL_SMB3_11
) {
3029 flags
|= SMB2_PRIORITY_VALUE_TO_MASK(conn
->smb2
.io_priority
);
3033 uid
= session
->smb2
->session_id
;
3035 if (use_channel_sequence
) {
3036 channel_sequence
= session
->smb2
->channel_sequence
;
3039 if (use_replay_flag
&& session
->smb2
->replay_active
) {
3040 additional_flags
|= SMB2_HDR_FLAG_REPLAY_OPERATION
;
3043 state
->smb2
.should_sign
= session
->smb2
->should_sign
;
3044 state
->smb2
.should_encrypt
= session
->smb2
->should_encrypt
;
3045 state
->smb2
.require_signed_response
=
3046 session
->smb2
->require_signed_response
;
3048 if (cmd
== SMB2_OP_SESSSETUP
&&
3049 !smb2_signing_key_valid(session
->smb2_channel
.signing_key
) &&
3050 smb2_signing_key_valid(session
->smb2
->signing_key
))
3053 * a session bind needs to be signed
3055 state
->smb2
.should_sign
= true;
3058 if (cmd
== SMB2_OP_SESSSETUP
&&
3059 !smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
3060 state
->smb2
.should_encrypt
= false;
3063 if (additional_flags
& SMB2_HDR_FLAG_SIGNED
) {
3064 if (!smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
3065 tevent_req_nterror(req
, NT_STATUS_NO_USER_SESSION_KEY
);
3069 additional_flags
&= ~SMB2_HDR_FLAG_SIGNED
;
3070 state
->smb2
.should_sign
= true;
3075 tid
= tcon
->smb2
.tcon_id
;
3077 if (tcon
->smb2
.should_sign
) {
3078 state
->smb2
.should_sign
= true;
3080 if (tcon
->smb2
.should_encrypt
) {
3081 state
->smb2
.should_encrypt
= true;
3085 if (state
->smb2
.should_encrypt
) {
3086 state
->smb2
.should_sign
= false;
3089 state
->smb2
.recv_iov
= talloc_zero_array(state
, struct iovec
, 3);
3090 if (tevent_req_nomem(state
->smb2
.recv_iov
, req
)) {
3094 flags
|= additional_flags
;
3095 flags
&= ~clear_flags
;
3097 state
->smb2
.fixed
= fixed
;
3098 state
->smb2
.fixed_len
= fixed_len
;
3099 state
->smb2
.dyn
= dyn
;
3100 state
->smb2
.dyn_len
= dyn_len
;
3101 state
->smb2
.max_dyn_len
= max_dyn_len
;
3103 if (state
->smb2
.should_encrypt
) {
3104 SIVAL(state
->smb2
.transform
, SMB2_TF_PROTOCOL_ID
, SMB2_TF_MAGIC
);
3105 SBVAL(state
->smb2
.transform
, SMB2_TF_SESSION_ID
, uid
);
3108 SIVAL(state
->smb2
.hdr
, SMB2_HDR_PROTOCOL_ID
, SMB2_MAGIC
);
3109 SSVAL(state
->smb2
.hdr
, SMB2_HDR_LENGTH
, SMB2_HDR_BODY
);
3110 SSVAL(state
->smb2
.hdr
, SMB2_HDR_OPCODE
, cmd
);
3111 SSVAL(state
->smb2
.hdr
, SMB2_HDR_CHANNEL_SEQUENCE
, channel_sequence
);
3112 SIVAL(state
->smb2
.hdr
, SMB2_HDR_FLAGS
, flags
);
3113 SIVAL(state
->smb2
.hdr
, SMB2_HDR_PID
, 0); /* reserved */
3114 SIVAL(state
->smb2
.hdr
, SMB2_HDR_TID
, tid
);
3115 SBVAL(state
->smb2
.hdr
, SMB2_HDR_SESSION_ID
, uid
);
3118 case SMB2_OP_CANCEL
:
3119 state
->one_way
= true;
3123 * If this is a dummy request, it will have
3124 * UINT64_MAX as message id.
3125 * If we send on break acknowledgement,
3126 * this gets overwritten later.
3128 SBVAL(state
->smb2
.hdr
, SMB2_HDR_MESSAGE_ID
, UINT64_MAX
);
3132 if (timeout_msec
> 0) {
3133 state
->endtime
= timeval_current_ofs_msec(timeout_msec
);
3134 if (!tevent_req_set_endtime(req
, ev
, state
->endtime
)) {
3142 void smb2cli_req_set_notify_async(struct tevent_req
*req
)
3144 struct smbXcli_req_state
*state
=
3145 tevent_req_data(req
,
3146 struct smbXcli_req_state
);
3148 state
->smb2
.notify_async
= true;
3151 static void smb2cli_req_writev_done(struct tevent_req
*subreq
);
3152 static NTSTATUS
smb2cli_conn_dispatch_incoming(struct smbXcli_conn
*conn
,
3153 TALLOC_CTX
*tmp_mem
,
3156 NTSTATUS
smb2cli_req_compound_submit(struct tevent_req
**reqs
,
3159 struct smbXcli_req_state
*state
;
3160 struct tevent_req
*subreq
;
3162 int i
, num_iov
, nbt_len
;
3164 struct smb2_signing_key
*encryption_key
= NULL
;
3165 uint64_t encryption_session_id
= 0;
3166 uint64_t nonce_high
= UINT64_MAX
;
3167 uint64_t nonce_low
= UINT64_MAX
;
3170 * 1 for the nbt length, optional TRANSFORM
3171 * per request: HDR, fixed, dyn, padding
3172 * -1 because the last one does not need padding
3175 iov
= talloc_array(reqs
[0], struct iovec
, 1 + 1 + 4*num_reqs
- 1);
3177 return NT_STATUS_NO_MEMORY
;
3184 * the session of the first request that requires encryption
3185 * specifies the encryption key.
3187 for (i
=0; i
<num_reqs
; i
++) {
3188 if (!tevent_req_is_in_progress(reqs
[i
])) {
3189 return NT_STATUS_INTERNAL_ERROR
;
3192 state
= tevent_req_data(reqs
[i
], struct smbXcli_req_state
);
3194 if (!smbXcli_conn_is_connected(state
->conn
)) {
3195 return NT_STATUS_CONNECTION_DISCONNECTED
;
3198 if ((state
->conn
->protocol
!= PROTOCOL_NONE
) &&
3199 (state
->conn
->protocol
< PROTOCOL_SMB2_02
)) {
3200 return NT_STATUS_REVISION_MISMATCH
;
3203 if (state
->session
== NULL
) {
3207 if (!state
->smb2
.should_encrypt
) {
3211 encryption_key
= state
->session
->smb2
->encryption_key
;
3212 if (!smb2_signing_key_valid(encryption_key
)) {
3213 return NT_STATUS_INVALID_PARAMETER_MIX
;
3216 encryption_session_id
= state
->session
->smb2
->session_id
;
3218 state
->session
->smb2
->nonce_low
+= 1;
3219 if (state
->session
->smb2
->nonce_low
== 0) {
3220 state
->session
->smb2
->nonce_high
+= 1;
3221 state
->session
->smb2
->nonce_low
+= 1;
3225 * CCM and GCM algorithms must never have their
3226 * nonce wrap, or the security of the whole
3227 * communication and the keys is destroyed.
3228 * We must drop the connection once we have
3229 * transferred too much data.
3231 * NOTE: We assume nonces greater than 8 bytes.
3233 if (state
->session
->smb2
->nonce_high
>=
3234 state
->session
->smb2
->nonce_high_max
)
3236 return NT_STATUS_ENCRYPTION_FAILED
;
3239 nonce_high
= state
->session
->smb2
->nonce_high_random
;
3240 nonce_high
+= state
->session
->smb2
->nonce_high
;
3241 nonce_low
= state
->session
->smb2
->nonce_low
;
3244 iov
[num_iov
].iov_base
= state
->smb2
.transform
;
3245 iov
[num_iov
].iov_len
= sizeof(state
->smb2
.transform
);
3248 SBVAL(state
->smb2
.transform
, SMB2_TF_PROTOCOL_ID
, SMB2_TF_MAGIC
);
3249 SBVAL(state
->smb2
.transform
, SMB2_TF_NONCE
,
3251 SBVAL(state
->smb2
.transform
, SMB2_TF_NONCE
+8,
3253 SBVAL(state
->smb2
.transform
, SMB2_TF_SESSION_ID
,
3254 encryption_session_id
);
3256 nbt_len
+= SMB2_TF_HDR_SIZE
;
3260 for (i
=0; i
<num_reqs
; i
++) {
3269 struct smb2_signing_key
*signing_key
= NULL
;
3271 if (!tevent_req_is_in_progress(reqs
[i
])) {
3272 return NT_STATUS_INTERNAL_ERROR
;
3275 state
= tevent_req_data(reqs
[i
], struct smbXcli_req_state
);
3277 if (!smbXcli_conn_is_connected(state
->conn
)) {
3278 return NT_STATUS_CONNECTION_DISCONNECTED
;
3281 if ((state
->conn
->protocol
!= PROTOCOL_NONE
) &&
3282 (state
->conn
->protocol
< PROTOCOL_SMB2_02
)) {
3283 return NT_STATUS_REVISION_MISMATCH
;
3286 opcode
= SVAL(state
->smb2
.hdr
, SMB2_HDR_OPCODE
);
3287 if (opcode
== SMB2_OP_CANCEL
) {
3291 avail
= UINT64_MAX
- state
->conn
->smb2
.mid
;
3293 return NT_STATUS_CONNECTION_ABORTED
;
3296 if (state
->conn
->smb2
.server
.capabilities
& SMB2_CAP_LARGE_MTU
) {
3297 uint32_t max_dyn_len
= 1;
3299 max_dyn_len
= MAX(max_dyn_len
, state
->smb2
.dyn_len
);
3300 max_dyn_len
= MAX(max_dyn_len
, state
->smb2
.max_dyn_len
);
3302 charge
= (max_dyn_len
- 1)/ 65536 + 1;
3307 charge
= MAX(state
->smb2
.credit_charge
, charge
);
3309 avail
= MIN(avail
, state
->conn
->smb2
.cur_credits
);
3310 if (avail
< charge
) {
3311 DBG_ERR("Insufficient credits. "
3312 "%"PRIu64
" available, %"PRIu16
" needed\n",
3314 return NT_STATUS_INTERNAL_ERROR
;
3318 if (state
->conn
->smb2
.max_credits
> state
->conn
->smb2
.cur_credits
) {
3319 credits
= state
->conn
->smb2
.max_credits
-
3320 state
->conn
->smb2
.cur_credits
;
3322 if (state
->conn
->smb2
.max_credits
>= state
->conn
->smb2
.cur_credits
) {
3326 mid
= state
->conn
->smb2
.mid
;
3327 state
->conn
->smb2
.mid
+= charge
;
3328 state
->conn
->smb2
.cur_credits
-= charge
;
3330 if (state
->conn
->smb2
.server
.capabilities
& SMB2_CAP_LARGE_MTU
) {
3331 SSVAL(state
->smb2
.hdr
, SMB2_HDR_CREDIT_CHARGE
, charge
);
3333 SSVAL(state
->smb2
.hdr
, SMB2_HDR_CREDIT
, credits
);
3334 SBVAL(state
->smb2
.hdr
, SMB2_HDR_MESSAGE_ID
, mid
);
3336 state
->smb2
.cancel_flags
= SVAL(state
->smb2
.hdr
, SMB2_HDR_FLAGS
);
3337 state
->smb2
.cancel_flags
&= ~SMB2_HDR_FLAG_CHAINED
;
3338 if (state
->conn
->smb2
.server
.sign_algo
>= SMB2_SIGNING_AES128_GMAC
) {
3339 state
->smb2
.cancel_mid
= mid
;
3341 state
->smb2
.cancel_mid
= 0;
3343 state
->smb2
.cancel_aid
= 0;
3346 if (state
->session
&& encryption_key
== NULL
) {
3348 * We prefer the channel signing key if it is
3351 if (state
->smb2
.should_sign
) {
3352 signing_key
= state
->session
->smb2_channel
.signing_key
;
3356 * If it is a channel binding, we already have the main
3357 * signing key and try that one.
3359 if (signing_key
!= NULL
&&
3360 !smb2_signing_key_valid(signing_key
)) {
3361 signing_key
= state
->session
->smb2
->signing_key
;
3365 * If we do not have any session key yet, we skip the
3366 * signing of SMB2_OP_SESSSETUP requests.
3368 if (signing_key
!= NULL
&&
3369 !smb2_signing_key_valid(signing_key
)) {
3375 iov
[num_iov
].iov_base
= state
->smb2
.hdr
;
3376 iov
[num_iov
].iov_len
= sizeof(state
->smb2
.hdr
);
3379 iov
[num_iov
].iov_base
= discard_const(state
->smb2
.fixed
);
3380 iov
[num_iov
].iov_len
= state
->smb2
.fixed_len
;
3383 if (state
->smb2
.dyn
!= NULL
) {
3384 iov
[num_iov
].iov_base
= discard_const(state
->smb2
.dyn
);
3385 iov
[num_iov
].iov_len
= state
->smb2
.dyn_len
;
3389 reqlen
= sizeof(state
->smb2
.hdr
);
3390 reqlen
+= state
->smb2
.fixed_len
;
3391 reqlen
+= state
->smb2
.dyn_len
;
3393 if (i
< num_reqs
-1) {
3394 if ((reqlen
% 8) > 0) {
3395 uint8_t pad
= 8 - (reqlen
% 8);
3396 iov
[num_iov
].iov_base
= state
->smb2
.pad
;
3397 iov
[num_iov
].iov_len
= pad
;
3401 SIVAL(state
->smb2
.hdr
, SMB2_HDR_NEXT_COMMAND
, reqlen
);
3404 state
->smb2
.encryption_session_id
= encryption_session_id
;
3406 if (signing_key
!= NULL
) {
3409 status
= smb2_signing_sign_pdu(signing_key
,
3410 &iov
[hdr_iov
], num_iov
- hdr_iov
);
3411 if (!NT_STATUS_IS_OK(status
)) {
3418 ret
= smbXcli_req_set_pending(reqs
[i
]);
3420 return NT_STATUS_NO_MEMORY
;
3424 state
= tevent_req_data(reqs
[0], struct smbXcli_req_state
);
3425 _smb_setlen_tcp(state
->length_hdr
, nbt_len
);
3426 iov
[0].iov_base
= state
->length_hdr
;
3427 iov
[0].iov_len
= sizeof(state
->length_hdr
);
3429 if (encryption_key
!= NULL
) {
3431 size_t buflen
= nbt_len
- SMB2_TF_HDR_SIZE
;
3435 buf
= talloc_array(iov
, uint8_t, buflen
);
3437 return NT_STATUS_NO_MEMORY
;
3441 * We copy the buffers before encrypting them,
3442 * this is at least currently needed for the
3443 * to keep state->smb2.hdr.
3445 * Also the callers may expect there buffers
3448 for (vi
= tf_iov
+ 1; vi
< num_iov
; vi
++) {
3449 struct iovec
*v
= &iov
[vi
];
3450 const uint8_t *o
= (const uint8_t *)v
->iov_base
;
3452 memcpy(buf
, o
, v
->iov_len
);
3453 v
->iov_base
= (void *)buf
;
3457 status
= smb2_signing_encrypt_pdu(encryption_key
,
3458 &iov
[tf_iov
], num_iov
- tf_iov
);
3459 if (!NT_STATUS_IS_OK(status
)) {
3464 if (state
->conn
->dispatch_incoming
== NULL
) {
3465 state
->conn
->dispatch_incoming
= smb2cli_conn_dispatch_incoming
;
3468 subreq
= writev_send(state
, state
->ev
, state
->conn
->outgoing
,
3469 state
->conn
->sock_fd
, false, iov
, num_iov
);
3470 if (subreq
== NULL
) {
3471 return NT_STATUS_NO_MEMORY
;
3473 tevent_req_set_callback(subreq
, smb2cli_req_writev_done
, reqs
[0]);
3474 state
->write_req
= subreq
;
3476 return NT_STATUS_OK
;
3479 void smb2cli_req_set_credit_charge(struct tevent_req
*req
, uint16_t charge
)
3481 struct smbXcli_req_state
*state
=
3482 tevent_req_data(req
,
3483 struct smbXcli_req_state
);
3485 state
->smb2
.credit_charge
= charge
;
3488 struct tevent_req
*smb2cli_req_send(TALLOC_CTX
*mem_ctx
,
3489 struct tevent_context
*ev
,
3490 struct smbXcli_conn
*conn
,
3492 uint32_t additional_flags
,
3493 uint32_t clear_flags
,
3494 uint32_t timeout_msec
,
3495 struct smbXcli_tcon
*tcon
,
3496 struct smbXcli_session
*session
,
3497 const uint8_t *fixed
,
3501 uint32_t max_dyn_len
)
3503 struct tevent_req
*req
;
3506 req
= smb2cli_req_create(mem_ctx
, ev
, conn
, cmd
,
3507 additional_flags
, clear_flags
,
3516 if (!tevent_req_is_in_progress(req
)) {
3517 return tevent_req_post(req
, ev
);
3519 status
= smb2cli_req_compound_submit(&req
, 1);
3520 if (tevent_req_nterror(req
, status
)) {
3521 return tevent_req_post(req
, ev
);
3526 static void smb2cli_req_writev_done(struct tevent_req
*subreq
)
3528 struct tevent_req
*req
=
3529 tevent_req_callback_data(subreq
,
3531 struct smbXcli_req_state
*state
=
3532 tevent_req_data(req
,
3533 struct smbXcli_req_state
);
3537 state
->write_req
= NULL
;
3539 nwritten
= writev_recv(subreq
, &err
);
3540 TALLOC_FREE(subreq
);
3541 if (nwritten
== -1) {
3542 /* here, we need to notify all pending requests */
3543 NTSTATUS status
= map_nt_error_from_unix_common(err
);
3544 smbXcli_conn_disconnect(state
->conn
, status
);
3549 static struct smbXcli_session
* smbXcli_session_by_uid(struct smbXcli_conn
*conn
,
3552 struct smbXcli_session
*s
= conn
->sessions
;
3554 for (; s
; s
= s
->next
) {
3555 if (s
->smb2
->session_id
!= uid
) {
3564 static NTSTATUS
smb2cli_inbuf_parse_compound(struct smbXcli_conn
*conn
,
3567 TALLOC_CTX
*mem_ctx
,
3568 struct iovec
**piov
,
3574 uint8_t *first_hdr
= buf
;
3575 size_t verified_buflen
= 0;
3579 iov
= talloc_array(mem_ctx
, struct iovec
, num_iov
);
3581 return NT_STATUS_NO_MEMORY
;
3584 while (taken
< buflen
) {
3585 size_t len
= buflen
- taken
;
3586 uint8_t *hdr
= first_hdr
+ taken
;
3589 size_t next_command_ofs
;
3591 struct iovec
*iov_tmp
;
3593 if (verified_buflen
> taken
) {
3594 len
= verified_buflen
- taken
;
3601 DEBUG(10, ("%d bytes left, expected at least %d\n",
3605 if (IVAL(hdr
, 0) == SMB2_TF_MAGIC
) {
3606 struct smbXcli_session
*s
;
3608 struct iovec tf_iov
[2];
3612 if (len
< SMB2_TF_HDR_SIZE
) {
3613 DEBUG(10, ("%d bytes left, expected at least %d\n",
3614 (int)len
, SMB2_TF_HDR_SIZE
));
3618 tf_len
= SMB2_TF_HDR_SIZE
;
3621 hdr
= first_hdr
+ taken
;
3622 enc_len
= IVAL(tf
, SMB2_TF_MSG_SIZE
);
3623 uid
= BVAL(tf
, SMB2_TF_SESSION_ID
);
3625 if (len
< SMB2_TF_HDR_SIZE
+ enc_len
) {
3626 DEBUG(10, ("%d bytes left, expected at least %d\n",
3628 (int)(SMB2_TF_HDR_SIZE
+ enc_len
)));
3632 s
= smbXcli_session_by_uid(conn
, uid
);
3634 DEBUG(10, ("unknown session_id %llu\n",
3635 (unsigned long long)uid
));
3639 tf_iov
[0].iov_base
= (void *)tf
;
3640 tf_iov
[0].iov_len
= tf_len
;
3641 tf_iov
[1].iov_base
= (void *)hdr
;
3642 tf_iov
[1].iov_len
= enc_len
;
3644 status
= smb2_signing_decrypt_pdu(s
->smb2
->decryption_key
,
3646 if (!NT_STATUS_IS_OK(status
)) {
3651 verified_buflen
= taken
+ enc_len
;
3656 * We need the header plus the body length field
3659 if (len
< SMB2_HDR_BODY
+ 2) {
3660 DEBUG(10, ("%d bytes left, expected at least %d\n",
3661 (int)len
, SMB2_HDR_BODY
));
3664 if (IVAL(hdr
, 0) != SMB2_MAGIC
) {
3665 DEBUG(10, ("Got non-SMB2 PDU: %x\n",
3669 if (SVAL(hdr
, 4) != SMB2_HDR_BODY
) {
3670 DEBUG(10, ("Got HDR len %d, expected %d\n",
3671 SVAL(hdr
, 4), SMB2_HDR_BODY
));
3676 next_command_ofs
= IVAL(hdr
, SMB2_HDR_NEXT_COMMAND
);
3677 body_size
= SVAL(hdr
, SMB2_HDR_BODY
);
3679 if (next_command_ofs
!= 0) {
3680 if (next_command_ofs
< (SMB2_HDR_BODY
+ 2)) {
3683 if (next_command_ofs
> full_size
) {
3686 full_size
= next_command_ofs
;
3688 if (body_size
< 2) {
3691 body_size
&= 0xfffe;
3693 if (body_size
> (full_size
- SMB2_HDR_BODY
)) {
3697 iov_tmp
= talloc_realloc(mem_ctx
, iov
, struct iovec
,
3699 if (iov_tmp
== NULL
) {
3701 return NT_STATUS_NO_MEMORY
;
3704 cur
= &iov
[num_iov
];
3707 cur
[0].iov_base
= tf
;
3708 cur
[0].iov_len
= tf_len
;
3709 cur
[1].iov_base
= hdr
;
3710 cur
[1].iov_len
= SMB2_HDR_BODY
;
3711 cur
[2].iov_base
= hdr
+ SMB2_HDR_BODY
;
3712 cur
[2].iov_len
= body_size
;
3713 cur
[3].iov_base
= hdr
+ SMB2_HDR_BODY
+ body_size
;
3714 cur
[3].iov_len
= full_size
- (SMB2_HDR_BODY
+ body_size
);
3720 *pnum_iov
= num_iov
;
3721 return NT_STATUS_OK
;
3725 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3728 static struct tevent_req
*smb2cli_conn_find_pending(struct smbXcli_conn
*conn
,
3731 size_t num_pending
= talloc_array_length(conn
->pending
);
3734 for (i
=0; i
<num_pending
; i
++) {
3735 struct tevent_req
*req
= conn
->pending
[i
];
3736 struct smbXcli_req_state
*state
=
3737 tevent_req_data(req
,
3738 struct smbXcli_req_state
);
3740 if (mid
== BVAL(state
->smb2
.hdr
, SMB2_HDR_MESSAGE_ID
)) {
3747 static NTSTATUS
smb2cli_conn_dispatch_incoming(struct smbXcli_conn
*conn
,
3748 TALLOC_CTX
*tmp_mem
,
3751 struct tevent_req
*req
;
3752 struct smbXcli_req_state
*state
= NULL
;
3753 struct iovec
*iov
= NULL
;
3754 size_t i
, num_iov
= 0;
3757 struct smbXcli_session
*last_session
= NULL
;
3758 size_t inbuf_len
= smb_len_tcp(inbuf
);
3760 status
= smb2cli_inbuf_parse_compound(conn
,
3761 inbuf
+ NBT_HDR_SIZE
,
3765 if (!NT_STATUS_IS_OK(status
)) {
3769 for (i
=0; i
<num_iov
; i
+=4) {
3770 uint8_t *inbuf_ref
= NULL
;
3771 struct iovec
*cur
= &iov
[i
];
3772 uint8_t *inhdr
= (uint8_t *)cur
[1].iov_base
;
3773 uint16_t opcode
= SVAL(inhdr
, SMB2_HDR_OPCODE
);
3774 uint32_t flags
= IVAL(inhdr
, SMB2_HDR_FLAGS
);
3775 uint64_t mid
= BVAL(inhdr
, SMB2_HDR_MESSAGE_ID
);
3776 uint16_t req_opcode
;
3778 uint16_t credits
= SVAL(inhdr
, SMB2_HDR_CREDIT
);
3779 uint32_t new_credits
;
3780 struct smbXcli_session
*session
= NULL
;
3781 struct smb2_signing_key
*signing_key
= NULL
;
3782 bool was_encrypted
= false;
3784 new_credits
= conn
->smb2
.cur_credits
;
3785 new_credits
+= credits
;
3786 if (new_credits
> UINT16_MAX
) {
3787 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3789 conn
->smb2
.cur_credits
+= credits
;
3791 req
= smb2cli_conn_find_pending(conn
, mid
);
3793 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3795 state
= tevent_req_data(req
, struct smbXcli_req_state
);
3797 req_opcode
= SVAL(state
->smb2
.hdr
, SMB2_HDR_OPCODE
);
3798 if (opcode
!= req_opcode
) {
3799 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3801 req_flags
= SVAL(state
->smb2
.hdr
, SMB2_HDR_FLAGS
);
3803 if (!(flags
& SMB2_HDR_FLAG_REDIRECT
)) {
3804 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3807 status
= NT_STATUS(IVAL(inhdr
, SMB2_HDR_STATUS
));
3808 if ((flags
& SMB2_HDR_FLAG_ASYNC
) &&
3809 NT_STATUS_EQUAL(status
, NT_STATUS_PENDING
)) {
3810 uint64_t async_id
= BVAL(inhdr
, SMB2_HDR_ASYNC_ID
);
3812 if (state
->smb2
.got_async
) {
3813 /* We only expect one STATUS_PENDING response */
3814 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3816 state
->smb2
.got_async
= true;
3819 * async interim responses are not signed,
3820 * even if the SMB2_HDR_FLAG_SIGNED flag
3823 state
->smb2
.cancel_flags
|= SMB2_HDR_FLAG_ASYNC
;
3824 state
->smb2
.cancel_aid
= async_id
;
3826 if (state
->smb2
.notify_async
) {
3827 tevent_req_defer_callback(req
, state
->ev
);
3828 tevent_req_notify_callback(req
);
3833 session
= state
->session
;
3834 if (req_flags
& SMB2_HDR_FLAG_CHAINED
) {
3835 session
= last_session
;
3837 last_session
= session
;
3839 if (flags
& SMB2_HDR_FLAG_SIGNED
) {
3840 uint64_t uid
= BVAL(inhdr
, SMB2_HDR_SESSION_ID
);
3842 if (session
== NULL
) {
3843 session
= smbXcli_session_by_uid(state
->conn
,
3847 if (session
== NULL
) {
3848 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
3851 last_session
= session
;
3852 signing_key
= session
->smb2_channel
.signing_key
;
3855 if (opcode
== SMB2_OP_SESSSETUP
) {
3857 * We prefer the channel signing key, if it is
3860 * If we do not have a channel signing key yet,
3861 * we try the main signing key, if it is not
3862 * the final response.
3864 if (signing_key
!= NULL
&&
3865 !smb2_signing_key_valid(signing_key
) &&
3866 !NT_STATUS_IS_OK(status
)) {
3867 signing_key
= session
->smb2
->signing_key
;
3870 if (signing_key
!= NULL
&&
3871 !smb2_signing_key_valid(signing_key
)) {
3873 * If we do not have a session key to
3874 * verify the signature, we defer the
3875 * signing check to the caller.
3877 * The caller gets NT_STATUS_OK, it
3879 * smb2cli_session_set_session_key()
3881 * smb2cli_session_set_channel_key()
3882 * which will check the signature
3883 * with the channel signing key.
3888 if (!NT_STATUS_IS_OK(status
)) {
3890 * Only check the signature of the last response
3891 * of a successful session auth. This matches
3892 * Windows behaviour for NTLM auth and reauth.
3894 state
->smb2
.require_signed_response
= false;
3898 if (state
->smb2
.should_sign
||
3899 state
->smb2
.require_signed_response
)
3901 if (!(flags
& SMB2_HDR_FLAG_SIGNED
)) {
3902 return NT_STATUS_ACCESS_DENIED
;
3906 if (!smb2_signing_key_valid(signing_key
) &&
3907 state
->smb2
.require_signed_response
) {
3908 signing_key
= session
->smb2_channel
.signing_key
;
3911 if (cur
[0].iov_len
== SMB2_TF_HDR_SIZE
) {
3912 const uint8_t *tf
= (const uint8_t *)cur
[0].iov_base
;
3913 uint64_t uid
= BVAL(tf
, SMB2_TF_SESSION_ID
);
3916 * If the response was encrypted in a SMB2_TRANSFORM
3917 * pdu, which belongs to the correct session,
3918 * we do not need to do signing checks
3920 * It could be the session the response belongs to
3921 * or the session that was used to encrypt the
3922 * SMB2_TRANSFORM request.
3924 if ((session
&& session
->smb2
->session_id
== uid
) ||
3925 (state
->smb2
.encryption_session_id
== uid
)) {
3927 was_encrypted
= true;
3931 if (NT_STATUS_EQUAL(status
, NT_STATUS_USER_SESSION_DELETED
)) {
3933 * if the server returns NT_STATUS_USER_SESSION_DELETED
3934 * the response is not signed and we should
3935 * propagate the NT_STATUS_USER_SESSION_DELETED
3936 * status to the caller.
3938 state
->smb2
.signing_skipped
= true;
3941 if (NT_STATUS_EQUAL(status
, NT_STATUS_REQUEST_OUT_OF_SEQUENCE
)) {
3943 * if the server returns
3944 * NT_STATUS_REQUEST_OUT_OF_SEQUENCE for a session setup
3945 * request, the response is not signed and we should
3946 * propagate the NT_STATUS_REQUEST_OUT_OF_SEQUENCE
3947 * status to the caller
3949 if (opcode
== SMB2_OP_SESSSETUP
) {
3950 state
->smb2
.signing_skipped
= true;
3954 if (NT_STATUS_EQUAL(status
, NT_STATUS_NOT_SUPPORTED
)) {
3956 * if the server returns NT_STATUS_NOT_SUPPORTED
3957 * for a session setup request, the response is not
3958 * signed and we should propagate the NT_STATUS_NOT_SUPPORTED
3959 * status to the caller.
3961 if (opcode
== SMB2_OP_SESSSETUP
) {
3962 state
->smb2
.signing_skipped
= true;
3966 if (NT_STATUS_EQUAL(status
, NT_STATUS_ACCESS_DENIED
)) {
3968 * if the server returns
3969 * NT_STATUS_ACCESS_DENIED for a session setup
3970 * request, the response is not signed and we should
3971 * propagate the NT_STATUS_ACCESS_DENIED
3972 * status to the caller without disconnecting
3973 * the connection because we where not able to
3974 * verify the response signature.
3976 if (opcode
== SMB2_OP_SESSSETUP
) {
3977 state
->smb2
.signing_skipped
= true;
3982 if (NT_STATUS_EQUAL(status
, NT_STATUS_INVALID_PARAMETER
)) {
3984 * if the server returns
3985 * NT_STATUS_INVALID_PARAMETER
3986 * the response might not be encrypted.
3988 if (state
->smb2
.should_encrypt
&& !was_encrypted
) {
3989 state
->smb2
.signing_skipped
= true;
3994 if (state
->smb2
.should_encrypt
&& !was_encrypted
) {
3995 if (!state
->smb2
.signing_skipped
) {
3996 return NT_STATUS_ACCESS_DENIED
;
4000 if (NT_STATUS_EQUAL(status
, NT_STATUS_NETWORK_NAME_DELETED
) ||
4001 NT_STATUS_EQUAL(status
, NT_STATUS_FILE_CLOSED
) ||
4002 NT_STATUS_EQUAL(status
, NT_STATUS_INVALID_PARAMETER
)) {
4004 * if the server returns
4005 * NT_STATUS_NETWORK_NAME_DELETED
4006 * NT_STATUS_FILE_CLOSED
4007 * NT_STATUS_INVALID_PARAMETER
4008 * the response might not be signed
4009 * as this happens before the signing checks.
4011 * If server echos the signature (or all zeros)
4012 * we should report the status from the server
4018 cmp
= mem_equal_const_time(inhdr
+SMB2_HDR_SIGNATURE
,
4019 state
->smb2
.hdr
+SMB2_HDR_SIGNATURE
,
4022 state
->smb2
.signing_skipped
= true;
4028 zero
= all_zero(inhdr
+SMB2_HDR_SIGNATURE
, 16);
4030 state
->smb2
.signing_skipped
= true;
4037 NTSTATUS signing_status
;
4039 signing_status
= smb2_signing_check_pdu(signing_key
,
4041 if (!NT_STATUS_IS_OK(signing_status
)) {
4043 * If the signing check fails, we disconnect
4046 return signing_status
;
4050 if (NT_STATUS_EQUAL(status
, NT_STATUS_NETWORK_SESSION_EXPIRED
) &&
4051 (session
!= NULL
) && session
->disconnect_expired
)
4054 * this should be a short term hack
4055 * until the upper layers have implemented
4056 * re-authentication.
4061 smbXcli_req_unset_pending(req
);
4064 * There might be more than one response
4065 * we need to defer the notifications
4067 if ((num_iov
== 5) && (talloc_array_length(conn
->pending
) == 0)) {
4072 tevent_req_defer_callback(req
, state
->ev
);
4076 * Note: here we use talloc_reference() in a way
4077 * that does not expose it to the caller.
4079 inbuf_ref
= talloc_reference(state
->smb2
.recv_iov
, inbuf
);
4080 if (tevent_req_nomem(inbuf_ref
, req
)) {
4084 /* copy the related buffers */
4085 state
->smb2
.recv_iov
[0] = cur
[1];
4086 state
->smb2
.recv_iov
[1] = cur
[2];
4087 state
->smb2
.recv_iov
[2] = cur
[3];
4089 tevent_req_done(req
);
4093 return NT_STATUS_RETRY
;
4096 return NT_STATUS_OK
;
4099 NTSTATUS
smb2cli_req_recv(struct tevent_req
*req
, TALLOC_CTX
*mem_ctx
,
4100 struct iovec
**piov
,
4101 const struct smb2cli_req_expected_response
*expected
,
4102 size_t num_expected
)
4104 struct smbXcli_req_state
*state
=
4105 tevent_req_data(req
,
4106 struct smbXcli_req_state
);
4109 bool found_status
= false;
4110 bool found_size
= false;
4117 if (tevent_req_is_in_progress(req
) && state
->smb2
.got_async
) {
4118 return NT_STATUS_PENDING
;
4121 if (tevent_req_is_nterror(req
, &status
)) {
4122 for (i
=0; i
< num_expected
; i
++) {
4123 if (NT_STATUS_EQUAL(status
, expected
[i
].status
)) {
4124 return NT_STATUS_UNEXPECTED_NETWORK_ERROR
;
4131 if (num_expected
== 0) {
4132 found_status
= true;
4136 status
= NT_STATUS(IVAL(state
->smb2
.recv_iov
[0].iov_base
, SMB2_HDR_STATUS
));
4137 body_size
= SVAL(state
->smb2
.recv_iov
[1].iov_base
, 0);
4139 for (i
=0; i
< num_expected
; i
++) {
4140 if (!NT_STATUS_EQUAL(status
, expected
[i
].status
)) {
4144 found_status
= true;
4145 if (expected
[i
].body_size
== 0) {
4150 if (expected
[i
].body_size
== body_size
) {
4156 if (!found_status
) {
4160 if (state
->smb2
.signing_skipped
) {
4161 if (num_expected
> 0) {
4162 return NT_STATUS_ACCESS_DENIED
;
4164 if (!NT_STATUS_IS_ERR(status
)) {
4165 return NT_STATUS_ACCESS_DENIED
;
4170 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
4174 *piov
= talloc_move(mem_ctx
, &state
->smb2
.recv_iov
);
4180 NTSTATUS
smb2cli_req_get_sent_iov(struct tevent_req
*req
,
4181 struct iovec
*sent_iov
)
4183 struct smbXcli_req_state
*state
=
4184 tevent_req_data(req
,
4185 struct smbXcli_req_state
);
4187 if (tevent_req_is_in_progress(req
)) {
4188 return NT_STATUS_PENDING
;
4191 sent_iov
[0].iov_base
= state
->smb2
.hdr
;
4192 sent_iov
[0].iov_len
= sizeof(state
->smb2
.hdr
);
4194 sent_iov
[1].iov_base
= discard_const(state
->smb2
.fixed
);
4195 sent_iov
[1].iov_len
= state
->smb2
.fixed_len
;
4197 if (state
->smb2
.dyn
!= NULL
) {
4198 sent_iov
[2].iov_base
= discard_const(state
->smb2
.dyn
);
4199 sent_iov
[2].iov_len
= state
->smb2
.dyn_len
;
4201 sent_iov
[2].iov_base
= NULL
;
4202 sent_iov
[2].iov_len
= 0;
4205 return NT_STATUS_OK
;
4208 static const struct {
4209 enum protocol_types proto
;
4210 const char *smb1_name
;
4211 } smb1cli_prots
[] = {
4212 {PROTOCOL_CORE
, "PC NETWORK PROGRAM 1.0"},
4213 {PROTOCOL_COREPLUS
, "MICROSOFT NETWORKS 1.03"},
4214 {PROTOCOL_LANMAN1
, "MICROSOFT NETWORKS 3.0"},
4215 {PROTOCOL_LANMAN1
, "LANMAN1.0"},
4216 {PROTOCOL_LANMAN2
, "LM1.2X002"},
4217 {PROTOCOL_LANMAN2
, "DOS LANMAN2.1"},
4218 {PROTOCOL_LANMAN2
, "LANMAN2.1"},
4219 {PROTOCOL_LANMAN2
, "Samba"},
4220 {PROTOCOL_NT1
, "NT LANMAN 1.0"},
4221 {PROTOCOL_NT1
, "NT LM 0.12"},
4222 {PROTOCOL_SMB2_02
, "SMB 2.002"},
4223 {PROTOCOL_SMB2_10
, "SMB 2.???"},
4226 static const struct {
4227 enum protocol_types proto
;
4228 uint16_t smb2_dialect
;
4229 } smb2cli_prots
[] = {
4230 {PROTOCOL_SMB2_02
, SMB2_DIALECT_REVISION_202
},
4231 {PROTOCOL_SMB2_10
, SMB2_DIALECT_REVISION_210
},
4232 {PROTOCOL_SMB3_00
, SMB3_DIALECT_REVISION_300
},
4233 {PROTOCOL_SMB3_02
, SMB3_DIALECT_REVISION_302
},
4234 {PROTOCOL_SMB3_11
, SMB3_DIALECT_REVISION_311
},
4237 struct smbXcli_negprot_state
{
4238 struct smbXcli_conn
*conn
;
4239 struct tevent_context
*ev
;
4240 struct smb2_negotiate_contexts
*in_ctx
;
4241 struct smb2_negotiate_contexts
*out_ctx
;
4242 uint32_t timeout_msec
;
4249 static void smbXcli_negprot_invalid_done(struct tevent_req
*subreq
);
4250 static struct tevent_req
*smbXcli_negprot_smb1_subreq(struct smbXcli_negprot_state
*state
);
4251 static void smbXcli_negprot_smb1_done(struct tevent_req
*subreq
);
4252 static struct tevent_req
*smbXcli_negprot_smb2_subreq(struct smbXcli_negprot_state
*state
);
4253 static void smbXcli_negprot_smb2_done(struct tevent_req
*subreq
);
4254 static NTSTATUS
smbXcli_negprot_dispatch_incoming(struct smbXcli_conn
*conn
,
4258 struct tevent_req
*smbXcli_negprot_send(TALLOC_CTX
*mem_ctx
,
4259 struct tevent_context
*ev
,
4260 struct smbXcli_conn
*conn
,
4261 uint32_t timeout_msec
,
4262 enum protocol_types min_protocol
,
4263 enum protocol_types max_protocol
,
4264 uint16_t max_credits
,
4265 struct smb2_negotiate_contexts
*in_ctx
)
4267 struct tevent_req
*req
, *subreq
;
4268 struct smbXcli_negprot_state
*state
;
4270 req
= tevent_req_create(mem_ctx
, &state
,
4271 struct smbXcli_negprot_state
);
4277 state
->in_ctx
= in_ctx
;
4278 state
->timeout_msec
= timeout_msec
;
4280 if (min_protocol
== PROTOCOL_NONE
) {
4281 tevent_req_nterror(req
, NT_STATUS_INVALID_PARAMETER_MIX
);
4282 return tevent_req_post(req
, ev
);
4285 if (max_protocol
== PROTOCOL_NONE
) {
4286 tevent_req_nterror(req
, NT_STATUS_INVALID_PARAMETER_MIX
);
4287 return tevent_req_post(req
, ev
);
4290 if (min_protocol
> max_protocol
) {
4291 tevent_req_nterror(req
, NT_STATUS_INVALID_PARAMETER_MIX
);
4292 return tevent_req_post(req
, ev
);
4295 conn
->min_protocol
= min_protocol
;
4296 conn
->max_protocol
= max_protocol
;
4297 conn
->protocol
= PROTOCOL_NONE
;
4299 if (max_protocol
>= PROTOCOL_SMB2_02
) {
4300 conn
->smb2
.max_credits
= max_credits
;
4303 if ((min_protocol
< PROTOCOL_SMB2_02
) &&
4304 (max_protocol
< PROTOCOL_SMB2_02
)) {
4308 conn
->dispatch_incoming
= smb1cli_conn_dispatch_incoming
;
4310 subreq
= smbXcli_negprot_smb1_subreq(state
);
4311 if (tevent_req_nomem(subreq
, req
)) {
4312 return tevent_req_post(req
, ev
);
4314 tevent_req_set_callback(subreq
, smbXcli_negprot_smb1_done
, req
);
4318 if ((min_protocol
>= PROTOCOL_SMB2_02
) &&
4319 (max_protocol
>= PROTOCOL_SMB2_02
)) {
4323 conn
->dispatch_incoming
= smb2cli_conn_dispatch_incoming
;
4325 subreq
= smbXcli_negprot_smb2_subreq(state
);
4326 if (tevent_req_nomem(subreq
, req
)) {
4327 return tevent_req_post(req
, ev
);
4329 tevent_req_set_callback(subreq
, smbXcli_negprot_smb2_done
, req
);
4334 * We send an SMB1 negprot with the SMB2 dialects
4335 * and expect a SMB1 or a SMB2 response.
4337 * smbXcli_negprot_dispatch_incoming() will fix the
4338 * callback to match protocol of the response.
4340 conn
->dispatch_incoming
= smbXcli_negprot_dispatch_incoming
;
4342 subreq
= smbXcli_negprot_smb1_subreq(state
);
4343 if (tevent_req_nomem(subreq
, req
)) {
4344 return tevent_req_post(req
, ev
);
4346 tevent_req_set_callback(subreq
, smbXcli_negprot_invalid_done
, req
);
4350 static void smbXcli_negprot_invalid_done(struct tevent_req
*subreq
)
4352 struct tevent_req
*req
=
4353 tevent_req_callback_data(subreq
,
4358 * we just want the low level error
4360 status
= tevent_req_simple_recv_ntstatus(subreq
);
4361 TALLOC_FREE(subreq
);
4362 if (tevent_req_nterror(req
, status
)) {
4366 /* this should never happen */
4367 tevent_req_nterror(req
, NT_STATUS_INTERNAL_ERROR
);
4370 static struct tevent_req
*smbXcli_negprot_smb1_subreq(struct smbXcli_negprot_state
*state
)
4373 DATA_BLOB bytes
= data_blob_null
;
4377 /* setup the protocol strings */
4378 for (i
=0; i
< ARRAY_SIZE(smb1cli_prots
); i
++) {
4382 if (smb1cli_prots
[i
].proto
< state
->conn
->min_protocol
) {
4386 if (smb1cli_prots
[i
].proto
> state
->conn
->max_protocol
) {
4390 ok
= data_blob_append(state
, &bytes
, &c
, sizeof(c
));
4396 * We know it is already ascii and
4397 * we want NULL termination.
4399 ok
= data_blob_append(state
, &bytes
,
4400 smb1cli_prots
[i
].smb1_name
,
4401 strlen(smb1cli_prots
[i
].smb1_name
)+1);
4407 smb1cli_req_flags(state
->conn
->max_protocol
,
4408 state
->conn
->smb1
.client
.capabilities
,
4413 return smb1cli_req_send(state
, state
->ev
, state
->conn
,
4417 state
->timeout_msec
,
4418 0xFFFE, 0, NULL
, /* pid, tid, session */
4419 0, NULL
, /* wct, vwv */
4420 bytes
.length
, bytes
.data
);
4423 static void smbXcli_negprot_smb1_done(struct tevent_req
*subreq
)
4425 struct tevent_req
*req
=
4426 tevent_req_callback_data(subreq
,
4428 struct smbXcli_negprot_state
*state
=
4429 tevent_req_data(req
,
4430 struct smbXcli_negprot_state
);
4431 struct smbXcli_conn
*conn
= state
->conn
;
4432 struct iovec
*recv_iov
= NULL
;
4433 uint8_t *inhdr
= NULL
;
4441 size_t num_prots
= 0;
4443 uint32_t client_capabilities
= conn
->smb1
.client
.capabilities
;
4444 uint32_t both_capabilities
;
4445 uint32_t server_capabilities
= 0;
4446 uint32_t capabilities
;
4447 uint32_t client_max_xmit
= conn
->smb1
.client
.max_xmit
;
4448 uint32_t server_max_xmit
= 0;
4450 uint32_t server_max_mux
= 0;
4451 uint16_t server_security_mode
= 0;
4452 uint32_t server_session_key
= 0;
4453 bool server_readbraw
= false;
4454 bool server_writebraw
= false;
4455 bool server_lockread
= false;
4456 bool server_writeunlock
= false;
4457 struct GUID server_guid
= GUID_zero();
4458 DATA_BLOB server_gss_blob
= data_blob_null
;
4459 uint8_t server_challenge
[8];
4460 char *server_workgroup
= NULL
;
4461 char *server_name
= NULL
;
4462 int server_time_zone
= 0;
4463 NTTIME server_system_time
= 0;
4464 static const struct smb1cli_req_expected_response expected
[] = {
4466 .status
= NT_STATUS_OK
,
4467 .wct
= 0x11, /* NT1 */
4470 .status
= NT_STATUS_OK
,
4471 .wct
= 0x0D, /* LM */
4474 .status
= NT_STATUS_OK
,
4475 .wct
= 0x01, /* CORE */
4479 ZERO_STRUCT(server_challenge
);
4481 status
= smb1cli_req_recv(subreq
, state
,
4486 NULL
, /* pvwv_offset */
4489 NULL
, /* pbytes_offset */
4491 expected
, ARRAY_SIZE(expected
));
4492 TALLOC_FREE(subreq
);
4493 if (tevent_req_nterror(req
, status
)) {
4496 if (inhdr
== NULL
) {
4497 tevent_req_nterror(req
, NT_STATUS_INTERNAL_ERROR
);
4501 flags
= CVAL(inhdr
, HDR_FLG
);
4503 protnum
= SVAL(vwv
, 0);
4505 for (i
=0; i
< ARRAY_SIZE(smb1cli_prots
); i
++) {
4506 if (smb1cli_prots
[i
].proto
< state
->conn
->min_protocol
) {
4510 if (smb1cli_prots
[i
].proto
> state
->conn
->max_protocol
) {
4514 if (protnum
!= num_prots
) {
4519 conn
->protocol
= smb1cli_prots
[i
].proto
;
4523 if (conn
->protocol
== PROTOCOL_NONE
) {
4524 DBG_ERR("No compatible protocol selected by server.\n");
4525 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4529 if ((conn
->protocol
< PROTOCOL_NT1
) && conn
->mandatory_signing
) {
4530 DEBUG(0,("smbXcli_negprot: SMB signing is mandatory "
4531 "and the selected protocol level doesn't support it.\n"));
4532 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
4536 if (flags
& FLAG_SUPPORT_LOCKREAD
) {
4537 server_lockread
= true;
4538 server_writeunlock
= true;
4541 if (conn
->protocol
>= PROTOCOL_NT1
) {
4542 const char *client_signing
= NULL
;
4543 bool server_mandatory
= false;
4544 bool server_allowed
= false;
4545 const char *server_signing
= NULL
;
4550 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4555 server_security_mode
= CVAL(vwv
+ 1, 0);
4556 server_max_mux
= SVAL(vwv
+ 1, 1);
4557 server_max_xmit
= IVAL(vwv
+ 3, 1);
4558 server_session_key
= IVAL(vwv
+ 7, 1);
4559 server_time_zone
= SVALS(vwv
+ 15, 1);
4560 server_time_zone
*= 60;
4561 /* this time arrives in real GMT */
4562 server_system_time
= BVAL(vwv
+ 11, 1);
4563 server_capabilities
= IVAL(vwv
+ 9, 1);
4565 key_len
= CVAL(vwv
+ 16, 1);
4567 if (server_capabilities
& CAP_RAW_MODE
) {
4568 server_readbraw
= true;
4569 server_writebraw
= true;
4571 if (server_capabilities
& CAP_LOCK_AND_READ
) {
4572 server_lockread
= true;
4575 if (server_capabilities
& CAP_EXTENDED_SECURITY
) {
4576 DATA_BLOB blob1
, blob2
;
4578 if (num_bytes
< 16) {
4579 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4583 blob1
= data_blob_const(bytes
, 16);
4584 status
= GUID_from_data_blob(&blob1
, &server_guid
);
4585 if (tevent_req_nterror(req
, status
)) {
4589 blob1
= data_blob_const(bytes
+16, num_bytes
-16);
4590 blob2
= data_blob_dup_talloc(state
, blob1
);
4591 if (blob1
.length
> 0 &&
4592 tevent_req_nomem(blob2
.data
, req
)) {
4595 server_gss_blob
= blob2
;
4597 DATA_BLOB blob1
, blob2
;
4599 if (num_bytes
< key_len
) {
4600 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4604 if (key_len
!= 0 && key_len
!= 8) {
4605 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4610 memcpy(server_challenge
, bytes
, 8);
4613 blob1
= data_blob_const(bytes
+key_len
, num_bytes
-key_len
);
4614 blob2
= data_blob_const(bytes
+key_len
, num_bytes
-key_len
);
4615 if (blob1
.length
> 0) {
4618 len
= utf16_len_n(blob1
.data
,
4622 ok
= convert_string_talloc(state
,
4630 status
= map_nt_error_from_unix_common(errno
);
4631 tevent_req_nterror(req
, status
);
4636 blob2
.data
+= blob1
.length
;
4637 blob2
.length
-= blob1
.length
;
4638 if (blob2
.length
> 0) {
4641 ok
= convert_string_talloc(state
,
4649 status
= map_nt_error_from_unix_common(errno
);
4650 tevent_req_nterror(req
, status
);
4656 client_signing
= "disabled";
4657 if (conn
->allow_signing
) {
4658 client_signing
= "allowed";
4660 if (conn
->mandatory_signing
) {
4661 client_signing
= "required";
4664 server_signing
= "not supported";
4665 if (server_security_mode
& NEGOTIATE_SECURITY_SIGNATURES_ENABLED
) {
4666 server_signing
= "supported";
4667 server_allowed
= true;
4668 } else if (conn
->mandatory_signing
) {
4670 * We have mandatory signing as client
4671 * lets assume the server will look at our
4672 * FLAGS2_SMB_SECURITY_SIGNATURES_REQUIRED
4673 * flag in the session setup
4675 server_signing
= "not announced";
4676 server_allowed
= true;
4678 if (server_security_mode
& NEGOTIATE_SECURITY_SIGNATURES_REQUIRED
) {
4679 server_signing
= "required";
4680 server_mandatory
= true;
4683 ok
= smb1_signing_set_negotiated(conn
->smb1
.signing
,
4687 DEBUG(1,("cli_negprot: SMB signing is required, "
4688 "but client[%s] and server[%s] mismatch\n",
4689 client_signing
, server_signing
));
4690 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
4694 } else if (conn
->protocol
>= PROTOCOL_LANMAN1
) {
4700 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4704 server_security_mode
= SVAL(vwv
+ 1, 0);
4705 server_max_xmit
= SVAL(vwv
+ 2, 0);
4706 server_max_mux
= SVAL(vwv
+ 3, 0);
4707 server_readbraw
= ((SVAL(vwv
+ 5, 0) & 0x1) != 0);
4708 server_writebraw
= ((SVAL(vwv
+ 5, 0) & 0x2) != 0);
4709 server_session_key
= IVAL(vwv
+ 6, 0);
4710 server_time_zone
= SVALS(vwv
+ 10, 0);
4711 server_time_zone
*= 60;
4712 /* this time is converted to GMT by make_unix_date */
4713 t
= pull_dos_date((const uint8_t *)(vwv
+ 8), server_time_zone
);
4714 unix_to_nt_time(&server_system_time
, t
);
4715 key_len
= SVAL(vwv
+ 11, 0);
4717 if (num_bytes
< key_len
) {
4718 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4722 if (key_len
!= 0 && key_len
!= 8) {
4723 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4728 memcpy(server_challenge
, bytes
, 8);
4731 blob1
= data_blob_const(bytes
+key_len
, num_bytes
-key_len
);
4732 if (blob1
.length
> 0) {
4736 len
= utf16_len_n(blob1
.data
,
4740 ok
= convert_string_talloc(state
,
4748 status
= map_nt_error_from_unix_common(errno
);
4749 tevent_req_nterror(req
, status
);
4755 /* the old core protocol */
4756 server_time_zone
= get_time_zone(time(NULL
));
4757 server_max_xmit
= 1024;
4761 if (server_max_xmit
< 1024) {
4762 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4766 if (server_max_mux
< 1) {
4767 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
4772 * Now calculate the negotiated capabilities
4773 * based on the mask for:
4774 * - client only flags
4775 * - flags used in both directions
4776 * - server only flags
4778 both_capabilities
= client_capabilities
& server_capabilities
;
4779 capabilities
= client_capabilities
& SMB_CAP_CLIENT_MASK
;
4780 capabilities
|= both_capabilities
& SMB_CAP_BOTH_MASK
;
4781 capabilities
|= server_capabilities
& SMB_CAP_SERVER_MASK
;
4783 max_xmit
= MIN(client_max_xmit
, server_max_xmit
);
4785 conn
->smb1
.server
.capabilities
= server_capabilities
;
4786 conn
->smb1
.capabilities
= capabilities
;
4788 conn
->smb1
.server
.max_xmit
= server_max_xmit
;
4789 conn
->smb1
.max_xmit
= max_xmit
;
4791 conn
->smb1
.server
.max_mux
= server_max_mux
;
4793 conn
->smb1
.server
.security_mode
= server_security_mode
;
4795 conn
->smb1
.server
.readbraw
= server_readbraw
;
4796 conn
->smb1
.server
.writebraw
= server_writebraw
;
4797 conn
->smb1
.server
.lockread
= server_lockread
;
4798 conn
->smb1
.server
.writeunlock
= server_writeunlock
;
4800 conn
->smb1
.server
.session_key
= server_session_key
;
4802 talloc_steal(conn
, server_gss_blob
.data
);
4803 conn
->smb1
.server
.gss_blob
= server_gss_blob
;
4804 conn
->smb1
.server
.guid
= server_guid
;
4805 memcpy(conn
->smb1
.server
.challenge
, server_challenge
, 8);
4806 conn
->smb1
.server
.workgroup
= talloc_move(conn
, &server_workgroup
);
4807 conn
->smb1
.server
.name
= talloc_move(conn
, &server_name
);
4809 conn
->smb1
.server
.time_zone
= server_time_zone
;
4810 conn
->smb1
.server
.system_time
= server_system_time
;
4812 tevent_req_done(req
);
4815 static size_t smbXcli_padding_helper(uint32_t offset
, size_t n
)
4817 if ((offset
& (n
-1)) == 0) return 0;
4818 return n
- (offset
& (n
-1));
4821 static struct tevent_req
*smbXcli_negprot_smb2_subreq(struct smbXcli_negprot_state
*state
)
4825 uint16_t dialect_count
= 0;
4826 DATA_BLOB dyn
= data_blob_null
;
4828 for (i
=0; i
< ARRAY_SIZE(smb2cli_prots
); i
++) {
4832 if (smb2cli_prots
[i
].proto
< state
->conn
->min_protocol
) {
4836 if (smb2cli_prots
[i
].proto
> state
->conn
->max_protocol
) {
4840 SSVAL(val
, 0, smb2cli_prots
[i
].smb2_dialect
);
4842 ok
= data_blob_append(state
, &dyn
, val
, sizeof(val
));
4850 buf
= state
->smb2
.fixed
;
4852 SSVAL(buf
, 2, dialect_count
);
4853 SSVAL(buf
, 4, state
->conn
->smb2
.client
.security_mode
);
4854 SSVAL(buf
, 6, 0); /* Reserved */
4855 if (state
->conn
->max_protocol
>= PROTOCOL_SMB3_00
) {
4856 SIVAL(buf
, 8, state
->conn
->smb2
.client
.capabilities
);
4858 SIVAL(buf
, 8, 0); /* Capabilities */
4860 if (state
->conn
->max_protocol
>= PROTOCOL_SMB2_10
) {
4862 struct GUID_ndr_buf guid_buf
= { .buf
= {0}, };
4864 status
= GUID_to_ndr_buf(&state
->conn
->smb2
.client
.guid
,
4866 if (!NT_STATUS_IS_OK(status
)) {
4869 memcpy(buf
+12, guid_buf
.buf
, 16); /* ClientGuid */
4871 memset(buf
+12, 0, 16); /* ClientGuid */
4874 if (state
->conn
->max_protocol
>= PROTOCOL_SMB3_11
) {
4875 const struct smb3_signing_capabilities
*client_sign_algos
=
4876 &state
->conn
->smb2
.client
.smb3_capabilities
.signing
;
4877 const struct smb3_encryption_capabilities
*client_ciphers
=
4878 &state
->conn
->smb2
.client
.smb3_capabilities
.encryption
;
4880 struct smb2_negotiate_contexts c
= { .num_contexts
= 0, };
4881 uint8_t *netname_utf16
= NULL
;
4882 size_t netname_utf16_len
= 0;
4886 const uint8_t zeros
[8] = {0, };
4890 SSVAL(p
, 0, 1); /* HashAlgorithmCount */
4891 SSVAL(p
, 2, 32); /* SaltLength */
4892 SSVAL(p
, 4, SMB2_PREAUTH_INTEGRITY_SHA512
);
4893 generate_random_buffer(p
+ 6, 32);
4895 status
= smb2_negotiate_context_add(
4896 state
, &c
, SMB2_PREAUTH_INTEGRITY_CAPABILITIES
, p
, 38);
4897 if (!NT_STATUS_IS_OK(status
)) {
4901 if (client_ciphers
->num_algos
> 0) {
4903 SSVAL(p
, ofs
, client_ciphers
->num_algos
);
4906 for (i
= 0; i
< client_ciphers
->num_algos
; i
++) {
4907 size_t next_ofs
= ofs
+ 2;
4908 SMB_ASSERT(next_ofs
< ARRAY_SIZE(p
));
4909 SSVAL(p
, ofs
, client_ciphers
->algos
[i
]);
4913 status
= smb2_negotiate_context_add(
4914 state
, &c
, SMB2_ENCRYPTION_CAPABILITIES
, p
, ofs
);
4915 if (!NT_STATUS_IS_OK(status
)) {
4920 if (client_sign_algos
->num_algos
> 0) {
4922 SSVAL(p
, ofs
, client_sign_algos
->num_algos
);
4925 for (i
= 0; i
< client_sign_algos
->num_algos
; i
++) {
4926 size_t next_ofs
= ofs
+ 2;
4927 SMB_ASSERT(next_ofs
< ARRAY_SIZE(p
));
4928 SSVAL(p
, ofs
, client_sign_algos
->algos
[i
]);
4932 status
= smb2_negotiate_context_add(
4933 state
, &c
, SMB2_SIGNING_CAPABILITIES
, p
, ofs
);
4934 if (!NT_STATUS_IS_OK(status
)) {
4939 ok
= convert_string_talloc(state
, CH_UNIX
, CH_UTF16
,
4940 state
->conn
->remote_name
,
4941 strlen(state
->conn
->remote_name
),
4942 &netname_utf16
, &netname_utf16_len
);
4947 status
= smb2_negotiate_context_add(state
, &c
,
4948 SMB2_NETNAME_NEGOTIATE_CONTEXT_ID
,
4949 netname_utf16
, netname_utf16_len
);
4950 if (!NT_STATUS_IS_OK(status
)) {
4954 if (state
->in_ctx
!= NULL
) {
4955 struct smb2_negotiate_contexts
*ctxs
= state
->in_ctx
;
4957 for (i
=0; i
<ctxs
->num_contexts
; i
++) {
4958 struct smb2_negotiate_context
*ctx
=
4961 status
= smb2_negotiate_context_add(
4967 if (!NT_STATUS_IS_OK(status
)) {
4973 status
= smb2_negotiate_context_push(state
, &b
, c
);
4974 if (!NT_STATUS_IS_OK(status
)) {
4978 offset
= SMB2_HDR_BODY
+ sizeof(state
->smb2
.fixed
) + dyn
.length
;
4979 pad
= smbXcli_padding_helper(offset
, 8);
4981 ok
= data_blob_append(state
, &dyn
, zeros
, pad
);
4987 ok
= data_blob_append(state
, &dyn
, b
.data
, b
.length
);
4992 SIVAL(buf
, 28, offset
); /* NegotiateContextOffset */
4993 SSVAL(buf
, 32, c
.num_contexts
); /* NegotiateContextCount */
4994 SSVAL(buf
, 34, 0); /* Reserved */
4996 SBVAL(buf
, 28, 0); /* Reserved/ClientStartTime */
4999 return smb2cli_req_send(state
, state
->ev
,
5000 state
->conn
, SMB2_OP_NEGPROT
,
5002 state
->timeout_msec
,
5003 NULL
, NULL
, /* tcon, session */
5004 state
->smb2
.fixed
, sizeof(state
->smb2
.fixed
),
5005 dyn
.data
, dyn
.length
,
5006 UINT16_MAX
); /* max_dyn_len */
5009 static NTSTATUS
smbXcli_negprot_smb3_check_capabilities(struct tevent_req
*req
);
5011 static void smbXcli_negprot_smb2_done(struct tevent_req
*subreq
)
5013 struct tevent_req
*req
=
5014 tevent_req_callback_data(subreq
,
5016 struct smbXcli_negprot_state
*state
=
5017 tevent_req_data(req
,
5018 struct smbXcli_negprot_state
);
5019 struct smbXcli_conn
*conn
= state
->conn
;
5020 size_t security_offset
, security_length
;
5023 struct iovec
*iov
= NULL
;
5026 uint16_t dialect_revision
;
5027 uint32_t negotiate_context_offset
= 0;
5028 uint16_t negotiate_context_count
= 0;
5029 DATA_BLOB negotiate_context_blob
= data_blob_null
;
5033 struct smb2_negotiate_context
*preauth
= NULL
;
5034 uint16_t hash_count
;
5035 uint16_t salt_length
;
5036 uint16_t hash_selected
;
5037 gnutls_hash_hd_t hash_hnd
= NULL
;
5038 struct smb2_negotiate_context
*sign_algo
= NULL
;
5039 struct smb2_negotiate_context
*cipher
= NULL
;
5040 struct smb2_negotiate_context
*posix
= NULL
;
5041 struct iovec sent_iov
[3] = {{0}, {0}, {0}};
5042 static const struct smb2cli_req_expected_response expected
[] = {
5044 .status
= NT_STATUS_OK
,
5050 status
= smb2cli_req_recv(subreq
, state
, &iov
,
5051 expected
, ARRAY_SIZE(expected
));
5052 if (tevent_req_nterror(req
, status
)) {
5056 tevent_req_nterror(req
, NT_STATUS_INTERNAL_ERROR
);
5060 body
= (uint8_t *)iov
[1].iov_base
;
5062 dialect_revision
= SVAL(body
, 4);
5064 for (i
=0; i
< ARRAY_SIZE(smb2cli_prots
); i
++) {
5065 if (smb2cli_prots
[i
].proto
< state
->conn
->min_protocol
) {
5069 if (smb2cli_prots
[i
].proto
> state
->conn
->max_protocol
) {
5073 if (smb2cli_prots
[i
].smb2_dialect
!= dialect_revision
) {
5077 conn
->protocol
= smb2cli_prots
[i
].proto
;
5081 if (conn
->protocol
== PROTOCOL_NONE
) {
5082 TALLOC_FREE(subreq
);
5084 if (state
->conn
->min_protocol
>= PROTOCOL_SMB2_02
) {
5085 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5089 if (dialect_revision
!= SMB2_DIALECT_REVISION_2FF
) {
5090 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5094 /* make sure we do not loop forever */
5095 state
->conn
->min_protocol
= PROTOCOL_SMB2_02
;
5098 * send a SMB2 negprot, in order to negotiate
5101 subreq
= smbXcli_negprot_smb2_subreq(state
);
5102 if (tevent_req_nomem(subreq
, req
)) {
5105 tevent_req_set_callback(subreq
, smbXcli_negprot_smb2_done
, req
);
5109 conn
->smb2
.server
.security_mode
= SVAL(body
, 2);
5110 if (conn
->protocol
>= PROTOCOL_SMB3_11
) {
5111 negotiate_context_count
= SVAL(body
, 6);
5114 blob
= data_blob_const(body
+ 8, 16);
5115 status
= GUID_from_data_blob(&blob
, &conn
->smb2
.server
.guid
);
5116 if (tevent_req_nterror(req
, status
)) {
5120 conn
->smb2
.server
.capabilities
= IVAL(body
, 24);
5121 conn
->smb2
.server
.max_trans_size
= IVAL(body
, 28);
5122 conn
->smb2
.server
.max_read_size
= IVAL(body
, 32);
5123 conn
->smb2
.server
.max_write_size
= IVAL(body
, 36);
5124 conn
->smb2
.server
.system_time
= BVAL(body
, 40);
5125 conn
->smb2
.server
.start_time
= BVAL(body
, 48);
5127 if (conn
->smb2
.server
.max_trans_size
== 0 ||
5128 conn
->smb2
.server
.max_read_size
== 0 ||
5129 conn
->smb2
.server
.max_write_size
== 0) {
5131 * We can't connect to servers we can't
5132 * do any operations on.
5134 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5138 security_offset
= SVAL(body
, 56);
5139 security_length
= SVAL(body
, 58);
5141 if (security_offset
== 0) {
5143 * Azure sends security_offset = 0 and security_length = 0
5145 * We just set security_offset to the expected value
5146 * in order to allow the further logic to work
5149 if (security_length
!= 0) {
5150 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5153 security_offset
= SMB2_HDR_BODY
+ iov
[1].iov_len
;
5156 if (security_offset
!= SMB2_HDR_BODY
+ iov
[1].iov_len
) {
5157 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5161 if (security_length
> iov
[2].iov_len
) {
5162 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5166 conn
->smb2
.server
.gss_blob
= data_blob_talloc(conn
,
5169 if (tevent_req_nomem(conn
->smb2
.server
.gss_blob
.data
, req
)) {
5173 if (conn
->protocol
>= PROTOCOL_SMB3_00
) {
5174 conn
->smb2
.server
.sign_algo
= SMB2_SIGNING_AES128_CMAC
;
5176 conn
->smb2
.server
.sign_algo
= SMB2_SIGNING_HMAC_SHA256
;
5179 if (conn
->protocol
< PROTOCOL_SMB3_11
) {
5180 TALLOC_FREE(subreq
);
5182 if (conn
->smb2
.server
.capabilities
& SMB2_CAP_ENCRYPTION
) {
5183 conn
->smb2
.server
.cipher
= SMB2_ENCRYPTION_AES128_CCM
;
5186 status
= smbXcli_negprot_smb3_check_capabilities(req
);
5187 if (tevent_req_nterror(req
, status
)) {
5191 tevent_req_done(req
);
5196 * Here we are now at SMB3_11, so encryption should be
5197 * negotiated via context, not capabilities.
5200 if (conn
->smb2
.server
.capabilities
& SMB2_CAP_ENCRYPTION
) {
5202 * Server set SMB2_CAP_ENCRYPTION capability,
5203 * but *SHOULD* not, not *MUST* not. Just mask it off.
5204 * NetApp seems to do this:
5205 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=13009
5207 conn
->smb2
.server
.capabilities
&= ~SMB2_CAP_ENCRYPTION
;
5210 negotiate_context_offset
= IVAL(body
, 60);
5211 if (negotiate_context_offset
< security_offset
) {
5212 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5216 ctx_ofs
= negotiate_context_offset
- security_offset
;
5217 if (ctx_ofs
> iov
[2].iov_len
) {
5218 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5221 avail
= iov
[2].iov_len
- security_length
;
5222 needed
= iov
[2].iov_len
- ctx_ofs
;
5223 if (needed
> avail
) {
5224 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5228 negotiate_context_blob
.data
= (uint8_t *)iov
[2].iov_base
;
5229 negotiate_context_blob
.length
= iov
[2].iov_len
;
5231 negotiate_context_blob
.data
+= ctx_ofs
;
5232 negotiate_context_blob
.length
-= ctx_ofs
;
5234 state
->out_ctx
= talloc_zero(state
, struct smb2_negotiate_contexts
);
5235 if (tevent_req_nomem(state
->out_ctx
, req
)) {
5239 status
= smb2_negotiate_context_parse(state
->out_ctx
,
5240 negotiate_context_blob
,
5241 negotiate_context_count
,
5243 if (NT_STATUS_EQUAL(status
, NT_STATUS_INVALID_PARAMETER
)) {
5244 status
= NT_STATUS_INVALID_NETWORK_RESPONSE
;
5246 if (tevent_req_nterror(req
, status
)) {
5250 preauth
= smb2_negotiate_context_find(
5251 state
->out_ctx
, SMB2_PREAUTH_INTEGRITY_CAPABILITIES
);
5252 if (preauth
== NULL
) {
5253 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5257 if (preauth
->data
.length
< 6) {
5258 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5262 hash_count
= SVAL(preauth
->data
.data
, 0);
5263 salt_length
= SVAL(preauth
->data
.data
, 2);
5264 hash_selected
= SVAL(preauth
->data
.data
, 4);
5266 if (hash_count
!= 1) {
5267 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5271 if (preauth
->data
.length
!= (6 + salt_length
)) {
5272 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5276 if (hash_selected
!= SMB2_PREAUTH_INTEGRITY_SHA512
) {
5277 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5281 sign_algo
= smb2_negotiate_context_find(
5282 state
->out_ctx
, SMB2_SIGNING_CAPABILITIES
);
5283 if (sign_algo
!= NULL
) {
5284 const struct smb3_signing_capabilities
*client_sign_algos
=
5285 &state
->conn
->smb2
.client
.smb3_capabilities
.signing
;
5286 bool found_selected
= false;
5287 uint16_t sign_algo_count
;
5288 uint16_t sign_algo_selected
;
5290 if (client_sign_algos
->num_algos
== 0) {
5292 * We didn't ask for SMB2_ENCRYPTION_CAPABILITIES
5294 tevent_req_nterror(req
,
5295 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5299 if (sign_algo
->data
.length
< 2) {
5300 tevent_req_nterror(req
,
5301 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5305 sign_algo_count
= SVAL(sign_algo
->data
.data
, 0);
5306 if (sign_algo_count
!= 1) {
5307 tevent_req_nterror(req
,
5308 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5312 if (sign_algo
->data
.length
< (2 + 2 * sign_algo_count
)) {
5313 tevent_req_nterror(req
,
5314 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5317 sign_algo_selected
= SVAL(sign_algo
->data
.data
, 2);
5319 for (i
= 0; i
< client_sign_algos
->num_algos
; i
++) {
5320 if (client_sign_algos
->algos
[i
] == sign_algo_selected
) {
5324 found_selected
= true;
5329 if (!found_selected
) {
5331 * The server send a sign_algo we didn't offer.
5333 tevent_req_nterror(req
,
5334 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5338 conn
->smb2
.server
.sign_algo
= sign_algo_selected
;
5341 cipher
= smb2_negotiate_context_find(
5342 state
->out_ctx
, SMB2_ENCRYPTION_CAPABILITIES
);
5343 if (cipher
!= NULL
) {
5344 const struct smb3_encryption_capabilities
*client_ciphers
=
5345 &state
->conn
->smb2
.client
.smb3_capabilities
.encryption
;
5346 bool found_selected
= false;
5347 uint16_t cipher_count
;
5348 uint16_t cipher_selected
;
5350 if (client_ciphers
->num_algos
== 0) {
5352 * We didn't ask for SMB2_ENCRYPTION_CAPABILITIES
5354 tevent_req_nterror(req
,
5355 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5359 if (cipher
->data
.length
< 2) {
5360 tevent_req_nterror(req
,
5361 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5365 cipher_count
= SVAL(cipher
->data
.data
, 0);
5366 if (cipher_count
!= 1) {
5367 tevent_req_nterror(req
,
5368 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5372 if (cipher
->data
.length
< (2 + 2 * cipher_count
)) {
5373 tevent_req_nterror(req
,
5374 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5377 cipher_selected
= SVAL(cipher
->data
.data
, 2);
5379 for (i
= 0; i
< client_ciphers
->num_algos
; i
++) {
5380 if (cipher_selected
== SMB2_ENCRYPTION_NONE
) {
5382 * encryption not supported
5384 found_selected
= true;
5387 if (client_ciphers
->algos
[i
] == cipher_selected
) {
5391 found_selected
= true;
5396 if (!found_selected
) {
5398 * The server send a cipher we didn't offer.
5400 tevent_req_nterror(req
,
5401 NT_STATUS_INVALID_NETWORK_RESPONSE
);
5405 conn
->smb2
.server
.cipher
= cipher_selected
;
5408 posix
= smb2_negotiate_context_find(
5409 state
->out_ctx
, SMB2_POSIX_EXTENSIONS_AVAILABLE
);
5410 if (posix
!= NULL
) {
5411 DATA_BLOB posix_blob
= data_blob_const(
5412 SMB2_CREATE_TAG_POSIX
, strlen(SMB2_CREATE_TAG_POSIX
));
5413 int cmp
= data_blob_cmp(&posix
->data
, &posix_blob
);
5415 conn
->smb2
.server
.smb311_posix
= (cmp
== 0);
5419 /* First we hash the request */
5420 smb2cli_req_get_sent_iov(subreq
, sent_iov
);
5422 rc
= gnutls_hash_init(&hash_hnd
, GNUTLS_DIG_SHA512
);
5424 tevent_req_nterror(req
,
5425 gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
));
5429 rc
= gnutls_hash(hash_hnd
,
5430 conn
->smb2
.preauth_sha512
,
5431 sizeof(conn
->smb2
.preauth_sha512
));
5433 gnutls_hash_deinit(hash_hnd
, NULL
);
5434 tevent_req_nterror(req
,
5435 gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
));
5438 for (i
= 0; i
< 3; i
++) {
5439 rc
= gnutls_hash(hash_hnd
,
5440 sent_iov
[i
].iov_base
,
5441 sent_iov
[i
].iov_len
);
5443 gnutls_hash_deinit(hash_hnd
, NULL
);
5444 tevent_req_nterror(req
,
5445 gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
));
5450 /* This resets the hash state */
5451 gnutls_hash_output(hash_hnd
, conn
->smb2
.preauth_sha512
);
5452 TALLOC_FREE(subreq
);
5454 /* And now we hash the response */
5455 rc
= gnutls_hash(hash_hnd
,
5456 conn
->smb2
.preauth_sha512
,
5457 sizeof(conn
->smb2
.preauth_sha512
));
5459 gnutls_hash_deinit(hash_hnd
, NULL
);
5460 tevent_req_nterror(req
,
5461 gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
));
5464 for (i
= 0; i
< 3; i
++) {
5465 rc
= gnutls_hash(hash_hnd
,
5469 gnutls_hash_deinit(hash_hnd
, NULL
);
5470 tevent_req_nterror(req
,
5471 gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
));
5475 gnutls_hash_deinit(hash_hnd
, conn
->smb2
.preauth_sha512
);
5477 tevent_req_nterror(req
,
5478 NT_STATUS_UNSUCCESSFUL
);
5482 status
= smbXcli_negprot_smb3_check_capabilities(req
);
5483 if (tevent_req_nterror(req
, status
)) {
5487 tevent_req_done(req
);
5490 static NTSTATUS
smbXcli_negprot_smb3_check_capabilities(struct tevent_req
*req
)
5492 struct smbXcli_negprot_state
*state
=
5493 tevent_req_data(req
,
5494 struct smbXcli_negprot_state
);
5495 struct smbXcli_conn
*conn
= state
->conn
;
5497 return smb311_capabilities_check(&conn
->smb2
.client
.smb3_capabilities
,
5500 NT_STATUS_ACCESS_DENIED
,
5503 conn
->smb2
.server
.sign_algo
,
5504 conn
->smb2
.server
.cipher
);
5507 static NTSTATUS
smbXcli_negprot_dispatch_incoming(struct smbXcli_conn
*conn
,
5508 TALLOC_CTX
*tmp_mem
,
5511 size_t num_pending
= talloc_array_length(conn
->pending
);
5512 struct tevent_req
*subreq
;
5513 struct smbXcli_req_state
*substate
;
5514 struct tevent_req
*req
;
5515 uint32_t protocol_magic
;
5516 size_t inbuf_len
= smb_len_nbt(inbuf
);
5518 if (num_pending
!= 1) {
5519 return NT_STATUS_INTERNAL_ERROR
;
5522 if (inbuf_len
< 4) {
5523 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
5526 subreq
= conn
->pending
[0];
5527 substate
= tevent_req_data(subreq
, struct smbXcli_req_state
);
5528 req
= tevent_req_callback_data(subreq
, struct tevent_req
);
5530 protocol_magic
= IVAL(inbuf
, 4);
5532 switch (protocol_magic
) {
5534 tevent_req_set_callback(subreq
, smbXcli_negprot_smb1_done
, req
);
5535 conn
->dispatch_incoming
= smb1cli_conn_dispatch_incoming
;
5536 return smb1cli_conn_dispatch_incoming(conn
, tmp_mem
, inbuf
);
5539 if (substate
->smb2
.recv_iov
== NULL
) {
5541 * For the SMB1 negprot we have move it.
5543 substate
->smb2
.recv_iov
= substate
->smb1
.recv_iov
;
5544 substate
->smb1
.recv_iov
= NULL
;
5548 * we got an SMB2 answer, which consumed sequence number 0
5549 * so we need to use 1 as the next one.
5551 * we also need to set the current credits to 0
5552 * as we consumed the initial one. The SMB2 answer
5553 * hopefully grant us a new credit.
5556 conn
->smb2
.cur_credits
= 0;
5557 tevent_req_set_callback(subreq
, smbXcli_negprot_smb2_done
, req
);
5558 conn
->dispatch_incoming
= smb2cli_conn_dispatch_incoming
;
5559 return smb2cli_conn_dispatch_incoming(conn
, tmp_mem
, inbuf
);
5562 DEBUG(10, ("Got non-SMB PDU\n"));
5563 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
5566 NTSTATUS
smbXcli_negprot_recv(
5567 struct tevent_req
*req
,
5568 TALLOC_CTX
*mem_ctx
,
5569 struct smb2_negotiate_contexts
**out_ctx
)
5571 struct smbXcli_negprot_state
*state
= tevent_req_data(
5572 req
, struct smbXcli_negprot_state
);
5575 if (tevent_req_is_nterror(req
, &status
)) {
5576 tevent_req_received(req
);
5580 if (out_ctx
!= NULL
) {
5581 *out_ctx
= talloc_move(mem_ctx
, &state
->out_ctx
);
5584 tevent_req_received(req
);
5585 return NT_STATUS_OK
;
5588 NTSTATUS
smbXcli_negprot(struct smbXcli_conn
*conn
,
5589 uint32_t timeout_msec
,
5590 enum protocol_types min_protocol
,
5591 enum protocol_types max_protocol
,
5592 struct smb2_negotiate_contexts
*in_ctx
,
5593 TALLOC_CTX
*mem_ctx
,
5594 struct smb2_negotiate_contexts
**out_ctx
)
5596 TALLOC_CTX
*frame
= talloc_stackframe();
5597 struct tevent_context
*ev
;
5598 struct tevent_req
*req
;
5599 NTSTATUS status
= NT_STATUS_NO_MEMORY
;
5602 if (smbXcli_conn_has_async_calls(conn
)) {
5604 * Can't use sync call while an async call is in flight
5606 status
= NT_STATUS_INVALID_PARAMETER_MIX
;
5609 ev
= samba_tevent_context_init(frame
);
5613 req
= smbXcli_negprot_send(
5620 WINDOWS_CLIENT_PURE_SMB2_NEGPROT_INITIAL_CREDIT_ASK
,
5625 ok
= tevent_req_poll_ntstatus(req
, ev
, &status
);
5629 status
= smbXcli_negprot_recv(req
, mem_ctx
, out_ctx
);
5635 struct smb2cli_validate_negotiate_info_state
{
5636 struct smbXcli_conn
*conn
;
5637 DATA_BLOB in_input_buffer
;
5638 DATA_BLOB in_output_buffer
;
5639 DATA_BLOB out_input_buffer
;
5640 DATA_BLOB out_output_buffer
;
5644 static void smb2cli_validate_negotiate_info_done(struct tevent_req
*subreq
);
5646 struct tevent_req
*smb2cli_validate_negotiate_info_send(TALLOC_CTX
*mem_ctx
,
5647 struct tevent_context
*ev
,
5648 struct smbXcli_conn
*conn
,
5649 uint32_t timeout_msec
,
5650 struct smbXcli_session
*session
,
5651 struct smbXcli_tcon
*tcon
)
5653 struct tevent_req
*req
;
5654 struct smb2cli_validate_negotiate_info_state
*state
;
5656 uint16_t dialect_count
= 0;
5657 struct tevent_req
*subreq
;
5658 bool _save_should_sign
;
5661 req
= tevent_req_create(mem_ctx
, &state
,
5662 struct smb2cli_validate_negotiate_info_state
);
5668 state
->in_input_buffer
= data_blob_talloc_zero(state
,
5669 4 + 16 + 1 + 1 + 2);
5670 if (tevent_req_nomem(state
->in_input_buffer
.data
, req
)) {
5671 return tevent_req_post(req
, ev
);
5673 buf
= state
->in_input_buffer
.data
;
5675 if (state
->conn
->max_protocol
>= PROTOCOL_SMB3_00
) {
5676 SIVAL(buf
, 0, conn
->smb2
.client
.capabilities
);
5678 SIVAL(buf
, 0, 0); /* Capabilities */
5680 if (state
->conn
->max_protocol
>= PROTOCOL_SMB2_10
) {
5682 struct GUID_ndr_buf guid_buf
= { .buf
= {0}, };
5684 status
= GUID_to_ndr_buf(&conn
->smb2
.client
.guid
,
5686 if (!NT_STATUS_IS_OK(status
)) {
5689 memcpy(buf
+4, guid_buf
.buf
, 16); /* ClientGuid */
5691 memset(buf
+4, 0, 16); /* ClientGuid */
5693 if (state
->conn
->min_protocol
>= PROTOCOL_SMB2_02
) {
5694 SCVAL(buf
, 20, conn
->smb2
.client
.security_mode
);
5698 SCVAL(buf
, 21, 0); /* reserved */
5700 for (i
=0; i
< ARRAY_SIZE(smb2cli_prots
); i
++) {
5704 if (smb2cli_prots
[i
].proto
< state
->conn
->min_protocol
) {
5708 if (smb2cli_prots
[i
].proto
> state
->conn
->max_protocol
) {
5712 if (smb2cli_prots
[i
].proto
== state
->conn
->protocol
) {
5713 state
->dialect
= smb2cli_prots
[i
].smb2_dialect
;
5716 ofs
= state
->in_input_buffer
.length
;
5717 ok
= data_blob_realloc(state
, &state
->in_input_buffer
,
5720 tevent_req_oom(req
);
5721 return tevent_req_post(req
, ev
);
5724 buf
= state
->in_input_buffer
.data
;
5725 SSVAL(buf
, ofs
, smb2cli_prots
[i
].smb2_dialect
);
5729 buf
= state
->in_input_buffer
.data
;
5730 SSVAL(buf
, 22, dialect_count
);
5732 _save_should_sign
= smb2cli_tcon_is_signing_on(tcon
);
5733 smb2cli_tcon_should_sign(tcon
, true);
5734 subreq
= smb2cli_ioctl_send(state
, ev
, conn
,
5735 timeout_msec
, session
, tcon
,
5736 UINT64_MAX
, /* in_fid_persistent */
5737 UINT64_MAX
, /* in_fid_volatile */
5738 FSCTL_VALIDATE_NEGOTIATE_INFO
,
5739 0, /* in_max_input_length */
5740 &state
->in_input_buffer
,
5741 24, /* in_max_output_length */
5742 &state
->in_output_buffer
,
5743 SMB2_IOCTL_FLAG_IS_FSCTL
);
5744 smb2cli_tcon_should_sign(tcon
, _save_should_sign
);
5745 if (tevent_req_nomem(subreq
, req
)) {
5746 return tevent_req_post(req
, ev
);
5748 tevent_req_set_callback(subreq
,
5749 smb2cli_validate_negotiate_info_done
,
5755 static void smb2cli_validate_negotiate_info_done(struct tevent_req
*subreq
)
5757 struct tevent_req
*req
=
5758 tevent_req_callback_data(subreq
,
5760 struct smb2cli_validate_negotiate_info_state
*state
=
5761 tevent_req_data(req
,
5762 struct smb2cli_validate_negotiate_info_state
);
5765 uint32_t capabilities
;
5766 DATA_BLOB guid_blob
;
5767 struct GUID server_guid
;
5768 uint16_t security_mode
;
5771 status
= smb2cli_ioctl_recv(subreq
, state
,
5772 &state
->out_input_buffer
,
5773 &state
->out_output_buffer
);
5774 TALLOC_FREE(subreq
);
5777 * This response must be signed correctly for
5778 * these "normal" error codes to be processed.
5779 * If the packet wasn't signed correctly we will get
5780 * NT_STATUS_ACCESS_DENIED or NT_STATUS_HMAC_NOT_SUPPORTED,
5781 * or NT_STATUS_INVALID_NETWORK_RESPONSE
5782 * from smb2_signing_check_pdu().
5784 * We must never ignore the above errors here.
5787 if (NT_STATUS_EQUAL(status
, NT_STATUS_FILE_CLOSED
)) {
5789 * The response was signed, but not supported
5791 * Older Windows and Samba releases return
5792 * NT_STATUS_FILE_CLOSED.
5794 tevent_req_done(req
);
5797 if (NT_STATUS_EQUAL(status
, NT_STATUS_INVALID_DEVICE_REQUEST
)) {
5799 * The response was signed, but not supported
5801 * This is returned by the NTVFS based Samba 4.x file server
5804 tevent_req_done(req
);
5807 if (NT_STATUS_EQUAL(status
, NT_STATUS_FS_DRIVER_REQUIRED
)) {
5809 * The response was signed, but not supported
5811 * This is returned by the NTVFS based Samba 4.x file server
5814 tevent_req_done(req
);
5817 if (NT_STATUS_EQUAL(status
, NT_STATUS_NOT_SUPPORTED
)) {
5819 * The response was signed, but not supported
5821 * This might be returned by older Windows versions or by
5822 * NetApp SMB server implementations.
5826 * https://blogs.msdn.microsoft.com/openspecification/2012/06/28/smb3-secure-dialect-negotiation/
5829 tevent_req_done(req
);
5832 if (NT_STATUS_EQUAL(status
, NT_STATUS_INVALID_PARAMETER
)) {
5834 * The response was signed, but not supported
5836 * This might be returned by NetApp Ontap 7.3.7 SMB server
5839 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=14607
5842 tevent_req_done(req
);
5845 if (tevent_req_nterror(req
, status
)) {
5849 if (state
->out_output_buffer
.length
!= 24) {
5850 tevent_req_nterror(req
, NT_STATUS_INVALID_NETWORK_RESPONSE
);
5854 buf
= state
->out_output_buffer
.data
;
5856 capabilities
= IVAL(buf
, 0);
5857 guid_blob
= data_blob_const(buf
+ 4, 16);
5858 status
= GUID_from_data_blob(&guid_blob
, &server_guid
);
5859 if (tevent_req_nterror(req
, status
)) {
5862 security_mode
= CVAL(buf
, 20);
5863 dialect
= SVAL(buf
, 22);
5865 if (capabilities
!= state
->conn
->smb2
.server
.capabilities
) {
5866 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
5870 if (!GUID_equal(&server_guid
, &state
->conn
->smb2
.server
.guid
)) {
5871 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
5875 if (security_mode
!= state
->conn
->smb2
.server
.security_mode
) {
5876 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
5880 if (dialect
!= state
->dialect
) {
5881 tevent_req_nterror(req
, NT_STATUS_ACCESS_DENIED
);
5885 tevent_req_done(req
);
5888 NTSTATUS
smb2cli_validate_negotiate_info_recv(struct tevent_req
*req
)
5890 return tevent_req_simple_recv_ntstatus(req
);
5893 static int smbXcli_session_destructor(struct smbXcli_session
*session
)
5895 if (session
->conn
== NULL
) {
5899 DLIST_REMOVE(session
->conn
->sessions
, session
);
5903 struct smbXcli_session
*smbXcli_session_create(TALLOC_CTX
*mem_ctx
,
5904 struct smbXcli_conn
*conn
)
5906 struct smbXcli_session
*session
;
5909 session
= talloc_zero(mem_ctx
, struct smbXcli_session
);
5910 if (session
== NULL
) {
5913 session
->smb2
= talloc_zero(session
, struct smb2cli_session
);
5914 if (session
->smb2
== NULL
) {
5915 talloc_free(session
);
5918 talloc_set_destructor(session
, smbXcli_session_destructor
);
5920 status
= smb2_signing_key_sign_create(session
->smb2
,
5921 conn
->smb2
.server
.sign_algo
,
5922 NULL
, /* no master key */
5923 NULL
, /* derivations */
5924 &session
->smb2
->signing_key
);
5925 if (!NT_STATUS_IS_OK(status
)) {
5926 talloc_free(session
);
5930 DLIST_ADD_END(conn
->sessions
, session
);
5931 session
->conn
= conn
;
5933 status
= smb2_signing_key_sign_create(session
,
5934 conn
->smb2
.server
.sign_algo
,
5935 NULL
, /* no master key */
5936 NULL
, /* derivations */
5937 &session
->smb2_channel
.signing_key
);
5938 if (!NT_STATUS_IS_OK(status
)) {
5939 talloc_free(session
);
5943 memcpy(session
->smb2_channel
.preauth_sha512
,
5944 conn
->smb2
.preauth_sha512
,
5945 sizeof(session
->smb2_channel
.preauth_sha512
));
5950 struct smbXcli_session
*smbXcli_session_shallow_copy(TALLOC_CTX
*mem_ctx
,
5951 struct smbXcli_session
*src
)
5953 struct smbXcli_session
*session
;
5957 session
= talloc_zero(mem_ctx
, struct smbXcli_session
);
5958 if (session
== NULL
) {
5961 session
->smb2
= talloc_zero(session
, struct smb2cli_session
);
5962 if (session
->smb2
== NULL
) {
5963 talloc_free(session
);
5968 * Note we keep a pointer to the session keys of the
5969 * main session and rely on the caller to free the
5970 * shallow copy first!
5972 session
->conn
= src
->conn
;
5973 *session
->smb2
= *src
->smb2
;
5974 session
->smb2_channel
= src
->smb2_channel
;
5975 session
->disconnect_expired
= src
->disconnect_expired
;
5978 * This is only supposed to be called in test code
5979 * but we should not reuse nonces!
5981 * Add the current timestamp as NTTIME to nonce_high
5982 * and set nonce_low to a value we can recognize in captures.
5984 clock_gettime_mono(&ts
);
5985 nt
= unix_timespec_to_nt_time(ts
);
5986 nt
&= session
->smb2
->nonce_high_max
;
5987 if (nt
== session
->smb2
->nonce_high_max
|| nt
< UINT8_MAX
) {
5988 talloc_free(session
);
5991 session
->smb2
->nonce_high
+= nt
;
5992 session
->smb2
->nonce_low
= UINT32_MAX
;
5994 DLIST_ADD_END(src
->conn
->sessions
, session
);
5995 talloc_set_destructor(session
, smbXcli_session_destructor
);
6000 bool smbXcli_session_is_guest(struct smbXcli_session
*session
)
6002 if (session
== NULL
) {
6006 if (session
->conn
== NULL
) {
6010 if (session
->conn
->mandatory_signing
) {
6014 if (session
->conn
->protocol
>= PROTOCOL_SMB2_02
) {
6015 if (session
->smb2
->session_flags
& SMB2_SESSION_FLAG_IS_GUEST
) {
6021 if (session
->smb1
.action
& SMB_SETUP_GUEST
) {
6028 bool smbXcli_session_is_authenticated(struct smbXcli_session
*session
)
6030 const DATA_BLOB
*application_key
;
6032 if (session
== NULL
) {
6036 if (session
->conn
== NULL
) {
6041 * If we have an application key we had a session key negotiated
6044 if (session
->conn
->protocol
>= PROTOCOL_SMB2_02
) {
6045 if (!smb2_signing_key_valid(session
->smb2
->application_key
)) {
6048 application_key
= &session
->smb2
->application_key
->blob
;
6050 application_key
= &session
->smb1
.application_key
;
6053 if (application_key
->length
== 0) {
6060 NTSTATUS
smb2cli_session_signing_key(struct smbXcli_session
*session
,
6061 TALLOC_CTX
*mem_ctx
,
6064 const struct smb2_signing_key
*sig
= NULL
;
6066 if (session
->conn
== NULL
) {
6067 return NT_STATUS_NO_USER_SESSION_KEY
;
6071 * Use channel signing key if there is one, otherwise fallback
6075 if (smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
6076 sig
= session
->smb2_channel
.signing_key
;
6077 } else if (smb2_signing_key_valid(session
->smb2
->signing_key
)) {
6078 sig
= session
->smb2
->signing_key
;
6080 return NT_STATUS_NO_USER_SESSION_KEY
;
6083 *key
= data_blob_dup_talloc(mem_ctx
, sig
->blob
);
6084 if (key
->data
== NULL
) {
6085 return NT_STATUS_NO_MEMORY
;
6088 return NT_STATUS_OK
;
6091 NTSTATUS
smb2cli_session_encryption_key(struct smbXcli_session
*session
,
6092 TALLOC_CTX
*mem_ctx
,
6095 if (session
->conn
== NULL
) {
6096 return NT_STATUS_NO_USER_SESSION_KEY
;
6099 if (session
->conn
->protocol
< PROTOCOL_SMB3_00
) {
6100 return NT_STATUS_NO_USER_SESSION_KEY
;
6103 if (!smb2_signing_key_valid(session
->smb2
->encryption_key
)) {
6104 return NT_STATUS_NO_USER_SESSION_KEY
;
6107 *key
= data_blob_dup_talloc(mem_ctx
, session
->smb2
->encryption_key
->blob
);
6108 if (key
->data
== NULL
) {
6109 return NT_STATUS_NO_MEMORY
;
6112 return NT_STATUS_OK
;
6115 NTSTATUS
smb2cli_session_decryption_key(struct smbXcli_session
*session
,
6116 TALLOC_CTX
*mem_ctx
,
6119 if (session
->conn
== NULL
) {
6120 return NT_STATUS_NO_USER_SESSION_KEY
;
6123 if (session
->conn
->protocol
< PROTOCOL_SMB3_00
) {
6124 return NT_STATUS_NO_USER_SESSION_KEY
;
6127 if (!smb2_signing_key_valid(session
->smb2
->decryption_key
)) {
6128 return NT_STATUS_NO_USER_SESSION_KEY
;
6131 *key
= data_blob_dup_talloc(mem_ctx
, session
->smb2
->decryption_key
->blob
);
6132 if (key
->data
== NULL
) {
6133 return NT_STATUS_NO_MEMORY
;
6136 return NT_STATUS_OK
;
6139 NTSTATUS
smbXcli_session_application_key(struct smbXcli_session
*session
,
6140 TALLOC_CTX
*mem_ctx
,
6143 const DATA_BLOB
*application_key
;
6145 *key
= data_blob_null
;
6147 if (session
->conn
== NULL
) {
6148 return NT_STATUS_NO_USER_SESSION_KEY
;
6151 if (session
->conn
->protocol
>= PROTOCOL_SMB2_02
) {
6152 if (!smb2_signing_key_valid(session
->smb2
->application_key
)) {
6153 return NT_STATUS_NO_USER_SESSION_KEY
;
6155 application_key
= &session
->smb2
->application_key
->blob
;
6157 application_key
= &session
->smb1
.application_key
;
6160 if (application_key
->length
== 0) {
6161 return NT_STATUS_NO_USER_SESSION_KEY
;
6164 *key
= data_blob_dup_talloc(mem_ctx
, *application_key
);
6165 if (key
->data
== NULL
) {
6166 return NT_STATUS_NO_MEMORY
;
6169 return NT_STATUS_OK
;
6172 void smbXcli_session_set_disconnect_expired(struct smbXcli_session
*session
)
6174 session
->disconnect_expired
= true;
6177 uint16_t smb1cli_session_current_id(struct smbXcli_session
*session
)
6179 return session
->smb1
.session_id
;
6182 void smb1cli_session_set_id(struct smbXcli_session
*session
,
6183 uint16_t session_id
)
6185 session
->smb1
.session_id
= session_id
;
6188 void smb1cli_session_set_action(struct smbXcli_session
*session
,
6191 session
->smb1
.action
= action
;
6194 NTSTATUS
smb1cli_session_set_session_key(struct smbXcli_session
*session
,
6195 const DATA_BLOB _session_key
)
6197 struct smbXcli_conn
*conn
= session
->conn
;
6198 uint8_t session_key
[16];
6201 return NT_STATUS_INVALID_PARAMETER_MIX
;
6204 if (session
->smb1
.application_key
.length
!= 0) {
6206 * TODO: do not allow this...
6208 * return NT_STATUS_INVALID_PARAMETER_MIX;
6210 data_blob_clear_free(&session
->smb1
.application_key
);
6211 session
->smb1
.protected_key
= false;
6214 if (_session_key
.length
== 0) {
6215 return NT_STATUS_OK
;
6218 ZERO_STRUCT(session_key
);
6219 memcpy(session_key
, _session_key
.data
,
6220 MIN(_session_key
.length
, sizeof(session_key
)));
6222 session
->smb1
.application_key
= data_blob_talloc(session
,
6224 sizeof(session_key
));
6225 ZERO_STRUCT(session_key
);
6226 if (session
->smb1
.application_key
.data
== NULL
) {
6227 return NT_STATUS_NO_MEMORY
;
6230 session
->smb1
.protected_key
= false;
6232 return NT_STATUS_OK
;
6235 NTSTATUS
smb1cli_session_protect_session_key(struct smbXcli_session
*session
)
6239 if (session
->smb1
.protected_key
) {
6240 /* already protected */
6241 return NT_STATUS_OK
;
6244 if (session
->smb1
.application_key
.length
!= 16) {
6245 return NT_STATUS_INVALID_PARAMETER_MIX
;
6248 status
= smb1_key_derivation(session
->smb1
.application_key
.data
,
6249 session
->smb1
.application_key
.length
,
6250 session
->smb1
.application_key
.data
);
6251 if (!NT_STATUS_IS_OK(status
)) {
6255 session
->smb1
.protected_key
= true;
6257 return NT_STATUS_OK
;
6260 uint8_t smb2cli_session_security_mode(struct smbXcli_session
*session
)
6262 struct smbXcli_conn
*conn
= session
->conn
;
6263 uint8_t security_mode
= 0;
6266 return security_mode
;
6269 security_mode
= SMB2_NEGOTIATE_SIGNING_ENABLED
;
6270 if (conn
->mandatory_signing
) {
6271 security_mode
|= SMB2_NEGOTIATE_SIGNING_REQUIRED
;
6273 if (session
->smb2
->should_sign
) {
6274 security_mode
|= SMB2_NEGOTIATE_SIGNING_REQUIRED
;
6277 return security_mode
;
6280 uint64_t smb2cli_session_current_id(struct smbXcli_session
*session
)
6282 return session
->smb2
->session_id
;
6285 uint16_t smb2cli_session_get_flags(struct smbXcli_session
*session
)
6287 return session
->smb2
->session_flags
;
6290 void smb2cli_session_set_id_and_flags(struct smbXcli_session
*session
,
6291 uint64_t session_id
,
6292 uint16_t session_flags
)
6294 session
->smb2
->session_id
= session_id
;
6295 session
->smb2
->session_flags
= session_flags
;
6298 void smb2cli_session_increment_channel_sequence(struct smbXcli_session
*session
)
6300 session
->smb2
->channel_sequence
+= 1;
6303 uint16_t smb2cli_session_reset_channel_sequence(struct smbXcli_session
*session
,
6304 uint16_t channel_sequence
)
6308 prev_cs
= session
->smb2
->channel_sequence
;
6309 session
->smb2
->channel_sequence
= channel_sequence
;
6314 uint16_t smb2cli_session_current_channel_sequence(struct smbXcli_session
*session
)
6316 return session
->smb2
->channel_sequence
;
6319 void smb2cli_session_start_replay(struct smbXcli_session
*session
)
6321 session
->smb2
->replay_active
= true;
6324 void smb2cli_session_stop_replay(struct smbXcli_session
*session
)
6326 session
->smb2
->replay_active
= false;
6329 void smb2cli_session_require_signed_response(struct smbXcli_session
*session
,
6330 bool require_signed_response
)
6332 session
->smb2
->require_signed_response
= require_signed_response
;
6335 NTSTATUS
smb2cli_session_update_preauth(struct smbXcli_session
*session
,
6336 const struct iovec
*iov
)
6338 gnutls_hash_hd_t hash_hnd
= NULL
;
6342 if (session
->conn
== NULL
) {
6343 return NT_STATUS_INTERNAL_ERROR
;
6346 if (session
->conn
->protocol
< PROTOCOL_SMB3_11
) {
6347 return NT_STATUS_OK
;
6350 if (smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
6351 return NT_STATUS_OK
;
6354 rc
= gnutls_hash_init(&hash_hnd
,
6357 return gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
);
6360 rc
= gnutls_hash(hash_hnd
,
6361 session
->smb2_channel
.preauth_sha512
,
6362 sizeof(session
->smb2_channel
.preauth_sha512
));
6364 gnutls_hash_deinit(hash_hnd
, NULL
);
6365 return gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
);
6367 for (i
= 0; i
< 3; i
++) {
6368 rc
= gnutls_hash(hash_hnd
,
6372 gnutls_hash_deinit(hash_hnd
, NULL
);
6373 return gnutls_error_to_ntstatus(rc
, NT_STATUS_HASH_NOT_SUPPORTED
);
6376 gnutls_hash_deinit(hash_hnd
, session
->smb2_channel
.preauth_sha512
);
6378 return NT_STATUS_OK
;
6381 NTSTATUS
smb2cli_session_set_session_key(struct smbXcli_session
*session
,
6382 const DATA_BLOB _session_key
,
6383 const struct iovec
*recv_iov
)
6385 struct smbXcli_conn
*conn
= session
->conn
;
6386 uint16_t no_sign_flags
= 0;
6387 bool check_signature
= true;
6390 struct smb2_signing_derivations derivations
= {
6393 DATA_BLOB preauth_hash
= data_blob_null
;
6394 size_t nonce_size
= 0;
6397 return NT_STATUS_INVALID_PARAMETER_MIX
;
6400 if (recv_iov
[0].iov_len
!= SMB2_HDR_BODY
) {
6401 return NT_STATUS_INVALID_PARAMETER_MIX
;
6404 if (!conn
->mandatory_signing
) {
6406 * only allow guest sessions without
6407 * mandatory signing.
6409 * If we try an authentication with username != ""
6410 * and the server let us in without verifying the
6411 * password we don't have a negotiated session key
6414 no_sign_flags
= SMB2_SESSION_FLAG_IS_GUEST
;
6417 if (session
->smb2
->session_flags
& no_sign_flags
) {
6418 session
->smb2
->should_sign
= false;
6419 return NT_STATUS_OK
;
6422 if (smb2_signing_key_valid(session
->smb2
->signing_key
)) {
6423 return NT_STATUS_INVALID_PARAMETER_MIX
;
6426 if (conn
->protocol
>= PROTOCOL_SMB3_11
) {
6427 preauth_hash
= data_blob_const(session
->smb2_channel
.preauth_sha512
,
6428 sizeof(session
->smb2_channel
.preauth_sha512
));
6431 smb2_signing_derivations_fill_const_stack(&derivations
,
6435 status
= smb2_signing_key_sign_create(session
->smb2
,
6436 conn
->smb2
.server
.sign_algo
,
6438 derivations
.signing
,
6439 &session
->smb2
->signing_key
);
6440 if (!NT_STATUS_IS_OK(status
)) {
6444 status
= smb2_signing_key_cipher_create(session
->smb2
,
6445 conn
->smb2
.server
.cipher
,
6447 derivations
.cipher_c2s
,
6448 &session
->smb2
->encryption_key
);
6449 if (!NT_STATUS_IS_OK(status
)) {
6453 status
= smb2_signing_key_cipher_create(session
->smb2
,
6454 conn
->smb2
.server
.cipher
,
6456 derivations
.cipher_s2c
,
6457 &session
->smb2
->decryption_key
);
6458 if (!NT_STATUS_IS_OK(status
)) {
6462 status
= smb2_signing_key_sign_create(session
->smb2
,
6463 conn
->smb2
.server
.sign_algo
,
6465 derivations
.application
,
6466 &session
->smb2
->application_key
);
6467 if (!NT_STATUS_IS_OK(status
)) {
6471 status
= smb2_signing_key_copy(session
,
6472 session
->smb2
->signing_key
,
6473 &session
->smb2_channel
.signing_key
);
6474 if (!NT_STATUS_IS_OK(status
)) {
6478 check_signature
= conn
->mandatory_signing
;
6480 hdr_flags
= IVAL(recv_iov
[0].iov_base
, SMB2_HDR_FLAGS
);
6481 if (hdr_flags
& SMB2_HDR_FLAG_SIGNED
) {
6483 * Sadly some vendors don't sign the
6484 * final SMB2 session setup response
6486 * At least Windows and Samba are always doing this
6487 * if there's a session key available.
6489 * We only check the signature if it's mandatory
6490 * or SMB2_HDR_FLAG_SIGNED is provided.
6492 check_signature
= true;
6495 if (conn
->protocol
>= PROTOCOL_SMB3_11
) {
6496 check_signature
= true;
6499 if (check_signature
) {
6500 status
= smb2_signing_check_pdu(session
->smb2_channel
.signing_key
,
6502 if (!NT_STATUS_IS_OK(status
)) {
6507 session
->smb2
->should_sign
= false;
6508 session
->smb2
->should_encrypt
= false;
6510 if (conn
->desire_signing
) {
6511 session
->smb2
->should_sign
= true;
6514 if (conn
->smb2
.server
.security_mode
& SMB2_NEGOTIATE_SIGNING_REQUIRED
) {
6515 session
->smb2
->should_sign
= true;
6518 if (session
->smb2
->session_flags
& SMB2_SESSION_FLAG_ENCRYPT_DATA
) {
6519 session
->smb2
->should_encrypt
= true;
6522 if (conn
->protocol
< PROTOCOL_SMB3_00
) {
6523 session
->smb2
->should_encrypt
= false;
6526 if (conn
->smb2
.server
.cipher
== 0) {
6527 session
->smb2
->should_encrypt
= false;
6531 * CCM and GCM algorithms must never have their
6532 * nonce wrap, or the security of the whole
6533 * communication and the keys is destroyed.
6534 * We must drop the connection once we have
6535 * transferred too much data.
6537 * NOTE: We assume nonces greater than 8 bytes.
6539 generate_nonce_buffer((uint8_t *)&session
->smb2
->nonce_high_random
,
6540 sizeof(session
->smb2
->nonce_high_random
));
6541 switch (conn
->smb2
.server
.cipher
) {
6542 case SMB2_ENCRYPTION_AES128_CCM
:
6543 nonce_size
= SMB2_AES_128_CCM_NONCE_SIZE
;
6545 case SMB2_ENCRYPTION_AES128_GCM
:
6546 nonce_size
= gnutls_cipher_get_iv_size(GNUTLS_CIPHER_AES_128_GCM
);
6548 case SMB2_ENCRYPTION_AES256_CCM
:
6549 nonce_size
= SMB2_AES_128_CCM_NONCE_SIZE
;
6551 case SMB2_ENCRYPTION_AES256_GCM
:
6552 nonce_size
= gnutls_cipher_get_iv_size(GNUTLS_CIPHER_AES_256_GCM
);
6558 session
->smb2
->nonce_high_max
= SMB2_NONCE_HIGH_MAX(nonce_size
);
6559 session
->smb2
->nonce_high
= 0;
6560 session
->smb2
->nonce_low
= 0;
6562 return NT_STATUS_OK
;
6565 NTSTATUS
smb2cli_session_create_channel(TALLOC_CTX
*mem_ctx
,
6566 struct smbXcli_session
*session1
,
6567 struct smbXcli_conn
*conn
,
6568 struct smbXcli_session
**_session2
)
6570 struct smbXcli_session
*session2
;
6573 if (!smb2_signing_key_valid(session1
->smb2
->signing_key
)) {
6574 return NT_STATUS_INVALID_PARAMETER_MIX
;
6578 return NT_STATUS_INVALID_PARAMETER_MIX
;
6581 session2
= talloc_zero(mem_ctx
, struct smbXcli_session
);
6582 if (session2
== NULL
) {
6583 return NT_STATUS_NO_MEMORY
;
6585 session2
->smb2
= talloc_reference(session2
, session1
->smb2
);
6586 if (session2
->smb2
== NULL
) {
6587 talloc_free(session2
);
6588 return NT_STATUS_NO_MEMORY
;
6591 talloc_set_destructor(session2
, smbXcli_session_destructor
);
6592 DLIST_ADD_END(conn
->sessions
, session2
);
6593 session2
->conn
= conn
;
6595 status
= smb2_signing_key_sign_create(session2
,
6596 conn
->smb2
.server
.sign_algo
,
6597 NULL
, /* no master key */
6598 NULL
, /* derivations */
6599 &session2
->smb2_channel
.signing_key
);
6600 if (!NT_STATUS_IS_OK(status
)) {
6601 talloc_free(session2
);
6602 return NT_STATUS_NO_MEMORY
;
6605 memcpy(session2
->smb2_channel
.preauth_sha512
,
6606 conn
->smb2
.preauth_sha512
,
6607 sizeof(session2
->smb2_channel
.preauth_sha512
));
6609 *_session2
= session2
;
6610 return NT_STATUS_OK
;
6613 NTSTATUS
smb2cli_session_set_channel_key(struct smbXcli_session
*session
,
6614 const DATA_BLOB _channel_key
,
6615 const struct iovec
*recv_iov
)
6617 struct smbXcli_conn
*conn
= session
->conn
;
6618 uint8_t channel_key
[16];
6620 struct _derivation
{
6625 struct _derivation signing
;
6627 .signing
.label
.length
= 0,
6631 return NT_STATUS_INVALID_PARAMETER_MIX
;
6634 if (smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
6635 return NT_STATUS_INVALID_PARAMETER_MIX
;
6638 if (conn
->protocol
>= PROTOCOL_SMB3_11
) {
6639 struct _derivation
*d
;
6642 p
= data_blob_const(session
->smb2_channel
.preauth_sha512
,
6643 sizeof(session
->smb2_channel
.preauth_sha512
));
6645 d
= &derivation
.signing
;
6646 d
->label
= data_blob_string_const_null("SMBSigningKey");
6648 } else if (conn
->protocol
>= PROTOCOL_SMB3_00
) {
6649 struct _derivation
*d
;
6651 d
= &derivation
.signing
;
6652 d
->label
= data_blob_string_const_null("SMB2AESCMAC");
6653 d
->context
= data_blob_string_const_null("SmbSign");
6656 ZERO_STRUCT(channel_key
);
6657 memcpy(channel_key
, _channel_key
.data
,
6658 MIN(_channel_key
.length
, sizeof(channel_key
)));
6660 session
->smb2_channel
.signing_key
->blob
=
6661 data_blob_talloc(session
->smb2_channel
.signing_key
,
6663 sizeof(channel_key
));
6664 if (!smb2_signing_key_valid(session
->smb2_channel
.signing_key
)) {
6665 ZERO_STRUCT(channel_key
);
6666 return NT_STATUS_NO_MEMORY
;
6669 if (conn
->protocol
>= PROTOCOL_SMB3_00
) {
6670 struct _derivation
*d
= &derivation
.signing
;
6672 status
= smb2_key_derivation(channel_key
, sizeof(channel_key
),
6673 d
->label
.data
, d
->label
.length
,
6674 d
->context
.data
, d
->context
.length
,
6675 session
->smb2_channel
.signing_key
->blob
.data
,
6676 session
->smb2_channel
.signing_key
->blob
.length
);
6677 if (!NT_STATUS_IS_OK(status
)) {
6681 ZERO_STRUCT(channel_key
);
6683 status
= smb2_signing_check_pdu(session
->smb2_channel
.signing_key
,
6685 if (!NT_STATUS_IS_OK(status
)) {
6689 return NT_STATUS_OK
;
6692 NTSTATUS
smb2cli_session_encryption_on(struct smbXcli_session
*session
)
6694 if (!session
->smb2
->should_sign
) {
6696 * We need required signing on the session
6697 * in order to prevent man in the middle attacks.
6699 return NT_STATUS_INVALID_PARAMETER_MIX
;
6702 if (session
->smb2
->should_encrypt
) {
6703 return NT_STATUS_OK
;
6706 if (session
->conn
->protocol
< PROTOCOL_SMB3_00
) {
6707 return NT_STATUS_NOT_SUPPORTED
;
6710 if (session
->conn
->smb2
.server
.cipher
== 0) {
6711 return NT_STATUS_NOT_SUPPORTED
;
6714 if (!smb2_signing_key_valid(session
->smb2
->signing_key
)) {
6715 return NT_STATUS_NOT_SUPPORTED
;
6717 session
->smb2
->should_encrypt
= true;
6718 return NT_STATUS_OK
;
6721 uint16_t smb2cli_session_get_encryption_cipher(struct smbXcli_session
*session
)
6723 if (session
->conn
->protocol
< PROTOCOL_SMB3_00
) {
6727 if (!session
->smb2
->should_encrypt
) {
6731 return session
->conn
->smb2
.server
.cipher
;
6734 struct smbXcli_tcon
*smbXcli_tcon_create(TALLOC_CTX
*mem_ctx
)
6736 struct smbXcli_tcon
*tcon
;
6738 tcon
= talloc_zero(mem_ctx
, struct smbXcli_tcon
);
6747 * Return a deep structure copy of a struct smbXcli_tcon *
6750 struct smbXcli_tcon
*smbXcli_tcon_copy(TALLOC_CTX
*mem_ctx
,
6751 const struct smbXcli_tcon
*tcon_in
)
6753 struct smbXcli_tcon
*tcon
;
6755 tcon
= talloc_memdup(mem_ctx
, tcon_in
, sizeof(struct smbXcli_tcon
));
6760 /* Deal with the SMB1 strings. */
6761 if (tcon_in
->smb1
.service
!= NULL
) {
6762 tcon
->smb1
.service
= talloc_strdup(tcon
, tcon_in
->smb1
.service
);
6763 if (tcon
->smb1
.service
== NULL
) {
6768 if (tcon
->smb1
.fs_type
!= NULL
) {
6769 tcon
->smb1
.fs_type
= talloc_strdup(tcon
, tcon_in
->smb1
.fs_type
);
6770 if (tcon
->smb1
.fs_type
== NULL
) {
6778 void smbXcli_tcon_set_fs_attributes(struct smbXcli_tcon
*tcon
,
6779 uint32_t fs_attributes
)
6781 tcon
->fs_attributes
= fs_attributes
;
6784 uint32_t smbXcli_tcon_get_fs_attributes(struct smbXcli_tcon
*tcon
)
6786 return tcon
->fs_attributes
;
6789 bool smbXcli_tcon_is_dfs_share(struct smbXcli_tcon
*tcon
)
6795 if (tcon
->is_smb1
) {
6796 if (tcon
->smb1
.optional_support
& SMB_SHARE_IN_DFS
) {
6803 if (tcon
->smb2
.capabilities
& SMB2_SHARE_CAP_DFS
) {
6810 uint16_t smb1cli_tcon_current_id(struct smbXcli_tcon
*tcon
)
6812 return tcon
->smb1
.tcon_id
;
6815 void smb1cli_tcon_set_id(struct smbXcli_tcon
*tcon
, uint16_t tcon_id
)
6817 tcon
->is_smb1
= true;
6818 tcon
->smb1
.tcon_id
= tcon_id
;
6821 bool smb1cli_tcon_set_values(struct smbXcli_tcon
*tcon
,
6823 uint16_t optional_support
,
6824 uint32_t maximal_access
,
6825 uint32_t guest_maximal_access
,
6826 const char *service
,
6827 const char *fs_type
)
6829 tcon
->is_smb1
= true;
6830 tcon
->fs_attributes
= 0;
6831 tcon
->smb1
.tcon_id
= tcon_id
;
6832 tcon
->smb1
.optional_support
= optional_support
;
6833 tcon
->smb1
.maximal_access
= maximal_access
;
6834 tcon
->smb1
.guest_maximal_access
= guest_maximal_access
;
6836 TALLOC_FREE(tcon
->smb1
.service
);
6837 tcon
->smb1
.service
= talloc_strdup(tcon
, service
);
6838 if (service
!= NULL
&& tcon
->smb1
.service
== NULL
) {
6842 TALLOC_FREE(tcon
->smb1
.fs_type
);
6843 tcon
->smb1
.fs_type
= talloc_strdup(tcon
, fs_type
);
6844 if (fs_type
!= NULL
&& tcon
->smb1
.fs_type
== NULL
) {
6851 uint32_t smb2cli_tcon_current_id(struct smbXcli_tcon
*tcon
)
6853 return tcon
->smb2
.tcon_id
;
6856 void smb2cli_tcon_set_id(struct smbXcli_tcon
*tcon
, uint32_t tcon_id
)
6858 tcon
->smb2
.tcon_id
= tcon_id
;
6861 uint32_t smb2cli_tcon_capabilities(struct smbXcli_tcon
*tcon
)
6863 return tcon
->smb2
.capabilities
;
6866 uint32_t smb2cli_tcon_flags(struct smbXcli_tcon
*tcon
)
6868 return tcon
->smb2
.flags
;
6871 void smb2cli_tcon_set_values(struct smbXcli_tcon
*tcon
,
6872 struct smbXcli_session
*session
,
6876 uint32_t capabilities
,
6877 uint32_t maximal_access
)
6879 tcon
->is_smb1
= false;
6880 tcon
->fs_attributes
= 0;
6881 tcon
->smb2
.tcon_id
= tcon_id
;
6882 tcon
->smb2
.type
= type
;
6883 tcon
->smb2
.flags
= flags
;
6884 tcon
->smb2
.capabilities
= capabilities
;
6885 tcon
->smb2
.maximal_access
= maximal_access
;
6887 tcon
->smb2
.should_sign
= false;
6888 tcon
->smb2
.should_encrypt
= false;
6890 if (session
== NULL
) {
6894 tcon
->smb2
.should_sign
= session
->smb2
->should_sign
;
6895 tcon
->smb2
.should_encrypt
= session
->smb2
->should_encrypt
;
6897 if (flags
& SMB2_SHAREFLAG_ENCRYPT_DATA
) {
6898 tcon
->smb2
.should_encrypt
= true;
6902 void smb2cli_tcon_should_sign(struct smbXcli_tcon
*tcon
,
6905 tcon
->smb2
.should_sign
= should_sign
;
6908 bool smb2cli_tcon_is_signing_on(struct smbXcli_tcon
*tcon
)
6910 if (tcon
->smb2
.should_encrypt
) {
6914 return tcon
->smb2
.should_sign
;
6917 void smb2cli_tcon_should_encrypt(struct smbXcli_tcon
*tcon
,
6918 bool should_encrypt
)
6920 tcon
->smb2
.should_encrypt
= should_encrypt
;
6923 bool smb2cli_tcon_is_encryption_on(struct smbXcli_tcon
*tcon
)
6925 return tcon
->smb2
.should_encrypt
;
6928 void smb2cli_conn_set_mid(struct smbXcli_conn
*conn
, uint64_t mid
)
6930 conn
->smb2
.mid
= mid
;
6933 uint64_t smb2cli_conn_get_mid(struct smbXcli_conn
*conn
)
6935 return conn
->smb2
.mid
;
6938 NTSTATUS
smb2cli_parse_dyn_buffer(uint32_t dyn_offset
,
6939 const DATA_BLOB dyn_buffer
,
6940 uint32_t min_offset
,
6941 uint32_t buffer_offset
,
6942 uint32_t buffer_length
,
6943 uint32_t max_length
,
6944 uint32_t *next_offset
,
6950 *buffer
= data_blob_null
;
6951 *next_offset
= dyn_offset
;
6953 if (buffer_offset
== 0) {
6955 * If the offset is 0, we better ignore
6956 * the buffer_length field.
6958 return NT_STATUS_OK
;
6961 if (buffer_length
== 0) {
6963 * If the length is 0, we better ignore
6964 * the buffer_offset field.
6966 return NT_STATUS_OK
;
6969 if ((buffer_offset
% 8) != 0) {
6971 * The offset needs to be 8 byte aligned.
6973 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
6977 * We used to enforce buffer_offset to be
6978 * an exact match of the expected minimum,
6979 * but the NetApp Ontap 7.3.7 SMB server
6980 * gets the padding wrong and aligns the
6981 * input_buffer_offset by a value of 8.
6983 * So we just enforce that the offset is
6984 * not lower than the expected value.
6986 SMB_ASSERT(min_offset
>= dyn_offset
);
6987 if (buffer_offset
< min_offset
) {
6988 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
6992 * Make [input|output]_buffer_offset relative to "dyn_buffer"
6994 offset
= buffer_offset
- dyn_offset
;
6995 oob
= smb_buffer_oob(dyn_buffer
.length
, offset
, buffer_length
);
6997 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
7001 * Give the caller a hint what we consumed,
7002 * the caller may need to add possible padding.
7004 *next_offset
= buffer_offset
+ buffer_length
;
7006 if (max_length
== 0) {
7008 * If max_input_length is 0 we ignore the
7009 * input_buffer_length, because Windows 2008 echos the
7010 * DCERPC request from the requested input_buffer to
7011 * the response input_buffer.
7013 * We just use the same logic also for max_output_length...
7018 if (buffer_length
> max_length
) {
7019 return NT_STATUS_INVALID_NETWORK_RESPONSE
;
7022 *buffer
= (DATA_BLOB
) {
7023 .data
= dyn_buffer
.data
+ offset
,
7024 .length
= buffer_length
,
7026 return NT_STATUS_OK
;