libcli/smb: make sure the writev_send of smbXcli_conn_samba_suicide() is removed...
[samba.git] / libcli / smb / smbXcli_base.c
1 /*
2    Unix SMB/CIFS implementation.
3    Infrastructure for async SMB client requests
4    Copyright (C) Volker Lendecke 2008
5    Copyright (C) Stefan Metzmacher 2011
6
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.
11
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.
16
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/>.
19 */
20
21 #include "includes.h"
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 "lib/crypto/sha512.h"
37 #include "lib/crypto/aes.h"
38 #include "lib/crypto/aes_ccm_128.h"
39 #include "lib/crypto/aes_gcm_128.h"
40
41 struct smbXcli_conn;
42 struct smbXcli_req;
43 struct smbXcli_session;
44 struct smbXcli_tcon;
45
46 struct smbXcli_conn {
47         int sock_fd;
48         struct sockaddr_storage local_ss;
49         struct sockaddr_storage remote_ss;
50         const char *remote_name;
51
52         struct tevent_queue *outgoing;
53         struct tevent_req **pending;
54         struct tevent_req *read_smb_req;
55         struct tevent_req *suicide_req;
56
57         enum protocol_types min_protocol;
58         enum protocol_types max_protocol;
59         enum protocol_types protocol;
60         bool allow_signing;
61         bool desire_signing;
62         bool mandatory_signing;
63
64         /*
65          * The incoming dispatch function should return:
66          * - NT_STATUS_RETRY, if more incoming PDUs are expected.
67          * - NT_STATUS_OK, if no more processing is desired, e.g.
68          *                 the dispatch function called
69          *                 tevent_req_done().
70          * - All other return values disconnect the connection.
71          */
72         NTSTATUS (*dispatch_incoming)(struct smbXcli_conn *conn,
73                                       TALLOC_CTX *tmp_mem,
74                                       uint8_t *inbuf);
75
76         struct {
77                 struct {
78                         uint32_t capabilities;
79                         uint32_t max_xmit;
80                 } client;
81
82                 struct {
83                         uint32_t capabilities;
84                         uint32_t max_xmit;
85                         uint16_t max_mux;
86                         uint16_t security_mode;
87                         bool readbraw;
88                         bool writebraw;
89                         bool lockread;
90                         bool writeunlock;
91                         uint32_t session_key;
92                         struct GUID guid;
93                         DATA_BLOB gss_blob;
94                         uint8_t challenge[8];
95                         const char *workgroup;
96                         const char *name;
97                         int time_zone;
98                         NTTIME system_time;
99                 } server;
100
101                 uint32_t capabilities;
102                 uint32_t max_xmit;
103
104                 uint16_t mid;
105
106                 struct smb_signing_state *signing;
107                 struct smb_trans_enc_state *trans_enc;
108
109                 struct tevent_req *read_braw_req;
110         } smb1;
111
112         struct {
113                 struct {
114                         uint32_t capabilities;
115                         uint16_t security_mode;
116                         struct GUID guid;
117                 } client;
118
119                 struct {
120                         uint32_t capabilities;
121                         uint16_t security_mode;
122                         struct GUID guid;
123                         uint32_t max_trans_size;
124                         uint32_t max_read_size;
125                         uint32_t max_write_size;
126                         NTTIME system_time;
127                         NTTIME start_time;
128                         DATA_BLOB gss_blob;
129                         uint16_t cipher;
130                 } server;
131
132                 uint64_t mid;
133                 uint16_t cur_credits;
134                 uint16_t max_credits;
135
136                 uint32_t cc_chunk_len;
137                 uint32_t cc_max_chunks;
138
139                 uint8_t io_priority;
140
141                 uint8_t preauth_sha512[64];
142         } smb2;
143
144         struct smbXcli_session *sessions;
145 };
146
147 struct smb2cli_session {
148         uint64_t session_id;
149         uint16_t session_flags;
150         DATA_BLOB application_key;
151         DATA_BLOB signing_key;
152         bool should_sign;
153         bool should_encrypt;
154         DATA_BLOB encryption_key;
155         DATA_BLOB decryption_key;
156         uint64_t nonce_high_random;
157         uint64_t nonce_high_max;
158         uint64_t nonce_high;
159         uint64_t nonce_low;
160         uint16_t channel_sequence;
161         bool replay_active;
162 };
163
164 struct smbXcli_session {
165         struct smbXcli_session *prev, *next;
166         struct smbXcli_conn *conn;
167
168         struct {
169                 uint16_t session_id;
170                 DATA_BLOB application_key;
171                 bool protected_key;
172         } smb1;
173
174         struct smb2cli_session *smb2;
175
176         struct {
177                 DATA_BLOB signing_key;
178                 uint8_t preauth_sha512[64];
179         } smb2_channel;
180
181         /*
182          * this should be a short term hack
183          * until the upper layers have implemented
184          * re-authentication.
185          */
186         bool disconnect_expired;
187 };
188
189 struct smbXcli_tcon {
190         bool is_smb1;
191         uint32_t fs_attributes;
192
193         struct {
194                 uint16_t tcon_id;
195                 uint16_t optional_support;
196                 uint32_t maximal_access;
197                 uint32_t guest_maximal_access;
198                 char *service;
199                 char *fs_type;
200         } smb1;
201
202         struct {
203                 uint32_t tcon_id;
204                 uint8_t type;
205                 uint32_t flags;
206                 uint32_t capabilities;
207                 uint32_t maximal_access;
208                 bool should_sign;
209                 bool should_encrypt;
210         } smb2;
211 };
212
213 struct smbXcli_req_state {
214         struct tevent_context *ev;
215         struct smbXcli_conn *conn;
216         struct smbXcli_session *session; /* maybe NULL */
217         struct smbXcli_tcon *tcon; /* maybe NULL */
218
219         uint8_t length_hdr[4];
220
221         bool one_way;
222
223         uint8_t *inbuf;
224
225         struct {
226                 /* Space for the header including the wct */
227                 uint8_t hdr[HDR_VWV];
228
229                 /*
230                  * For normal requests, smb1cli_req_send chooses a mid.
231                  * SecondaryV trans requests need to use the mid of the primary
232                  * request, so we need a place to store it.
233                  * Assume it is set if != 0.
234                  */
235                 uint16_t mid;
236
237                 uint16_t *vwv;
238                 uint8_t bytecount_buf[2];
239
240 #define MAX_SMB_IOV 10
241                 /* length_hdr, hdr, words, byte_count, buffers */
242                 struct iovec iov[1 + 3 + MAX_SMB_IOV];
243                 int iov_count;
244
245                 bool one_way_seqnum;
246                 uint32_t seqnum;
247                 struct tevent_req **chained_requests;
248
249                 uint8_t recv_cmd;
250                 NTSTATUS recv_status;
251                 /* always an array of 3 talloc elements */
252                 struct iovec *recv_iov;
253         } smb1;
254
255         struct {
256                 const uint8_t *fixed;
257                 uint16_t fixed_len;
258                 const uint8_t *dyn;
259                 uint32_t dyn_len;
260
261                 uint8_t transform[SMB2_TF_HDR_SIZE];
262                 uint8_t hdr[SMB2_HDR_BODY];
263                 uint8_t pad[7]; /* padding space for compounding */
264
265                 /*
266                  * always an array of 3 talloc elements
267                  * (without a SMB2_TRANSFORM header!)
268                  *
269                  * HDR, BODY, DYN
270                  */
271                 struct iovec *recv_iov;
272
273                 /*
274                  * the expected max for the response dyn_len
275                  */
276                 uint32_t max_dyn_len;
277
278                 uint16_t credit_charge;
279
280                 bool should_sign;
281                 bool should_encrypt;
282                 uint64_t encryption_session_id;
283
284                 bool signing_skipped;
285                 bool notify_async;
286                 bool got_async;
287                 uint16_t cancel_flags;
288                 uint64_t cancel_mid;
289                 uint64_t cancel_aid;
290         } smb2;
291 };
292
293 static int smbXcli_conn_destructor(struct smbXcli_conn *conn)
294 {
295         /*
296          * NT_STATUS_OK, means we do not notify the callers
297          */
298         smbXcli_conn_disconnect(conn, NT_STATUS_OK);
299
300         while (conn->sessions) {
301                 conn->sessions->conn = NULL;
302                 DLIST_REMOVE(conn->sessions, conn->sessions);
303         }
304
305         if (conn->smb1.trans_enc) {
306                 TALLOC_FREE(conn->smb1.trans_enc);
307         }
308
309         return 0;
310 }
311
312 struct smbXcli_conn *smbXcli_conn_create(TALLOC_CTX *mem_ctx,
313                                          int fd,
314                                          const char *remote_name,
315                                          enum smb_signing_setting signing_state,
316                                          uint32_t smb1_capabilities,
317                                          struct GUID *client_guid,
318                                          uint32_t smb2_capabilities)
319 {
320         struct smbXcli_conn *conn = NULL;
321         void *ss = NULL;
322         struct sockaddr *sa = NULL;
323         socklen_t sa_length;
324         int ret;
325
326         conn = talloc_zero(mem_ctx, struct smbXcli_conn);
327         if (!conn) {
328                 return NULL;
329         }
330
331         conn->sock_fd = fd;
332
333         conn->remote_name = talloc_strdup(conn, remote_name);
334         if (conn->remote_name == NULL) {
335                 goto error;
336         }
337
338         ss = (void *)&conn->local_ss;
339         sa = (struct sockaddr *)ss;
340         sa_length = sizeof(conn->local_ss);
341         ret = getsockname(fd, sa, &sa_length);
342         if (ret == -1) {
343                 goto error;
344         }
345         ss = (void *)&conn->remote_ss;
346         sa = (struct sockaddr *)ss;
347         sa_length = sizeof(conn->remote_ss);
348         ret = getpeername(fd, sa, &sa_length);
349         if (ret == -1) {
350                 goto error;
351         }
352
353         conn->outgoing = tevent_queue_create(conn, "smbXcli_outgoing");
354         if (conn->outgoing == NULL) {
355                 goto error;
356         }
357         conn->pending = NULL;
358
359         conn->min_protocol = PROTOCOL_NONE;
360         conn->max_protocol = PROTOCOL_NONE;
361         conn->protocol = PROTOCOL_NONE;
362
363         switch (signing_state) {
364         case SMB_SIGNING_OFF:
365                 /* never */
366                 conn->allow_signing = false;
367                 conn->desire_signing = false;
368                 conn->mandatory_signing = false;
369                 break;
370         case SMB_SIGNING_DEFAULT:
371         case SMB_SIGNING_IF_REQUIRED:
372                 /* if the server requires it */
373                 conn->allow_signing = true;
374                 conn->desire_signing = false;
375                 conn->mandatory_signing = false;
376                 break;
377         case SMB_SIGNING_REQUIRED:
378                 /* always */
379                 conn->allow_signing = true;
380                 conn->desire_signing = true;
381                 conn->mandatory_signing = true;
382                 break;
383         }
384
385         conn->smb1.client.capabilities = smb1_capabilities;
386         conn->smb1.client.max_xmit = UINT16_MAX;
387
388         conn->smb1.capabilities = conn->smb1.client.capabilities;
389         conn->smb1.max_xmit = 1024;
390
391         conn->smb1.mid = 1;
392
393         /* initialise signing */
394         conn->smb1.signing = smb_signing_init(conn,
395                                               conn->allow_signing,
396                                               conn->desire_signing,
397                                               conn->mandatory_signing);
398         if (!conn->smb1.signing) {
399                 goto error;
400         }
401
402         conn->smb2.client.security_mode = SMB2_NEGOTIATE_SIGNING_ENABLED;
403         if (conn->mandatory_signing) {
404                 conn->smb2.client.security_mode |= SMB2_NEGOTIATE_SIGNING_REQUIRED;
405         }
406         if (client_guid) {
407                 conn->smb2.client.guid = *client_guid;
408         }
409         conn->smb2.client.capabilities = smb2_capabilities;
410
411         conn->smb2.cur_credits = 1;
412         conn->smb2.max_credits = 0;
413         conn->smb2.io_priority = 1;
414
415         /*
416          * Samba and Windows servers accept a maximum of 16 MiB with a maximum
417          * chunk length of 1 MiB.
418          */
419         conn->smb2.cc_chunk_len = 1024 * 1024;
420         conn->smb2.cc_max_chunks = 16;
421
422         talloc_set_destructor(conn, smbXcli_conn_destructor);
423         return conn;
424
425  error:
426         TALLOC_FREE(conn);
427         return NULL;
428 }
429
430 bool smbXcli_conn_is_connected(struct smbXcli_conn *conn)
431 {
432         if (conn == NULL) {
433                 return false;
434         }
435
436         if (conn->sock_fd == -1) {
437                 return false;
438         }
439
440         return true;
441 }
442
443 enum protocol_types smbXcli_conn_protocol(struct smbXcli_conn *conn)
444 {
445         return conn->protocol;
446 }
447
448 bool smbXcli_conn_use_unicode(struct smbXcli_conn *conn)
449 {
450         if (conn->protocol >= PROTOCOL_SMB2_02) {
451                 return true;
452         }
453
454         if (conn->smb1.capabilities & CAP_UNICODE) {
455                 return true;
456         }
457
458         return false;
459 }
460
461 void smbXcli_conn_set_sockopt(struct smbXcli_conn *conn, const char *options)
462 {
463         set_socket_options(conn->sock_fd, options);
464 }
465
466 const struct sockaddr_storage *smbXcli_conn_local_sockaddr(struct smbXcli_conn *conn)
467 {
468         return &conn->local_ss;
469 }
470
471 const struct sockaddr_storage *smbXcli_conn_remote_sockaddr(struct smbXcli_conn *conn)
472 {
473         return &conn->remote_ss;
474 }
475
476 const char *smbXcli_conn_remote_name(struct smbXcli_conn *conn)
477 {
478         return conn->remote_name;
479 }
480
481 uint16_t smbXcli_conn_max_requests(struct smbXcli_conn *conn)
482 {
483         if (conn->protocol >= PROTOCOL_SMB2_02) {
484                 /*
485                  * TODO...
486                  */
487                 return 1;
488         }
489
490         return conn->smb1.server.max_mux;
491 }
492
493 NTTIME smbXcli_conn_server_system_time(struct smbXcli_conn *conn)
494 {
495         if (conn->protocol >= PROTOCOL_SMB2_02) {
496                 return conn->smb2.server.system_time;
497         }
498
499         return conn->smb1.server.system_time;
500 }
501
502 const DATA_BLOB *smbXcli_conn_server_gss_blob(struct smbXcli_conn *conn)
503 {
504         if (conn->protocol >= PROTOCOL_SMB2_02) {
505                 return &conn->smb2.server.gss_blob;
506         }
507
508         return &conn->smb1.server.gss_blob;
509 }
510
511 const struct GUID *smbXcli_conn_server_guid(struct smbXcli_conn *conn)
512 {
513         if (conn->protocol >= PROTOCOL_SMB2_02) {
514                 return &conn->smb2.server.guid;
515         }
516
517         return &conn->smb1.server.guid;
518 }
519
520 struct smbXcli_conn_samba_suicide_state {
521         struct smbXcli_conn *conn;
522         struct iovec iov;
523         uint8_t buf[9];
524         struct tevent_req *write_req;
525 };
526
527 static void smbXcli_conn_samba_suicide_cleanup(struct tevent_req *req,
528                                                enum tevent_req_state req_state);
529 static void smbXcli_conn_samba_suicide_done(struct tevent_req *subreq);
530
531 struct tevent_req *smbXcli_conn_samba_suicide_send(TALLOC_CTX *mem_ctx,
532                                                    struct tevent_context *ev,
533                                                    struct smbXcli_conn *conn,
534                                                    uint8_t exitcode)
535 {
536         struct tevent_req *req, *subreq;
537         struct smbXcli_conn_samba_suicide_state *state;
538
539         req = tevent_req_create(mem_ctx, &state,
540                                 struct smbXcli_conn_samba_suicide_state);
541         if (req == NULL) {
542                 return NULL;
543         }
544         state->conn = conn;
545         SIVAL(state->buf, 4, 0x74697865);
546         SCVAL(state->buf, 8, exitcode);
547         _smb_setlen_nbt(state->buf, sizeof(state->buf)-4);
548
549         if (conn->suicide_req != NULL) {
550                 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER);
551                 return tevent_req_post(req, ev);
552         }
553
554         state->iov.iov_base = state->buf;
555         state->iov.iov_len = sizeof(state->buf);
556
557         subreq = writev_send(state, ev, conn->outgoing, conn->sock_fd,
558                              false, &state->iov, 1);
559         if (tevent_req_nomem(subreq, req)) {
560                 return tevent_req_post(req, ev);
561         }
562         tevent_req_set_callback(subreq, smbXcli_conn_samba_suicide_done, req);
563         state->write_req = subreq;
564
565         tevent_req_set_cleanup_fn(req, smbXcli_conn_samba_suicide_cleanup);
566
567         /*
568          * We need to use tevent_req_defer_callback()
569          * in order to allow smbXcli_conn_disconnect()
570          * to do a safe cleanup.
571          */
572         tevent_req_defer_callback(req, ev);
573         conn->suicide_req = req;
574
575         return req;
576 }
577
578 static void smbXcli_conn_samba_suicide_cleanup(struct tevent_req *req,
579                                                enum tevent_req_state req_state)
580 {
581         struct smbXcli_conn_samba_suicide_state *state = tevent_req_data(
582                 req, struct smbXcli_conn_samba_suicide_state);
583
584         TALLOC_FREE(state->write_req);
585
586         if (state->conn == NULL) {
587                 return;
588         }
589
590         if (state->conn->suicide_req == req) {
591                 state->conn->suicide_req = NULL;
592         }
593         state->conn = NULL;
594 }
595
596 static void smbXcli_conn_samba_suicide_done(struct tevent_req *subreq)
597 {
598         struct tevent_req *req = tevent_req_callback_data(
599                 subreq, struct tevent_req);
600         struct smbXcli_conn_samba_suicide_state *state = tevent_req_data(
601                 req, struct smbXcli_conn_samba_suicide_state);
602         ssize_t nwritten;
603         int err;
604
605         state->write_req = NULL;
606
607         nwritten = writev_recv(subreq, &err);
608         TALLOC_FREE(subreq);
609         if (nwritten == -1) {
610                 /* here, we need to notify all pending requests */
611                 NTSTATUS status = map_nt_error_from_unix_common(err);
612                 smbXcli_conn_disconnect(state->conn, status);
613                 return;
614         }
615         tevent_req_done(req);
616 }
617
618 NTSTATUS smbXcli_conn_samba_suicide_recv(struct tevent_req *req)
619 {
620         return tevent_req_simple_recv_ntstatus(req);
621 }
622
623 NTSTATUS smbXcli_conn_samba_suicide(struct smbXcli_conn *conn,
624                                     uint8_t exitcode)
625 {
626         TALLOC_CTX *frame = talloc_stackframe();
627         struct tevent_context *ev;
628         struct tevent_req *req;
629         NTSTATUS status = NT_STATUS_NO_MEMORY;
630         bool ok;
631
632         if (smbXcli_conn_has_async_calls(conn)) {
633                 /*
634                  * Can't use sync call while an async call is in flight
635                  */
636                 status = NT_STATUS_INVALID_PARAMETER_MIX;
637                 goto fail;
638         }
639         ev = samba_tevent_context_init(frame);
640         if (ev == NULL) {
641                 goto fail;
642         }
643         req = smbXcli_conn_samba_suicide_send(frame, ev, conn, exitcode);
644         if (req == NULL) {
645                 goto fail;
646         }
647         ok = tevent_req_poll_ntstatus(req, ev, &status);
648         if (!ok) {
649                 goto fail;
650         }
651         status = smbXcli_conn_samba_suicide_recv(req);
652  fail:
653         TALLOC_FREE(frame);
654         return status;
655 }
656
657 uint32_t smb1cli_conn_capabilities(struct smbXcli_conn *conn)
658 {
659         return conn->smb1.capabilities;
660 }
661
662 uint32_t smb1cli_conn_max_xmit(struct smbXcli_conn *conn)
663 {
664         return conn->smb1.max_xmit;
665 }
666
667 bool smb1cli_conn_req_possible(struct smbXcli_conn *conn)
668 {
669         size_t pending;
670         uint16_t possible = conn->smb1.server.max_mux;
671
672         pending = tevent_queue_length(conn->outgoing);
673         if (pending >= possible) {
674                 return false;
675         }
676         pending += talloc_array_length(conn->pending);
677         if (pending >= possible) {
678                 return false;
679         }
680
681         return true;
682 }
683
684 uint32_t smb1cli_conn_server_session_key(struct smbXcli_conn *conn)
685 {
686         return conn->smb1.server.session_key;
687 }
688
689 const uint8_t *smb1cli_conn_server_challenge(struct smbXcli_conn *conn)
690 {
691         return conn->smb1.server.challenge;
692 }
693
694 uint16_t smb1cli_conn_server_security_mode(struct smbXcli_conn *conn)
695 {
696         return conn->smb1.server.security_mode;
697 }
698
699 bool smb1cli_conn_server_readbraw(struct smbXcli_conn *conn)
700 {
701         return conn->smb1.server.readbraw;
702 }
703
704 bool smb1cli_conn_server_writebraw(struct smbXcli_conn *conn)
705 {
706         return conn->smb1.server.writebraw;
707 }
708
709 bool smb1cli_conn_server_lockread(struct smbXcli_conn *conn)
710 {
711         return conn->smb1.server.lockread;
712 }
713
714 bool smb1cli_conn_server_writeunlock(struct smbXcli_conn *conn)
715 {
716         return conn->smb1.server.writeunlock;
717 }
718
719 int smb1cli_conn_server_time_zone(struct smbXcli_conn *conn)
720 {
721         return conn->smb1.server.time_zone;
722 }
723
724 bool smb1cli_conn_activate_signing(struct smbXcli_conn *conn,
725                                    const DATA_BLOB user_session_key,
726                                    const DATA_BLOB response)
727 {
728         return smb_signing_activate(conn->smb1.signing,
729                                     user_session_key,
730                                     response);
731 }
732
733 bool smb1cli_conn_check_signing(struct smbXcli_conn *conn,
734                                 const uint8_t *buf, uint32_t seqnum)
735 {
736         const uint8_t *hdr = buf + NBT_HDR_SIZE;
737         size_t len = smb_len_nbt(buf);
738
739         return smb_signing_check_pdu(conn->smb1.signing, hdr, len, seqnum);
740 }
741
742 bool smb1cli_conn_signing_is_active(struct smbXcli_conn *conn)
743 {
744         return smb_signing_is_active(conn->smb1.signing);
745 }
746
747 void smb1cli_conn_set_encryption(struct smbXcli_conn *conn,
748                                  struct smb_trans_enc_state *es)
749 {
750         /* Replace the old state, if any. */
751         if (conn->smb1.trans_enc) {
752                 TALLOC_FREE(conn->smb1.trans_enc);
753         }
754         conn->smb1.trans_enc = es;
755 }
756
757 bool smb1cli_conn_encryption_on(struct smbXcli_conn *conn)
758 {
759         return common_encryption_on(conn->smb1.trans_enc);
760 }
761
762
763 static NTSTATUS smb1cli_pull_raw_error(const uint8_t *hdr)
764 {
765         uint32_t flags2 = SVAL(hdr, HDR_FLG2);
766         NTSTATUS status = NT_STATUS(IVAL(hdr, HDR_RCLS));
767
768         if (NT_STATUS_IS_OK(status)) {
769                 return NT_STATUS_OK;
770         }
771
772         if (flags2 & FLAGS2_32_BIT_ERROR_CODES) {
773                 return status;
774         }
775
776         return NT_STATUS_DOS(CVAL(hdr, HDR_RCLS), SVAL(hdr, HDR_ERR));
777 }
778
779 /**
780  * Is the SMB command able to hold an AND_X successor
781  * @param[in] cmd       The SMB command in question
782  * @retval Can we add a chained request after "cmd"?
783  */
784 bool smb1cli_is_andx_req(uint8_t cmd)
785 {
786         switch (cmd) {
787         case SMBtconX:
788         case SMBlockingX:
789         case SMBopenX:
790         case SMBreadX:
791         case SMBwriteX:
792         case SMBsesssetupX:
793         case SMBulogoffX:
794         case SMBntcreateX:
795                 return true;
796                 break;
797         default:
798                 break;
799         }
800
801         return false;
802 }
803
804 static uint16_t smb1cli_alloc_mid(struct smbXcli_conn *conn)
805 {
806         size_t num_pending = talloc_array_length(conn->pending);
807         uint16_t result;
808
809         if (conn->protocol == PROTOCOL_NONE) {
810                 /*
811                  * This is what windows sends on the SMB1 Negprot request
812                  * and some vendors reuse the SMB1 MID as SMB2 sequence number.
813                  */
814                 return 0;
815         }
816
817         while (true) {
818                 size_t i;
819
820                 result = conn->smb1.mid++;
821                 if ((result == 0) || (result == 0xffff)) {
822                         continue;
823                 }
824
825                 for (i=0; i<num_pending; i++) {
826                         if (result == smb1cli_req_mid(conn->pending[i])) {
827                                 break;
828                         }
829                 }
830
831                 if (i == num_pending) {
832                         return result;
833                 }
834         }
835 }
836
837 void smbXcli_req_unset_pending(struct tevent_req *req)
838 {
839         struct smbXcli_req_state *state =
840                 tevent_req_data(req,
841                 struct smbXcli_req_state);
842         struct smbXcli_conn *conn = state->conn;
843         size_t num_pending = talloc_array_length(conn->pending);
844         size_t i;
845
846         if (state->smb1.mid != 0) {
847                 /*
848                  * This is a [nt]trans[2] request which waits
849                  * for more than one reply.
850                  */
851                 return;
852         }
853
854         tevent_req_set_cleanup_fn(req, NULL);
855
856         if (num_pending == 1) {
857                 /*
858                  * The pending read_smb tevent_req is a child of
859                  * conn->pending. So if nothing is pending anymore, we need to
860                  * delete the socket read fde.
861                  */
862                 TALLOC_FREE(conn->pending);
863                 conn->read_smb_req = NULL;
864                 return;
865         }
866
867         for (i=0; i<num_pending; i++) {
868                 if (req == conn->pending[i]) {
869                         break;
870                 }
871         }
872         if (i == num_pending) {
873                 /*
874                  * Something's seriously broken. Just returning here is the
875                  * right thing nevertheless, the point of this routine is to
876                  * remove ourselves from conn->pending.
877                  */
878                 return;
879         }
880
881         /*
882          * Remove ourselves from the conn->pending array
883          */
884         for (; i < (num_pending - 1); i++) {
885                 conn->pending[i] = conn->pending[i+1];
886         }
887
888         /*
889          * No NULL check here, we're shrinking by sizeof(void *), and
890          * talloc_realloc just adjusts the size for this.
891          */
892         conn->pending = talloc_realloc(NULL, conn->pending, struct tevent_req *,
893                                        num_pending - 1);
894         return;
895 }
896
897 static void smbXcli_req_cleanup(struct tevent_req *req,
898                                 enum tevent_req_state req_state)
899 {
900         struct smbXcli_req_state *state =
901                 tevent_req_data(req,
902                 struct smbXcli_req_state);
903
904         switch (req_state) {
905         case TEVENT_REQ_RECEIVED:
906                 /*
907                  * Make sure we really remove it from
908                  * the pending array on destruction.
909                  */
910                 state->smb1.mid = 0;
911                 smbXcli_req_unset_pending(req);
912                 return;
913         default:
914                 return;
915         }
916 }
917
918 static bool smb1cli_req_cancel(struct tevent_req *req);
919 static bool smb2cli_req_cancel(struct tevent_req *req);
920
921 static bool smbXcli_req_cancel(struct tevent_req *req)
922 {
923         struct smbXcli_req_state *state =
924                 tevent_req_data(req,
925                 struct smbXcli_req_state);
926
927         if (!smbXcli_conn_is_connected(state->conn)) {
928                 return false;
929         }
930
931         if (state->conn->protocol == PROTOCOL_NONE) {
932                 return false;
933         }
934
935         if (state->conn->protocol >= PROTOCOL_SMB2_02) {
936                 return smb2cli_req_cancel(req);
937         }
938
939         return smb1cli_req_cancel(req);
940 }
941
942 static bool smbXcli_conn_receive_next(struct smbXcli_conn *conn);
943
944 bool smbXcli_req_set_pending(struct tevent_req *req)
945 {
946         struct smbXcli_req_state *state =
947                 tevent_req_data(req,
948                 struct smbXcli_req_state);
949         struct smbXcli_conn *conn;
950         struct tevent_req **pending;
951         size_t num_pending;
952
953         conn = state->conn;
954
955         if (!smbXcli_conn_is_connected(conn)) {
956                 return false;
957         }
958
959         num_pending = talloc_array_length(conn->pending);
960
961         pending = talloc_realloc(conn, conn->pending, struct tevent_req *,
962                                  num_pending+1);
963         if (pending == NULL) {
964                 return false;
965         }
966         pending[num_pending] = req;
967         conn->pending = pending;
968         tevent_req_set_cleanup_fn(req, smbXcli_req_cleanup);
969         tevent_req_set_cancel_fn(req, smbXcli_req_cancel);
970
971         if (!smbXcli_conn_receive_next(conn)) {
972                 /*
973                  * the caller should notify the current request
974                  *
975                  * And all other pending requests get notified
976                  * by smbXcli_conn_disconnect().
977                  */
978                 smbXcli_req_unset_pending(req);
979                 smbXcli_conn_disconnect(conn, NT_STATUS_NO_MEMORY);
980                 return false;
981         }
982
983         return true;
984 }
985
986 static void smbXcli_conn_received(struct tevent_req *subreq);
987
988 static bool smbXcli_conn_receive_next(struct smbXcli_conn *conn)
989 {
990         size_t num_pending = talloc_array_length(conn->pending);
991         struct tevent_req *req;
992         struct smbXcli_req_state *state;
993
994         if (conn->read_smb_req != NULL) {
995                 return true;
996         }
997
998         if (num_pending == 0) {
999                 if (conn->smb2.mid < UINT64_MAX) {
1000                         /* no more pending requests, so we are done for now */
1001                         return true;
1002                 }
1003
1004                 /*
1005                  * If there are no more SMB2 requests possible,
1006                  * because we are out of message ids,
1007                  * we need to disconnect.
1008                  */
1009                 smbXcli_conn_disconnect(conn, NT_STATUS_CONNECTION_ABORTED);
1010                 return true;
1011         }
1012
1013         req = conn->pending[0];
1014         state = tevent_req_data(req, struct smbXcli_req_state);
1015
1016         /*
1017          * We're the first ones, add the read_smb request that waits for the
1018          * answer from the server
1019          */
1020         conn->read_smb_req = read_smb_send(conn->pending,
1021                                            state->ev,
1022                                            conn->sock_fd);
1023         if (conn->read_smb_req == NULL) {
1024                 return false;
1025         }
1026         tevent_req_set_callback(conn->read_smb_req, smbXcli_conn_received, conn);
1027         return true;
1028 }
1029
1030 void smbXcli_conn_disconnect(struct smbXcli_conn *conn, NTSTATUS status)
1031 {
1032         struct smbXcli_session *session;
1033         int sock_fd = conn->sock_fd;
1034
1035         tevent_queue_stop(conn->outgoing);
1036
1037         conn->sock_fd = -1;
1038
1039         session = conn->sessions;
1040         if (talloc_array_length(conn->pending) == 0) {
1041                 /*
1042                  * if we do not have pending requests
1043                  * there is no need to update the channel_sequence
1044                  */
1045                 session = NULL;
1046         }
1047         for (; session; session = session->next) {
1048                 smb2cli_session_increment_channel_sequence(session);
1049         }
1050
1051         if (conn->suicide_req != NULL) {
1052                 /*
1053                  * smbXcli_conn_samba_suicide_send()
1054                  * used tevent_req_defer_callback() already.
1055                  */
1056                 if (!NT_STATUS_IS_OK(status)) {
1057                         tevent_req_nterror(conn->suicide_req, status);
1058                 }
1059                 conn->suicide_req = NULL;
1060         }
1061
1062         /*
1063          * Cancel all pending requests. We do not do a for-loop walking
1064          * conn->pending because that array changes in
1065          * smbXcli_req_unset_pending.
1066          */
1067         while (talloc_array_length(conn->pending) > 0) {
1068                 struct tevent_req *req;
1069                 struct smbXcli_req_state *state;
1070                 struct tevent_req **chain;
1071                 size_t num_chained;
1072                 size_t i;
1073
1074                 req = conn->pending[0];
1075                 state = tevent_req_data(req, struct smbXcli_req_state);
1076
1077                 if (state->smb1.chained_requests == NULL) {
1078                         /*
1079                          * We're dead. No point waiting for trans2
1080                          * replies.
1081                          */
1082                         state->smb1.mid = 0;
1083
1084                         smbXcli_req_unset_pending(req);
1085
1086                         if (NT_STATUS_IS_OK(status)) {
1087                                 /* do not notify the callers */
1088                                 continue;
1089                         }
1090
1091                         /*
1092                          * we need to defer the callback, because we may notify
1093                          * more then one caller.
1094                          */
1095                         tevent_req_defer_callback(req, state->ev);
1096                         tevent_req_nterror(req, status);
1097                         continue;
1098                 }
1099
1100                 chain = talloc_move(conn, &state->smb1.chained_requests);
1101                 num_chained = talloc_array_length(chain);
1102
1103                 for (i=0; i<num_chained; i++) {
1104                         req = chain[i];
1105                         state = tevent_req_data(req, struct smbXcli_req_state);
1106
1107                         /*
1108                          * We're dead. No point waiting for trans2
1109                          * replies.
1110                          */
1111                         state->smb1.mid = 0;
1112
1113                         smbXcli_req_unset_pending(req);
1114
1115                         if (NT_STATUS_IS_OK(status)) {
1116                                 /* do not notify the callers */
1117                                 continue;
1118                         }
1119
1120                         /*
1121                          * we need to defer the callback, because we may notify
1122                          * more than one caller.
1123                          */
1124                         tevent_req_defer_callback(req, state->ev);
1125                         tevent_req_nterror(req, status);
1126                 }
1127                 TALLOC_FREE(chain);
1128         }
1129
1130         if (sock_fd != -1) {
1131                 close(sock_fd);
1132         }
1133 }
1134
1135 /*
1136  * Fetch a smb request's mid. Only valid after the request has been sent by
1137  * smb1cli_req_send().
1138  */
1139 uint16_t smb1cli_req_mid(struct tevent_req *req)
1140 {
1141         struct smbXcli_req_state *state =
1142                 tevent_req_data(req,
1143                 struct smbXcli_req_state);
1144
1145         if (state->smb1.mid != 0) {
1146                 return state->smb1.mid;
1147         }
1148
1149         return SVAL(state->smb1.hdr, HDR_MID);
1150 }
1151
1152 void smb1cli_req_set_mid(struct tevent_req *req, uint16_t mid)
1153 {
1154         struct smbXcli_req_state *state =
1155                 tevent_req_data(req,
1156                 struct smbXcli_req_state);
1157
1158         state->smb1.mid = mid;
1159 }
1160
1161 uint32_t smb1cli_req_seqnum(struct tevent_req *req)
1162 {
1163         struct smbXcli_req_state *state =
1164                 tevent_req_data(req,
1165                 struct smbXcli_req_state);
1166
1167         return state->smb1.seqnum;
1168 }
1169
1170 void smb1cli_req_set_seqnum(struct tevent_req *req, uint32_t seqnum)
1171 {
1172         struct smbXcli_req_state *state =
1173                 tevent_req_data(req,
1174                 struct smbXcli_req_state);
1175
1176         state->smb1.seqnum = seqnum;
1177 }
1178
1179 static size_t smbXcli_iov_len(const struct iovec *iov, int count)
1180 {
1181         ssize_t ret = iov_buflen(iov, count);
1182
1183         /* Ignore the overflow case for now ... */
1184         return ret;
1185 }
1186
1187 static uint8_t *smbXcli_iov_concat(TALLOC_CTX *mem_ctx,
1188                                    const struct iovec *iov,
1189                                    int count)
1190 {
1191         ssize_t buflen;
1192         uint8_t *buf;
1193
1194         buflen = iov_buflen(iov, count);
1195         if (buflen == -1) {
1196                 return NULL;
1197         }
1198
1199         buf = talloc_array(mem_ctx, uint8_t, buflen);
1200         if (buf == NULL) {
1201                 return NULL;
1202         }
1203
1204         iov_buf(iov, count, buf, buflen);
1205
1206         return buf;
1207 }
1208
1209 static void smb1cli_req_flags(enum protocol_types protocol,
1210                               uint32_t smb1_capabilities,
1211                               uint8_t smb_command,
1212                               uint8_t additional_flags,
1213                               uint8_t clear_flags,
1214                               uint8_t *_flags,
1215                               uint16_t additional_flags2,
1216                               uint16_t clear_flags2,
1217                               uint16_t *_flags2)
1218 {
1219         uint8_t flags = 0;
1220         uint16_t flags2 = 0;
1221
1222         if (protocol >= PROTOCOL_LANMAN1) {
1223                 flags |= FLAG_CASELESS_PATHNAMES;
1224                 flags |= FLAG_CANONICAL_PATHNAMES;
1225         }
1226
1227         if (protocol >= PROTOCOL_LANMAN2) {
1228                 flags2 |= FLAGS2_LONG_PATH_COMPONENTS;
1229                 flags2 |= FLAGS2_EXTENDED_ATTRIBUTES;
1230         }
1231
1232         if (protocol >= PROTOCOL_NT1) {
1233                 flags2 |= FLAGS2_IS_LONG_NAME;
1234
1235                 if (smb1_capabilities & CAP_UNICODE) {
1236                         flags2 |= FLAGS2_UNICODE_STRINGS;
1237                 }
1238                 if (smb1_capabilities & CAP_STATUS32) {
1239                         flags2 |= FLAGS2_32_BIT_ERROR_CODES;
1240                 }
1241                 if (smb1_capabilities & CAP_EXTENDED_SECURITY) {
1242                         flags2 |= FLAGS2_EXTENDED_SECURITY;
1243                 }
1244         }
1245
1246         flags |= additional_flags;
1247         flags &= ~clear_flags;
1248         flags2 |= additional_flags2;
1249         flags2 &= ~clear_flags2;
1250
1251         *_flags = flags;
1252         *_flags2 = flags2;
1253 }
1254
1255 static void smb1cli_req_cancel_done(struct tevent_req *subreq);
1256
1257 static bool smb1cli_req_cancel(struct tevent_req *req)
1258 {
1259         struct smbXcli_req_state *state =
1260                 tevent_req_data(req,
1261                 struct smbXcli_req_state);
1262         uint8_t flags;
1263         uint16_t flags2;
1264         uint32_t pid;
1265         uint16_t mid;
1266         struct tevent_req *subreq;
1267         NTSTATUS status;
1268
1269         flags = CVAL(state->smb1.hdr, HDR_FLG);
1270         flags2 = SVAL(state->smb1.hdr, HDR_FLG2);
1271         pid  = SVAL(state->smb1.hdr, HDR_PID);
1272         pid |= SVAL(state->smb1.hdr, HDR_PIDHIGH)<<16;
1273         mid = SVAL(state->smb1.hdr, HDR_MID);
1274
1275         subreq = smb1cli_req_create(state, state->ev,
1276                                     state->conn,
1277                                     SMBntcancel,
1278                                     flags, 0,
1279                                     flags2, 0,
1280                                     0, /* timeout */
1281                                     pid,
1282                                     state->tcon,
1283                                     state->session,
1284                                     0, NULL, /* vwv */
1285                                     0, NULL); /* bytes */
1286         if (subreq == NULL) {
1287                 return false;
1288         }
1289         smb1cli_req_set_mid(subreq, mid);
1290
1291         status = smb1cli_req_chain_submit(&subreq, 1);
1292         if (!NT_STATUS_IS_OK(status)) {
1293                 TALLOC_FREE(subreq);
1294                 return false;
1295         }
1296         smb1cli_req_set_mid(subreq, 0);
1297
1298         tevent_req_set_callback(subreq, smb1cli_req_cancel_done, NULL);
1299
1300         return true;
1301 }
1302
1303 static void smb1cli_req_cancel_done(struct tevent_req *subreq)
1304 {
1305         /* we do not care about the result */
1306         TALLOC_FREE(subreq);
1307 }
1308
1309 struct tevent_req *smb1cli_req_create(TALLOC_CTX *mem_ctx,
1310                                       struct tevent_context *ev,
1311                                       struct smbXcli_conn *conn,
1312                                       uint8_t smb_command,
1313                                       uint8_t additional_flags,
1314                                       uint8_t clear_flags,
1315                                       uint16_t additional_flags2,
1316                                       uint16_t clear_flags2,
1317                                       uint32_t timeout_msec,
1318                                       uint32_t pid,
1319                                       struct smbXcli_tcon *tcon,
1320                                       struct smbXcli_session *session,
1321                                       uint8_t wct, uint16_t *vwv,
1322                                       int iov_count,
1323                                       struct iovec *bytes_iov)
1324 {
1325         struct tevent_req *req;
1326         struct smbXcli_req_state *state;
1327         uint8_t flags = 0;
1328         uint16_t flags2 = 0;
1329         uint16_t uid = 0;
1330         uint16_t tid = 0;
1331         ssize_t num_bytes;
1332
1333         if (iov_count > MAX_SMB_IOV) {
1334                 /*
1335                  * Should not happen :-)
1336                  */
1337                 return NULL;
1338         }
1339
1340         req = tevent_req_create(mem_ctx, &state,
1341                                 struct smbXcli_req_state);
1342         if (req == NULL) {
1343                 return NULL;
1344         }
1345         state->ev = ev;
1346         state->conn = conn;
1347         state->session = session;
1348         state->tcon = tcon;
1349
1350         if (session) {
1351                 uid = session->smb1.session_id;
1352         }
1353
1354         if (tcon) {
1355                 tid = tcon->smb1.tcon_id;
1356
1357                 if (tcon->fs_attributes & FILE_CASE_SENSITIVE_SEARCH) {
1358                         clear_flags |= FLAG_CASELESS_PATHNAMES;
1359                 } else {
1360                         /* Default setting, case insensitive. */
1361                         additional_flags |= FLAG_CASELESS_PATHNAMES;
1362                 }
1363
1364                 if (smbXcli_conn_dfs_supported(conn) &&
1365                     smbXcli_tcon_is_dfs_share(tcon))
1366                 {
1367                         additional_flags2 |= FLAGS2_DFS_PATHNAMES;
1368                 }
1369         }
1370
1371         state->smb1.recv_cmd = 0xFF;
1372         state->smb1.recv_status = NT_STATUS_INTERNAL_ERROR;
1373         state->smb1.recv_iov = talloc_zero_array(state, struct iovec, 3);
1374         if (state->smb1.recv_iov == NULL) {
1375                 TALLOC_FREE(req);
1376                 return NULL;
1377         }
1378
1379         smb1cli_req_flags(conn->protocol,
1380                           conn->smb1.capabilities,
1381                           smb_command,
1382                           additional_flags,
1383                           clear_flags,
1384                           &flags,
1385                           additional_flags2,
1386                           clear_flags2,
1387                           &flags2);
1388
1389         SIVAL(state->smb1.hdr, 0,           SMB_MAGIC);
1390         SCVAL(state->smb1.hdr, HDR_COM,     smb_command);
1391         SIVAL(state->smb1.hdr, HDR_RCLS,    NT_STATUS_V(NT_STATUS_OK));
1392         SCVAL(state->smb1.hdr, HDR_FLG,     flags);
1393         SSVAL(state->smb1.hdr, HDR_FLG2,    flags2);
1394         SSVAL(state->smb1.hdr, HDR_PIDHIGH, pid >> 16);
1395         SSVAL(state->smb1.hdr, HDR_TID,     tid);
1396         SSVAL(state->smb1.hdr, HDR_PID,     pid);
1397         SSVAL(state->smb1.hdr, HDR_UID,     uid);
1398         SSVAL(state->smb1.hdr, HDR_MID,     0); /* this comes later */
1399         SCVAL(state->smb1.hdr, HDR_WCT,     wct);
1400
1401         state->smb1.vwv = vwv;
1402
1403         num_bytes = iov_buflen(bytes_iov, iov_count);
1404         if (num_bytes == -1) {
1405                 /*
1406                  * I'd love to add a check for num_bytes<=UINT16_MAX here, but
1407                  * the smbclient->samba connections can lie and transfer more.
1408                  */
1409                 TALLOC_FREE(req);
1410                 return NULL;
1411         }
1412
1413         SSVAL(state->smb1.bytecount_buf, 0, num_bytes);
1414
1415         state->smb1.iov[0].iov_base = (void *)state->length_hdr;
1416         state->smb1.iov[0].iov_len  = sizeof(state->length_hdr);
1417         state->smb1.iov[1].iov_base = (void *)state->smb1.hdr;
1418         state->smb1.iov[1].iov_len  = sizeof(state->smb1.hdr);
1419         state->smb1.iov[2].iov_base = (void *)state->smb1.vwv;
1420         state->smb1.iov[2].iov_len  = wct * sizeof(uint16_t);
1421         state->smb1.iov[3].iov_base = (void *)state->smb1.bytecount_buf;
1422         state->smb1.iov[3].iov_len  = sizeof(uint16_t);
1423
1424         if (iov_count != 0) {
1425                 memcpy(&state->smb1.iov[4], bytes_iov,
1426                        iov_count * sizeof(*bytes_iov));
1427         }
1428         state->smb1.iov_count = iov_count + 4;
1429
1430         if (timeout_msec > 0) {
1431                 struct timeval endtime;
1432
1433                 endtime = timeval_current_ofs_msec(timeout_msec);
1434                 if (!tevent_req_set_endtime(req, ev, endtime)) {
1435                         return req;
1436                 }
1437         }
1438
1439         switch (smb_command) {
1440         case SMBtranss:
1441         case SMBtranss2:
1442         case SMBnttranss:
1443                 state->one_way = true;
1444                 break;
1445         case SMBntcancel:
1446                 state->one_way = true;
1447                 state->smb1.one_way_seqnum = true;
1448                 break;
1449         case SMBlockingX:
1450                 if ((wct == 8) &&
1451                     (CVAL(vwv+3, 0) == LOCKING_ANDX_OPLOCK_RELEASE)) {
1452                         state->one_way = true;
1453                 }
1454                 break;
1455         }
1456
1457         return req;
1458 }
1459
1460 static NTSTATUS smb1cli_conn_signv(struct smbXcli_conn *conn,
1461                                    struct iovec *iov, int iov_count,
1462                                    uint32_t *seqnum,
1463                                    bool one_way_seqnum)
1464 {
1465         TALLOC_CTX *frame = NULL;
1466         uint8_t *buf;
1467
1468         /*
1469          * Obvious optimization: Make cli_calculate_sign_mac work with struct
1470          * iovec directly. MD5Update would do that just fine.
1471          */
1472
1473         if (iov_count < 4) {
1474                 return NT_STATUS_INVALID_PARAMETER_MIX;
1475         }
1476         if (iov[0].iov_len != NBT_HDR_SIZE) {
1477                 return NT_STATUS_INVALID_PARAMETER_MIX;
1478         }
1479         if (iov[1].iov_len != (MIN_SMB_SIZE-sizeof(uint16_t))) {
1480                 return NT_STATUS_INVALID_PARAMETER_MIX;
1481         }
1482         if (iov[2].iov_len > (0xFF * sizeof(uint16_t))) {
1483                 return NT_STATUS_INVALID_PARAMETER_MIX;
1484         }
1485         if (iov[3].iov_len != sizeof(uint16_t)) {
1486                 return NT_STATUS_INVALID_PARAMETER_MIX;
1487         }
1488
1489         frame = talloc_stackframe();
1490
1491         buf = smbXcli_iov_concat(frame, &iov[1], iov_count - 1);
1492         if (buf == NULL) {
1493                 return NT_STATUS_NO_MEMORY;
1494         }
1495
1496         *seqnum = smb_signing_next_seqnum(conn->smb1.signing,
1497                                           one_way_seqnum);
1498         smb_signing_sign_pdu(conn->smb1.signing,
1499                              buf, talloc_get_size(buf),
1500                              *seqnum);
1501         memcpy(iov[1].iov_base, buf, iov[1].iov_len);
1502
1503         TALLOC_FREE(frame);
1504         return NT_STATUS_OK;
1505 }
1506
1507 static void smb1cli_req_writev_done(struct tevent_req *subreq);
1508 static NTSTATUS smb1cli_conn_dispatch_incoming(struct smbXcli_conn *conn,
1509                                                TALLOC_CTX *tmp_mem,
1510                                                uint8_t *inbuf);
1511
1512 static NTSTATUS smb1cli_req_writev_submit(struct tevent_req *req,
1513                                           struct smbXcli_req_state *state,
1514                                           struct iovec *iov, int iov_count)
1515 {
1516         struct tevent_req *subreq;
1517         NTSTATUS status;
1518         uint8_t cmd;
1519         uint16_t mid;
1520         ssize_t nbtlen;
1521
1522         if (!smbXcli_conn_is_connected(state->conn)) {
1523                 return NT_STATUS_CONNECTION_DISCONNECTED;
1524         }
1525
1526         if (state->conn->protocol > PROTOCOL_NT1) {
1527                 return NT_STATUS_REVISION_MISMATCH;
1528         }
1529
1530         if (iov_count < 4) {
1531                 return NT_STATUS_INVALID_PARAMETER_MIX;
1532         }
1533         if (iov[0].iov_len != NBT_HDR_SIZE) {
1534                 return NT_STATUS_INVALID_PARAMETER_MIX;
1535         }
1536         if (iov[1].iov_len != (MIN_SMB_SIZE-sizeof(uint16_t))) {
1537                 return NT_STATUS_INVALID_PARAMETER_MIX;
1538         }
1539         if (iov[2].iov_len > (0xFF * sizeof(uint16_t))) {
1540                 return NT_STATUS_INVALID_PARAMETER_MIX;
1541         }
1542         if (iov[3].iov_len != sizeof(uint16_t)) {
1543                 return NT_STATUS_INVALID_PARAMETER_MIX;
1544         }
1545
1546         cmd = CVAL(iov[1].iov_base, HDR_COM);
1547         if (cmd == SMBreadBraw) {
1548                 if (smbXcli_conn_has_async_calls(state->conn)) {
1549                         return NT_STATUS_INVALID_PARAMETER_MIX;
1550                 }
1551                 state->conn->smb1.read_braw_req = req;
1552         }
1553
1554         if (state->smb1.mid != 0) {
1555                 mid = state->smb1.mid;
1556         } else {
1557                 mid = smb1cli_alloc_mid(state->conn);
1558         }
1559         SSVAL(iov[1].iov_base, HDR_MID, mid);
1560
1561         nbtlen = iov_buflen(&iov[1], iov_count-1);
1562         if ((nbtlen == -1) || (nbtlen > 0x1FFFF)) {
1563                 return NT_STATUS_INVALID_PARAMETER_MIX;
1564         }
1565
1566         _smb_setlen_nbt(iov[0].iov_base, nbtlen);
1567
1568         status = smb1cli_conn_signv(state->conn, iov, iov_count,
1569                                     &state->smb1.seqnum,
1570                                     state->smb1.one_way_seqnum);
1571
1572         if (!NT_STATUS_IS_OK(status)) {
1573                 return status;
1574         }
1575
1576         /*
1577          * If we supported multiple encrytion contexts
1578          * here we'd look up based on tid.
1579          */
1580         if (common_encryption_on(state->conn->smb1.trans_enc)) {
1581                 char *buf, *enc_buf;
1582
1583                 buf = (char *)smbXcli_iov_concat(talloc_tos(), iov, iov_count);
1584                 if (buf == NULL) {
1585                         return NT_STATUS_NO_MEMORY;
1586                 }
1587                 status = common_encrypt_buffer(state->conn->smb1.trans_enc,
1588                                                (char *)buf, &enc_buf);
1589                 TALLOC_FREE(buf);
1590                 if (!NT_STATUS_IS_OK(status)) {
1591                         DEBUG(0, ("Error in encrypting client message: %s\n",
1592                                   nt_errstr(status)));
1593                         return status;
1594                 }
1595                 buf = (char *)talloc_memdup(state, enc_buf,
1596                                             smb_len_nbt(enc_buf)+4);
1597                 SAFE_FREE(enc_buf);
1598                 if (buf == NULL) {
1599                         return NT_STATUS_NO_MEMORY;
1600                 }
1601                 iov[0].iov_base = (void *)buf;
1602                 iov[0].iov_len = talloc_get_size(buf);
1603                 iov_count = 1;
1604         }
1605
1606         if (state->conn->dispatch_incoming == NULL) {
1607                 state->conn->dispatch_incoming = smb1cli_conn_dispatch_incoming;
1608         }
1609
1610         tevent_req_set_cancel_fn(req, smbXcli_req_cancel);
1611
1612         subreq = writev_send(state, state->ev, state->conn->outgoing,
1613                              state->conn->sock_fd, false, iov, iov_count);
1614         if (subreq == NULL) {
1615                 return NT_STATUS_NO_MEMORY;
1616         }
1617         tevent_req_set_callback(subreq, smb1cli_req_writev_done, req);
1618         return NT_STATUS_OK;
1619 }
1620
1621 struct tevent_req *smb1cli_req_send(TALLOC_CTX *mem_ctx,
1622                                     struct tevent_context *ev,
1623                                     struct smbXcli_conn *conn,
1624                                     uint8_t smb_command,
1625                                     uint8_t additional_flags,
1626                                     uint8_t clear_flags,
1627                                     uint16_t additional_flags2,
1628                                     uint16_t clear_flags2,
1629                                     uint32_t timeout_msec,
1630                                     uint32_t pid,
1631                                     struct smbXcli_tcon *tcon,
1632                                     struct smbXcli_session *session,
1633                                     uint8_t wct, uint16_t *vwv,
1634                                     uint32_t num_bytes,
1635                                     const uint8_t *bytes)
1636 {
1637         struct tevent_req *req;
1638         struct iovec iov;
1639         NTSTATUS status;
1640
1641         iov.iov_base = discard_const_p(void, bytes);
1642         iov.iov_len = num_bytes;
1643
1644         req = smb1cli_req_create(mem_ctx, ev, conn, smb_command,
1645                                  additional_flags, clear_flags,
1646                                  additional_flags2, clear_flags2,
1647                                  timeout_msec,
1648                                  pid, tcon, session,
1649                                  wct, vwv, 1, &iov);
1650         if (req == NULL) {
1651                 return NULL;
1652         }
1653         if (!tevent_req_is_in_progress(req)) {
1654                 return tevent_req_post(req, ev);
1655         }
1656         status = smb1cli_req_chain_submit(&req, 1);
1657         if (tevent_req_nterror(req, status)) {
1658                 return tevent_req_post(req, ev);
1659         }
1660         return req;
1661 }
1662
1663 static void smb1cli_req_writev_done(struct tevent_req *subreq)
1664 {
1665         struct tevent_req *req =
1666                 tevent_req_callback_data(subreq,
1667                 struct tevent_req);
1668         struct smbXcli_req_state *state =
1669                 tevent_req_data(req,
1670                 struct smbXcli_req_state);
1671         ssize_t nwritten;
1672         int err;
1673
1674         nwritten = writev_recv(subreq, &err);
1675         TALLOC_FREE(subreq);
1676         if (nwritten == -1) {
1677                 NTSTATUS status = map_nt_error_from_unix_common(err);
1678                 smbXcli_conn_disconnect(state->conn, status);
1679                 tevent_req_nterror(req, status);
1680                 return;
1681         }
1682
1683         if (state->one_way) {
1684                 state->inbuf = NULL;
1685                 tevent_req_done(req);
1686                 return;
1687         }
1688
1689         if (!smbXcli_req_set_pending(req)) {
1690                 tevent_req_nterror(req, NT_STATUS_NO_MEMORY);
1691                 return;
1692         }
1693 }
1694
1695 static void smbXcli_conn_received(struct tevent_req *subreq)
1696 {
1697         struct smbXcli_conn *conn =
1698                 tevent_req_callback_data(subreq,
1699                 struct smbXcli_conn);
1700         TALLOC_CTX *frame = talloc_stackframe();
1701         NTSTATUS status;
1702         uint8_t *inbuf;
1703         ssize_t received;
1704         int err;
1705
1706         if (subreq != conn->read_smb_req) {
1707                 DEBUG(1, ("Internal error: cli_smb_received called with "
1708                           "unexpected subreq\n"));
1709                 smbXcli_conn_disconnect(conn, NT_STATUS_INTERNAL_ERROR);
1710                 TALLOC_FREE(frame);
1711                 return;
1712         }
1713         conn->read_smb_req = NULL;
1714
1715         received = read_smb_recv(subreq, frame, &inbuf, &err);
1716         TALLOC_FREE(subreq);
1717         if (received == -1) {
1718                 status = map_nt_error_from_unix_common(err);
1719                 smbXcli_conn_disconnect(conn, status);
1720                 TALLOC_FREE(frame);
1721                 return;
1722         }
1723
1724         status = conn->dispatch_incoming(conn, frame, inbuf);
1725         TALLOC_FREE(frame);
1726         if (NT_STATUS_IS_OK(status)) {
1727                 /*
1728                  * We should not do any more processing
1729                  * as the dispatch function called
1730                  * tevent_req_done().
1731                  */
1732                 return;
1733         }
1734
1735         if (!NT_STATUS_EQUAL(status, NT_STATUS_RETRY)) {
1736                 /*
1737                  * We got an error, so notify all pending requests
1738                  */
1739                 smbXcli_conn_disconnect(conn, status);
1740                 return;
1741         }
1742
1743         /*
1744          * We got NT_STATUS_RETRY, so we may ask for a
1745          * next incoming pdu.
1746          */
1747         if (!smbXcli_conn_receive_next(conn)) {
1748                 smbXcli_conn_disconnect(conn, NT_STATUS_NO_MEMORY);
1749         }
1750 }
1751
1752 static NTSTATUS smb1cli_inbuf_parse_chain(uint8_t *buf, TALLOC_CTX *mem_ctx,
1753                                           struct iovec **piov, int *pnum_iov)
1754 {
1755         struct iovec *iov;
1756         int num_iov;
1757         size_t buflen;
1758         size_t taken;
1759         size_t remaining;
1760         uint8_t *hdr;
1761         uint8_t cmd;
1762         uint32_t wct_ofs;
1763         NTSTATUS status;
1764         size_t min_size = MIN_SMB_SIZE;
1765
1766         buflen = smb_len_tcp(buf);
1767         taken = 0;
1768
1769         hdr = buf + NBT_HDR_SIZE;
1770
1771         status = smb1cli_pull_raw_error(hdr);
1772         if (NT_STATUS_IS_ERR(status)) {
1773                 /*
1774                  * This is an ugly hack to support OS/2
1775                  * which skips the byte_count in the DATA block
1776                  * on some error responses.
1777                  *
1778                  * See bug #9096
1779                  */
1780                 min_size -= sizeof(uint16_t);
1781         }
1782
1783         if (buflen < min_size) {
1784                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
1785         }
1786
1787         /*
1788          * This returns iovec elements in the following order:
1789          *
1790          * - SMB header
1791          *
1792          * - Parameter Block
1793          * - Data Block
1794          *
1795          * - Parameter Block
1796          * - Data Block
1797          *
1798          * - Parameter Block
1799          * - Data Block
1800          */
1801         num_iov = 1;
1802
1803         iov = talloc_array(mem_ctx, struct iovec, num_iov);
1804         if (iov == NULL) {
1805                 return NT_STATUS_NO_MEMORY;
1806         }
1807         iov[0].iov_base = hdr;
1808         iov[0].iov_len = HDR_WCT;
1809         taken += HDR_WCT;
1810
1811         cmd = CVAL(hdr, HDR_COM);
1812         wct_ofs = HDR_WCT;
1813
1814         while (true) {
1815                 size_t len = buflen - taken;
1816                 struct iovec *cur;
1817                 struct iovec *iov_tmp;
1818                 uint8_t wct;
1819                 uint32_t bcc_ofs;
1820                 uint16_t bcc;
1821                 size_t needed;
1822
1823                 /*
1824                  * we need at least WCT
1825                  */
1826                 needed = sizeof(uint8_t);
1827                 if (len < needed) {
1828                         DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
1829                                    __location__, (int)len, (int)needed));
1830                         goto inval;
1831                 }
1832
1833                 /*
1834                  * Now we check if the specified words are there
1835                  */
1836                 wct = CVAL(hdr, wct_ofs);
1837                 needed += wct * sizeof(uint16_t);
1838                 if (len < needed) {
1839                         DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
1840                                    __location__, (int)len, (int)needed));
1841                         goto inval;
1842                 }
1843
1844                 if ((num_iov == 1) &&
1845                     (len == needed) &&
1846                     NT_STATUS_IS_ERR(status))
1847                 {
1848                         /*
1849                          * This is an ugly hack to support OS/2
1850                          * which skips the byte_count in the DATA block
1851                          * on some error responses.
1852                          *
1853                          * See bug #9096
1854                          */
1855                         iov_tmp = talloc_realloc(mem_ctx, iov, struct iovec,
1856                                                  num_iov + 2);
1857                         if (iov_tmp == NULL) {
1858                                 TALLOC_FREE(iov);
1859                                 return NT_STATUS_NO_MEMORY;
1860                         }
1861                         iov = iov_tmp;
1862                         cur = &iov[num_iov];
1863                         num_iov += 2;
1864
1865                         cur[0].iov_len = 0;
1866                         cur[0].iov_base = hdr + (wct_ofs + sizeof(uint8_t));
1867                         cur[1].iov_len = 0;
1868                         cur[1].iov_base = cur[0].iov_base;
1869
1870                         taken += needed;
1871                         break;
1872                 }
1873
1874                 /*
1875                  * we need at least BCC
1876                  */
1877                 needed += sizeof(uint16_t);
1878                 if (len < needed) {
1879                         DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
1880                                    __location__, (int)len, (int)needed));
1881                         goto inval;
1882                 }
1883
1884                 /*
1885                  * Now we check if the specified bytes are there
1886                  */
1887                 bcc_ofs = wct_ofs + sizeof(uint8_t) + wct * sizeof(uint16_t);
1888                 bcc = SVAL(hdr, bcc_ofs);
1889                 needed += bcc * sizeof(uint8_t);
1890                 if (len < needed) {
1891                         DEBUG(10, ("%s: %d bytes left, expected at least %d\n",
1892                                    __location__, (int)len, (int)needed));
1893                         goto inval;
1894                 }
1895
1896                 /*
1897                  * we allocate 2 iovec structures for words and bytes
1898                  */
1899                 iov_tmp = talloc_realloc(mem_ctx, iov, struct iovec,
1900                                          num_iov + 2);
1901                 if (iov_tmp == NULL) {
1902                         TALLOC_FREE(iov);
1903                         return NT_STATUS_NO_MEMORY;
1904                 }
1905                 iov = iov_tmp;
1906                 cur = &iov[num_iov];
1907                 num_iov += 2;
1908
1909                 cur[0].iov_len = wct * sizeof(uint16_t);
1910                 cur[0].iov_base = hdr + (wct_ofs + sizeof(uint8_t));
1911                 cur[1].iov_len = bcc * sizeof(uint8_t);
1912                 cur[1].iov_base = hdr + (bcc_ofs + sizeof(uint16_t));
1913
1914                 taken += needed;
1915
1916                 if (!smb1cli_is_andx_req(cmd)) {
1917                         /*
1918                          * If the current command does not have AndX chanining
1919                          * we are done.
1920                          */
1921                         break;
1922                 }
1923
1924                 if (wct == 0 && bcc == 0) {
1925                         /*
1926                          * An empty response also ends the chain,
1927                          * most likely with an error.
1928                          */
1929                         break;
1930                 }
1931
1932                 if (wct < 2) {
1933                         DEBUG(10, ("%s: wct[%d] < 2 for cmd[0x%02X]\n",
1934                                    __location__, (int)wct, (int)cmd));
1935                         goto inval;
1936                 }
1937                 cmd = CVAL(cur[0].iov_base, 0);
1938                 if (cmd == 0xFF) {
1939                         /*
1940                          * If it is the end of the chain we are also done.
1941                          */
1942                         break;
1943                 }
1944                 wct_ofs = SVAL(cur[0].iov_base, 2);
1945
1946                 if (wct_ofs < taken) {
1947                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
1948                 }
1949                 if (wct_ofs > buflen) {
1950                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
1951                 }
1952
1953                 /*
1954                  * we consumed everything up to the start of the next
1955                  * parameter block.
1956                  */
1957                 taken = wct_ofs;
1958         }
1959
1960         remaining = buflen - taken;
1961
1962         if (remaining > 0 && num_iov >= 3) {
1963                 /*
1964                  * The last DATA block gets the remaining
1965                  * bytes, this is needed to support
1966                  * CAP_LARGE_WRITEX and CAP_LARGE_READX.
1967                  */
1968                 iov[num_iov-1].iov_len += remaining;
1969         }
1970
1971         *piov = iov;
1972         *pnum_iov = num_iov;
1973         return NT_STATUS_OK;
1974
1975 inval:
1976         TALLOC_FREE(iov);
1977         return NT_STATUS_INVALID_NETWORK_RESPONSE;
1978 }
1979
1980 static NTSTATUS smb1cli_conn_dispatch_incoming(struct smbXcli_conn *conn,
1981                                                TALLOC_CTX *tmp_mem,
1982                                                uint8_t *inbuf)
1983 {
1984         struct tevent_req *req;
1985         struct smbXcli_req_state *state;
1986         NTSTATUS status;
1987         size_t num_pending;
1988         size_t i;
1989         uint8_t cmd;
1990         uint16_t mid;
1991         bool oplock_break;
1992         uint8_t *inhdr = inbuf + NBT_HDR_SIZE;
1993         size_t len = smb_len_tcp(inbuf);
1994         struct iovec *iov = NULL;
1995         int num_iov = 0;
1996         struct tevent_req **chain = NULL;
1997         size_t num_chained = 0;
1998         size_t num_responses = 0;
1999
2000         if (conn->smb1.read_braw_req != NULL) {
2001                 req = conn->smb1.read_braw_req;
2002                 conn->smb1.read_braw_req = NULL;
2003                 state = tevent_req_data(req, struct smbXcli_req_state);
2004
2005                 smbXcli_req_unset_pending(req);
2006
2007                 if (state->smb1.recv_iov == NULL) {
2008                         /*
2009                          * For requests with more than
2010                          * one response, we have to readd the
2011                          * recv_iov array.
2012                          */
2013                         state->smb1.recv_iov = talloc_zero_array(state,
2014                                                                  struct iovec,
2015                                                                  3);
2016                         if (tevent_req_nomem(state->smb1.recv_iov, req)) {
2017                                 return NT_STATUS_OK;
2018                         }
2019                 }
2020
2021                 state->smb1.recv_iov[0].iov_base = (void *)(inhdr);
2022                 state->smb1.recv_iov[0].iov_len = len;
2023                 ZERO_STRUCT(state->smb1.recv_iov[1]);
2024                 ZERO_STRUCT(state->smb1.recv_iov[2]);
2025
2026                 state->smb1.recv_cmd = SMBreadBraw;
2027                 state->smb1.recv_status = NT_STATUS_OK;
2028                 state->inbuf = talloc_move(state->smb1.recv_iov, &inbuf);
2029
2030                 tevent_req_done(req);
2031                 return NT_STATUS_OK;
2032         }
2033
2034         if ((IVAL(inhdr, 0) != SMB_MAGIC) /* 0xFF"SMB" */
2035             && (SVAL(inhdr, 0) != 0x45ff)) /* 0xFF"E" */ {
2036                 DEBUG(10, ("Got non-SMB PDU\n"));
2037                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
2038         }
2039
2040         /*
2041          * If we supported multiple encrytion contexts
2042          * here we'd look up based on tid.
2043          */
2044         if (common_encryption_on(conn->smb1.trans_enc)
2045             && (CVAL(inbuf, 0) == 0)) {
2046                 uint16_t enc_ctx_num;
2047
2048                 status = get_enc_ctx_num(inbuf, &enc_ctx_num);
2049                 if (!NT_STATUS_IS_OK(status)) {
2050                         DEBUG(10, ("get_enc_ctx_num returned %s\n",
2051                                    nt_errstr(status)));
2052                         return status;
2053                 }
2054
2055                 if (enc_ctx_num != conn->smb1.trans_enc->enc_ctx_num) {
2056                         DEBUG(10, ("wrong enc_ctx %d, expected %d\n",
2057                                    enc_ctx_num,
2058                                    conn->smb1.trans_enc->enc_ctx_num));
2059                         return NT_STATUS_INVALID_HANDLE;
2060                 }
2061
2062                 status = common_decrypt_buffer(conn->smb1.trans_enc,
2063                                                (char *)inbuf);
2064                 if (!NT_STATUS_IS_OK(status)) {
2065                         DEBUG(10, ("common_decrypt_buffer returned %s\n",
2066                                    nt_errstr(status)));
2067                         return status;
2068                 }
2069                 inhdr = inbuf + NBT_HDR_SIZE;
2070                 len = smb_len_nbt(inbuf);
2071         }
2072
2073         mid = SVAL(inhdr, HDR_MID);
2074         num_pending = talloc_array_length(conn->pending);
2075
2076         for (i=0; i<num_pending; i++) {
2077                 if (mid == smb1cli_req_mid(conn->pending[i])) {
2078                         break;
2079                 }
2080         }
2081         if (i == num_pending) {
2082                 /* Dump unexpected reply */
2083                 return NT_STATUS_RETRY;
2084         }
2085
2086         oplock_break = false;
2087
2088         if (mid == 0xffff) {
2089                 /*
2090                  * Paranoia checks that this is really an oplock break request.
2091                  */
2092                 oplock_break = (len == 51); /* hdr + 8 words */
2093                 oplock_break &= ((CVAL(inhdr, HDR_FLG) & FLAG_REPLY) == 0);
2094                 oplock_break &= (CVAL(inhdr, HDR_COM) == SMBlockingX);
2095                 oplock_break &= (SVAL(inhdr, HDR_VWV+VWV(6)) == 0);
2096                 oplock_break &= (SVAL(inhdr, HDR_VWV+VWV(7)) == 0);
2097
2098                 if (!oplock_break) {
2099                         /* Dump unexpected reply */
2100                         return NT_STATUS_RETRY;
2101                 }
2102         }
2103
2104         req = conn->pending[i];
2105         state = tevent_req_data(req, struct smbXcli_req_state);
2106
2107         if (!oplock_break /* oplock breaks are not signed */
2108             && !smb_signing_check_pdu(conn->smb1.signing,
2109                                       inhdr, len, state->smb1.seqnum+1)) {
2110                 DEBUG(10, ("cli_check_sign_mac failed\n"));
2111                 return NT_STATUS_ACCESS_DENIED;
2112         }
2113
2114         status = smb1cli_inbuf_parse_chain(inbuf, tmp_mem,
2115                                            &iov, &num_iov);
2116         if (!NT_STATUS_IS_OK(status)) {
2117                 DEBUG(10,("smb1cli_inbuf_parse_chain - %s\n",
2118                           nt_errstr(status)));
2119                 return status;
2120         }
2121
2122         cmd = CVAL(inhdr, HDR_COM);
2123         status = smb1cli_pull_raw_error(inhdr);
2124
2125         if (NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_SESSION_EXPIRED) &&
2126             (state->session != NULL) && state->session->disconnect_expired)
2127         {
2128                 /*
2129                  * this should be a short term hack
2130                  * until the upper layers have implemented
2131                  * re-authentication.
2132                  */
2133                 return status;
2134         }
2135
2136         if (state->smb1.chained_requests == NULL) {
2137                 if (num_iov != 3) {
2138                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
2139                 }
2140
2141                 smbXcli_req_unset_pending(req);
2142
2143                 if (state->smb1.recv_iov == NULL) {
2144                         /*
2145                          * For requests with more than
2146                          * one response, we have to readd the
2147                          * recv_iov array.
2148                          */
2149                         state->smb1.recv_iov = talloc_zero_array(state,
2150                                                                  struct iovec,
2151                                                                  3);
2152                         if (tevent_req_nomem(state->smb1.recv_iov, req)) {
2153                                 return NT_STATUS_OK;
2154                         }
2155                 }
2156
2157                 state->smb1.recv_cmd = cmd;
2158                 state->smb1.recv_status = status;
2159                 state->inbuf = talloc_move(state->smb1.recv_iov, &inbuf);
2160
2161                 state->smb1.recv_iov[0] = iov[0];
2162                 state->smb1.recv_iov[1] = iov[1];
2163                 state->smb1.recv_iov[2] = iov[2];
2164
2165                 if (talloc_array_length(conn->pending) == 0) {
2166                         tevent_req_done(req);
2167                         return NT_STATUS_OK;
2168                 }
2169
2170                 tevent_req_defer_callback(req, state->ev);
2171                 tevent_req_done(req);
2172                 return NT_STATUS_RETRY;
2173         }
2174
2175         chain = talloc_move(tmp_mem, &state->smb1.chained_requests);
2176         num_chained = talloc_array_length(chain);
2177         num_responses = (num_iov - 1)/2;
2178
2179         if (num_responses > num_chained) {
2180                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
2181         }
2182
2183         for (i=0; i<num_chained; i++) {
2184                 size_t iov_idx = 1 + (i*2);
2185                 struct iovec *cur = &iov[iov_idx];
2186                 uint8_t *inbuf_ref;
2187
2188                 req = chain[i];
2189                 state = tevent_req_data(req, struct smbXcli_req_state);
2190
2191                 smbXcli_req_unset_pending(req);
2192
2193                 /*
2194                  * as we finish multiple requests here
2195                  * we need to defer the callbacks as
2196                  * they could destroy our current stack state.
2197                  */
2198                 tevent_req_defer_callback(req, state->ev);
2199
2200                 if (i >= num_responses) {
2201                         tevent_req_nterror(req, NT_STATUS_REQUEST_ABORTED);
2202                         continue;
2203                 }
2204
2205                 if (state->smb1.recv_iov == NULL) {
2206                         /*
2207                          * For requests with more than
2208                          * one response, we have to readd the
2209                          * recv_iov array.
2210                          */
2211                         state->smb1.recv_iov = talloc_zero_array(state,
2212                                                                  struct iovec,
2213                                                                  3);
2214                         if (tevent_req_nomem(state->smb1.recv_iov, req)) {
2215                                 continue;
2216                         }
2217                 }
2218
2219                 state->smb1.recv_cmd = cmd;
2220
2221                 if (i == (num_responses - 1)) {
2222                         /*
2223                          * The last request in the chain gets the status
2224                          */
2225                         state->smb1.recv_status = status;
2226                 } else {
2227                         cmd = CVAL(cur[0].iov_base, 0);
2228                         state->smb1.recv_status = NT_STATUS_OK;
2229                 }
2230
2231                 state->inbuf = inbuf;
2232
2233                 /*
2234                  * Note: here we use talloc_reference() in a way
2235                  *       that does not expose it to the caller.
2236                  */
2237                 inbuf_ref = talloc_reference(state->smb1.recv_iov, inbuf);
2238                 if (tevent_req_nomem(inbuf_ref, req)) {
2239                         continue;
2240                 }
2241
2242                 /* copy the related buffers */
2243                 state->smb1.recv_iov[0] = iov[0];
2244                 state->smb1.recv_iov[1] = cur[0];
2245                 state->smb1.recv_iov[2] = cur[1];
2246
2247                 tevent_req_done(req);
2248         }
2249
2250         return NT_STATUS_RETRY;
2251 }
2252
2253 NTSTATUS smb1cli_req_recv(struct tevent_req *req,
2254                           TALLOC_CTX *mem_ctx,
2255                           struct iovec **piov,
2256                           uint8_t **phdr,
2257                           uint8_t *pwct,
2258                           uint16_t **pvwv,
2259                           uint32_t *pvwv_offset,
2260                           uint32_t *pnum_bytes,
2261                           uint8_t **pbytes,
2262                           uint32_t *pbytes_offset,
2263                           uint8_t **pinbuf,
2264                           const struct smb1cli_req_expected_response *expected,
2265                           size_t num_expected)
2266 {
2267         struct smbXcli_req_state *state =
2268                 tevent_req_data(req,
2269                 struct smbXcli_req_state);
2270         NTSTATUS status = NT_STATUS_OK;
2271         struct iovec *recv_iov = NULL;
2272         uint8_t *hdr = NULL;
2273         uint8_t wct = 0;
2274         uint32_t vwv_offset = 0;
2275         uint16_t *vwv = NULL;
2276         uint32_t num_bytes = 0;
2277         uint32_t bytes_offset = 0;
2278         uint8_t *bytes = NULL;
2279         size_t i;
2280         bool found_status = false;
2281         bool found_size = false;
2282
2283         if (piov != NULL) {
2284                 *piov = NULL;
2285         }
2286         if (phdr != NULL) {
2287                 *phdr = 0;
2288         }
2289         if (pwct != NULL) {
2290                 *pwct = 0;
2291         }
2292         if (pvwv != NULL) {
2293                 *pvwv = NULL;
2294         }
2295         if (pvwv_offset != NULL) {
2296                 *pvwv_offset = 0;
2297         }
2298         if (pnum_bytes != NULL) {
2299                 *pnum_bytes = 0;
2300         }
2301         if (pbytes != NULL) {
2302                 *pbytes = NULL;
2303         }
2304         if (pbytes_offset != NULL) {
2305                 *pbytes_offset = 0;
2306         }
2307         if (pinbuf != NULL) {
2308                 *pinbuf = NULL;
2309         }
2310
2311         if (state->inbuf != NULL) {
2312                 recv_iov = state->smb1.recv_iov;
2313                 state->smb1.recv_iov = NULL;
2314                 if (state->smb1.recv_cmd != SMBreadBraw) {
2315                         hdr = (uint8_t *)recv_iov[0].iov_base;
2316                         wct = recv_iov[1].iov_len/2;
2317                         vwv = (uint16_t *)recv_iov[1].iov_base;
2318                         vwv_offset = PTR_DIFF(vwv, hdr);
2319                         num_bytes = recv_iov[2].iov_len;
2320                         bytes = (uint8_t *)recv_iov[2].iov_base;
2321                         bytes_offset = PTR_DIFF(bytes, hdr);
2322                 }
2323         }
2324
2325         if (tevent_req_is_nterror(req, &status)) {
2326                 for (i=0; i < num_expected; i++) {
2327                         if (NT_STATUS_EQUAL(status, expected[i].status)) {
2328                                 found_status = true;
2329                                 break;
2330                         }
2331                 }
2332
2333                 if (found_status) {
2334                         return NT_STATUS_UNEXPECTED_NETWORK_ERROR;
2335                 }
2336
2337                 return status;
2338         }
2339
2340         if (num_expected == 0) {
2341                 found_status = true;
2342                 found_size = true;
2343         }
2344
2345         status = state->smb1.recv_status;
2346
2347         for (i=0; i < num_expected; i++) {
2348                 if (!NT_STATUS_EQUAL(status, expected[i].status)) {
2349                         continue;
2350                 }
2351
2352                 found_status = true;
2353                 if (expected[i].wct == 0) {
2354                         found_size = true;
2355                         break;
2356                 }
2357
2358                 if (expected[i].wct == wct) {
2359                         found_size = true;
2360                         break;
2361                 }
2362         }
2363
2364         if (!found_status) {
2365                 return status;
2366         }
2367
2368         if (!found_size) {
2369                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
2370         }
2371
2372         if (piov != NULL) {
2373                 *piov = talloc_move(mem_ctx, &recv_iov);
2374         }
2375
2376         if (phdr != NULL) {
2377                 *phdr = hdr;
2378         }
2379         if (pwct != NULL) {
2380                 *pwct = wct;
2381         }
2382         if (pvwv != NULL) {
2383                 *pvwv = vwv;
2384         }
2385         if (pvwv_offset != NULL) {
2386                 *pvwv_offset = vwv_offset;
2387         }
2388         if (pnum_bytes != NULL) {
2389                 *pnum_bytes = num_bytes;
2390         }
2391         if (pbytes != NULL) {
2392                 *pbytes = bytes;
2393         }
2394         if (pbytes_offset != NULL) {
2395                 *pbytes_offset = bytes_offset;
2396         }
2397         if (pinbuf != NULL) {
2398                 *pinbuf = state->inbuf;
2399         }
2400
2401         return status;
2402 }
2403
2404 size_t smb1cli_req_wct_ofs(struct tevent_req **reqs, int num_reqs)
2405 {
2406         size_t wct_ofs;
2407         int i;
2408
2409         wct_ofs = HDR_WCT;
2410
2411         for (i=0; i<num_reqs; i++) {
2412                 struct smbXcli_req_state *state;
2413                 state = tevent_req_data(reqs[i], struct smbXcli_req_state);
2414                 wct_ofs += smbXcli_iov_len(state->smb1.iov+2,
2415                                            state->smb1.iov_count-2);
2416                 wct_ofs = (wct_ofs + 3) & ~3;
2417         }
2418         return wct_ofs;
2419 }
2420
2421 NTSTATUS smb1cli_req_chain_submit(struct tevent_req **reqs, int num_reqs)
2422 {
2423         struct smbXcli_req_state *first_state =
2424                 tevent_req_data(reqs[0],
2425                 struct smbXcli_req_state);
2426         struct smbXcli_req_state *state;
2427         size_t wct_offset;
2428         size_t chain_padding = 0;
2429         int i, iovlen;
2430         struct iovec *iov = NULL;
2431         struct iovec *this_iov;
2432         NTSTATUS status;
2433         ssize_t nbt_len;
2434
2435         if (num_reqs == 1) {
2436                 return smb1cli_req_writev_submit(reqs[0], first_state,
2437                                                  first_state->smb1.iov,
2438                                                  first_state->smb1.iov_count);
2439         }
2440
2441         iovlen = 0;
2442         for (i=0; i<num_reqs; i++) {
2443                 if (!tevent_req_is_in_progress(reqs[i])) {
2444                         return NT_STATUS_INTERNAL_ERROR;
2445                 }
2446
2447                 state = tevent_req_data(reqs[i], struct smbXcli_req_state);
2448
2449                 if (state->smb1.iov_count < 4) {
2450                         return NT_STATUS_INVALID_PARAMETER_MIX;
2451                 }
2452
2453                 if (i == 0) {
2454                         /*
2455                          * The NBT and SMB header
2456                          */
2457                         iovlen += 2;
2458                 } else {
2459                         /*
2460                          * Chain padding
2461                          */
2462                         iovlen += 1;
2463                 }
2464
2465                 /*
2466                  * words and bytes
2467                  */
2468                 iovlen += state->smb1.iov_count - 2;
2469         }
2470
2471         iov = talloc_zero_array(first_state, struct iovec, iovlen);
2472         if (iov == NULL) {
2473                 return NT_STATUS_NO_MEMORY;
2474         }
2475
2476         first_state->smb1.chained_requests = (struct tevent_req **)talloc_memdup(
2477                 first_state, reqs, sizeof(*reqs) * num_reqs);
2478         if (first_state->smb1.chained_requests == NULL) {
2479                 TALLOC_FREE(iov);
2480                 return NT_STATUS_NO_MEMORY;
2481         }
2482
2483         wct_offset = HDR_WCT;
2484         this_iov = iov;
2485
2486         for (i=0; i<num_reqs; i++) {
2487                 size_t next_padding = 0;
2488                 uint16_t *vwv;
2489
2490                 state = tevent_req_data(reqs[i], struct smbXcli_req_state);
2491
2492                 if (i < num_reqs-1) {
2493                         if (!smb1cli_is_andx_req(CVAL(state->smb1.hdr, HDR_COM))
2494                             || CVAL(state->smb1.hdr, HDR_WCT) < 2) {
2495                                 TALLOC_FREE(iov);
2496                                 TALLOC_FREE(first_state->smb1.chained_requests);
2497                                 return NT_STATUS_INVALID_PARAMETER_MIX;
2498                         }
2499                 }
2500
2501                 wct_offset += smbXcli_iov_len(state->smb1.iov+2,
2502                                               state->smb1.iov_count-2) + 1;
2503                 if ((wct_offset % 4) != 0) {
2504                         next_padding = 4 - (wct_offset % 4);
2505                 }
2506                 wct_offset += next_padding;
2507                 vwv = state->smb1.vwv;
2508
2509                 if (i < num_reqs-1) {
2510                         struct smbXcli_req_state *next_state =
2511                                 tevent_req_data(reqs[i+1],
2512                                 struct smbXcli_req_state);
2513                         SCVAL(vwv+0, 0, CVAL(next_state->smb1.hdr, HDR_COM));
2514                         SCVAL(vwv+0, 1, 0);
2515                         SSVAL(vwv+1, 0, wct_offset);
2516                 } else if (smb1cli_is_andx_req(CVAL(state->smb1.hdr, HDR_COM))) {
2517                         /* properly end the chain */
2518                         SCVAL(vwv+0, 0, 0xff);
2519                         SCVAL(vwv+0, 1, 0xff);
2520                         SSVAL(vwv+1, 0, 0);
2521                 }
2522
2523                 if (i == 0) {
2524                         /*
2525                          * The NBT and SMB header
2526                          */
2527                         this_iov[0] = state->smb1.iov[0];
2528                         this_iov[1] = state->smb1.iov[1];
2529                         this_iov += 2;
2530                 } else {
2531                         /*
2532                          * This one is a bit subtle. We have to add
2533                          * chain_padding bytes between the requests, and we
2534                          * have to also include the wct field of the
2535                          * subsequent requests. We use the subsequent header
2536                          * for the padding, it contains the wct field in its
2537                          * last byte.
2538                          */
2539                         this_iov[0].iov_len = chain_padding+1;
2540                         this_iov[0].iov_base = (void *)&state->smb1.hdr[
2541                                 sizeof(state->smb1.hdr) - this_iov[0].iov_len];
2542                         memset(this_iov[0].iov_base, 0, this_iov[0].iov_len-1);
2543                         this_iov += 1;
2544                 }
2545
2546                 /*
2547                  * copy the words and bytes
2548                  */
2549                 memcpy(this_iov, state->smb1.iov+2,
2550                        sizeof(struct iovec) * (state->smb1.iov_count-2));
2551                 this_iov += state->smb1.iov_count - 2;
2552                 chain_padding = next_padding;
2553         }
2554
2555         nbt_len = iov_buflen(&iov[1], iovlen-1);
2556         if ((nbt_len == -1) || (nbt_len > first_state->conn->smb1.max_xmit)) {
2557                 TALLOC_FREE(iov);
2558                 TALLOC_FREE(first_state->smb1.chained_requests);
2559                 return NT_STATUS_INVALID_PARAMETER_MIX;
2560         }
2561
2562         status = smb1cli_req_writev_submit(reqs[0], first_state, iov, iovlen);
2563         if (!NT_STATUS_IS_OK(status)) {
2564                 TALLOC_FREE(iov);
2565                 TALLOC_FREE(first_state->smb1.chained_requests);
2566                 return status;
2567         }
2568
2569         return NT_STATUS_OK;
2570 }
2571
2572 bool smbXcli_conn_has_async_calls(struct smbXcli_conn *conn)
2573 {
2574         return ((tevent_queue_length(conn->outgoing) != 0)
2575                 || (talloc_array_length(conn->pending) != 0));
2576 }
2577
2578 bool smbXcli_conn_dfs_supported(struct smbXcli_conn *conn)
2579 {
2580         if (conn->protocol >= PROTOCOL_SMB2_02) {
2581                 return (smb2cli_conn_server_capabilities(conn) & SMB2_CAP_DFS);
2582         }
2583
2584         return (smb1cli_conn_capabilities(conn) & CAP_DFS);
2585 }
2586
2587 bool smb2cli_conn_req_possible(struct smbXcli_conn *conn, uint32_t *max_dyn_len)
2588 {
2589         uint16_t credits = 1;
2590
2591         if (conn->smb2.cur_credits == 0) {
2592                 if (max_dyn_len != NULL) {
2593                         *max_dyn_len = 0;
2594                 }
2595                 return false;
2596         }
2597
2598         if (conn->smb2.server.capabilities & SMB2_CAP_LARGE_MTU) {
2599                 credits = conn->smb2.cur_credits;
2600         }
2601
2602         if (max_dyn_len != NULL) {
2603                 *max_dyn_len = credits * 65536;
2604         }
2605
2606         return true;
2607 }
2608
2609 uint32_t smb2cli_conn_server_capabilities(struct smbXcli_conn *conn)
2610 {
2611         return conn->smb2.server.capabilities;
2612 }
2613
2614 uint16_t smb2cli_conn_server_security_mode(struct smbXcli_conn *conn)
2615 {
2616         return conn->smb2.server.security_mode;
2617 }
2618
2619 uint32_t smb2cli_conn_max_trans_size(struct smbXcli_conn *conn)
2620 {
2621         return conn->smb2.server.max_trans_size;
2622 }
2623
2624 uint32_t smb2cli_conn_max_read_size(struct smbXcli_conn *conn)
2625 {
2626         return conn->smb2.server.max_read_size;
2627 }
2628
2629 uint32_t smb2cli_conn_max_write_size(struct smbXcli_conn *conn)
2630 {
2631         return conn->smb2.server.max_write_size;
2632 }
2633
2634 void smb2cli_conn_set_max_credits(struct smbXcli_conn *conn,
2635                                   uint16_t max_credits)
2636 {
2637         conn->smb2.max_credits = max_credits;
2638 }
2639
2640 uint8_t smb2cli_conn_get_io_priority(struct smbXcli_conn *conn)
2641 {
2642         if (conn->protocol < PROTOCOL_SMB3_11) {
2643                 return 0;
2644         }
2645
2646         return conn->smb2.io_priority;
2647 }
2648
2649 void smb2cli_conn_set_io_priority(struct smbXcli_conn *conn,
2650                                   uint8_t io_priority)
2651 {
2652         conn->smb2.io_priority = io_priority;
2653 }
2654
2655 uint32_t smb2cli_conn_cc_chunk_len(struct smbXcli_conn *conn)
2656 {
2657         return conn->smb2.cc_chunk_len;
2658 }
2659
2660 void smb2cli_conn_set_cc_chunk_len(struct smbXcli_conn *conn,
2661                                     uint32_t chunk_len)
2662 {
2663         conn->smb2.cc_chunk_len = chunk_len;
2664 }
2665
2666 uint32_t smb2cli_conn_cc_max_chunks(struct smbXcli_conn *conn)
2667 {
2668         return conn->smb2.cc_max_chunks;
2669 }
2670
2671 void smb2cli_conn_set_cc_max_chunks(struct smbXcli_conn *conn,
2672                                     uint32_t max_chunks)
2673 {
2674         conn->smb2.cc_max_chunks = max_chunks;
2675 }
2676
2677 static void smb2cli_req_cancel_done(struct tevent_req *subreq);
2678
2679 static bool smb2cli_req_cancel(struct tevent_req *req)
2680 {
2681         struct smbXcli_req_state *state =
2682                 tevent_req_data(req,
2683                 struct smbXcli_req_state);
2684         struct smbXcli_tcon *tcon = state->tcon;
2685         struct smbXcli_session *session = state->session;
2686         uint8_t *fixed = state->smb2.pad;
2687         uint16_t fixed_len = 4;
2688         struct tevent_req *subreq;
2689         struct smbXcli_req_state *substate;
2690         NTSTATUS status;
2691
2692         SSVAL(fixed, 0, 0x04);
2693         SSVAL(fixed, 2, 0);
2694
2695         subreq = smb2cli_req_create(state, state->ev,
2696                                     state->conn,
2697                                     SMB2_OP_CANCEL,
2698                                     0, 0, /* flags */
2699                                     0, /* timeout */
2700                                     tcon, session,
2701                                     fixed, fixed_len,
2702                                     NULL, 0, 0);
2703         if (subreq == NULL) {
2704                 return false;
2705         }
2706         substate = tevent_req_data(subreq, struct smbXcli_req_state);
2707
2708         SIVAL(substate->smb2.hdr, SMB2_HDR_FLAGS, state->smb2.cancel_flags);
2709         SBVAL(substate->smb2.hdr, SMB2_HDR_MESSAGE_ID, state->smb2.cancel_mid);
2710         SBVAL(substate->smb2.hdr, SMB2_HDR_ASYNC_ID, state->smb2.cancel_aid);
2711
2712         status = smb2cli_req_compound_submit(&subreq, 1);
2713         if (!NT_STATUS_IS_OK(status)) {
2714                 TALLOC_FREE(subreq);
2715                 return false;
2716         }
2717
2718         tevent_req_set_callback(subreq, smb2cli_req_cancel_done, NULL);
2719
2720         return true;
2721 }
2722
2723 static void smb2cli_req_cancel_done(struct tevent_req *subreq)
2724 {
2725         /* we do not care about the result */
2726         TALLOC_FREE(subreq);
2727 }
2728
2729 struct tevent_req *smb2cli_req_create(TALLOC_CTX *mem_ctx,
2730                                       struct tevent_context *ev,
2731                                       struct smbXcli_conn *conn,
2732                                       uint16_t cmd,
2733                                       uint32_t additional_flags,
2734                                       uint32_t clear_flags,
2735                                       uint32_t timeout_msec,
2736                                       struct smbXcli_tcon *tcon,
2737                                       struct smbXcli_session *session,
2738                                       const uint8_t *fixed,
2739                                       uint16_t fixed_len,
2740                                       const uint8_t *dyn,
2741                                       uint32_t dyn_len,
2742                                       uint32_t max_dyn_len)
2743 {
2744         struct tevent_req *req;
2745         struct smbXcli_req_state *state;
2746         uint32_t flags = 0;
2747         uint32_t tid = 0;
2748         uint64_t uid = 0;
2749         bool use_channel_sequence = false;
2750         uint16_t channel_sequence = 0;
2751         bool use_replay_flag = false;
2752
2753         req = tevent_req_create(mem_ctx, &state,
2754                                 struct smbXcli_req_state);
2755         if (req == NULL) {
2756                 return NULL;
2757         }
2758
2759         state->ev = ev;
2760         state->conn = conn;
2761         state->session = session;
2762         state->tcon = tcon;
2763
2764         if (conn->smb2.server.capabilities & SMB2_CAP_PERSISTENT_HANDLES) {
2765                 use_channel_sequence = true;
2766         } else if (conn->smb2.server.capabilities & SMB2_CAP_MULTI_CHANNEL) {
2767                 use_channel_sequence = true;
2768         }
2769
2770         if (smbXcli_conn_protocol(conn) >= PROTOCOL_SMB3_00) {
2771                 use_replay_flag = true;
2772         }
2773
2774         if (smbXcli_conn_protocol(conn) >= PROTOCOL_SMB3_11) {
2775                 flags |= SMB2_PRIORITY_VALUE_TO_MASK(conn->smb2.io_priority);
2776         }
2777
2778         if (session) {
2779                 uid = session->smb2->session_id;
2780
2781                 if (use_channel_sequence) {
2782                         channel_sequence = session->smb2->channel_sequence;
2783                 }
2784
2785                 if (use_replay_flag && session->smb2->replay_active) {
2786                         additional_flags |= SMB2_HDR_FLAG_REPLAY_OPERATION;
2787                 }
2788
2789                 state->smb2.should_sign = session->smb2->should_sign;
2790                 state->smb2.should_encrypt = session->smb2->should_encrypt;
2791
2792                 if (cmd == SMB2_OP_SESSSETUP &&
2793                     session->smb2_channel.signing_key.length == 0 &&
2794                     session->smb2->signing_key.length != 0)
2795                 {
2796                         /*
2797                          * a session bind needs to be signed
2798                          */
2799                         state->smb2.should_sign = true;
2800                 }
2801
2802                 if (cmd == SMB2_OP_SESSSETUP &&
2803                     session->smb2_channel.signing_key.length == 0) {
2804                         state->smb2.should_encrypt = false;
2805                 }
2806
2807                 if (additional_flags & SMB2_HDR_FLAG_SIGNED) {
2808                         if (session->smb2_channel.signing_key.length == 0) {
2809                                 tevent_req_nterror(req, NT_STATUS_NO_USER_SESSION_KEY);
2810                                 return req;
2811                         }
2812
2813                         additional_flags &= ~SMB2_HDR_FLAG_SIGNED;
2814                         state->smb2.should_sign = true;
2815                 }
2816         }
2817
2818         if (tcon) {
2819                 tid = tcon->smb2.tcon_id;
2820
2821                 if (tcon->smb2.should_sign) {
2822                         state->smb2.should_sign = true;
2823                 }
2824                 if (tcon->smb2.should_encrypt) {
2825                         state->smb2.should_encrypt = true;
2826                 }
2827         }
2828
2829         if (state->smb2.should_encrypt) {
2830                 state->smb2.should_sign = false;
2831         }
2832
2833         state->smb2.recv_iov = talloc_zero_array(state, struct iovec, 3);
2834         if (state->smb2.recv_iov == NULL) {
2835                 TALLOC_FREE(req);
2836                 return NULL;
2837         }
2838
2839         flags |= additional_flags;
2840         flags &= ~clear_flags;
2841
2842         state->smb2.fixed = fixed;
2843         state->smb2.fixed_len = fixed_len;
2844         state->smb2.dyn = dyn;
2845         state->smb2.dyn_len = dyn_len;
2846         state->smb2.max_dyn_len = max_dyn_len;
2847
2848         if (state->smb2.should_encrypt) {
2849                 SIVAL(state->smb2.transform, SMB2_TF_PROTOCOL_ID, SMB2_TF_MAGIC);
2850                 SBVAL(state->smb2.transform, SMB2_TF_SESSION_ID, uid);
2851         }
2852
2853         SIVAL(state->smb2.hdr, SMB2_HDR_PROTOCOL_ID,    SMB2_MAGIC);
2854         SSVAL(state->smb2.hdr, SMB2_HDR_LENGTH,         SMB2_HDR_BODY);
2855         SSVAL(state->smb2.hdr, SMB2_HDR_OPCODE,         cmd);
2856         SSVAL(state->smb2.hdr, SMB2_HDR_CHANNEL_SEQUENCE, channel_sequence);
2857         SIVAL(state->smb2.hdr, SMB2_HDR_FLAGS,          flags);
2858         SIVAL(state->smb2.hdr, SMB2_HDR_PID,            0); /* reserved */
2859         SIVAL(state->smb2.hdr, SMB2_HDR_TID,            tid);
2860         SBVAL(state->smb2.hdr, SMB2_HDR_SESSION_ID,     uid);
2861
2862         switch (cmd) {
2863         case SMB2_OP_CANCEL:
2864                 state->one_way = true;
2865                 break;
2866         case SMB2_OP_BREAK:
2867                 /*
2868                  * If this is a dummy request, it will have
2869                  * UINT64_MAX as message id.
2870                  * If we send on break acknowledgement,
2871                  * this gets overwritten later.
2872                  */
2873                 SBVAL(state->smb2.hdr, SMB2_HDR_MESSAGE_ID, UINT64_MAX);
2874                 break;
2875         }
2876
2877         if (timeout_msec > 0) {
2878                 struct timeval endtime;
2879
2880                 endtime = timeval_current_ofs_msec(timeout_msec);
2881                 if (!tevent_req_set_endtime(req, ev, endtime)) {
2882                         return req;
2883                 }
2884         }
2885
2886         return req;
2887 }
2888
2889 void smb2cli_req_set_notify_async(struct tevent_req *req)
2890 {
2891         struct smbXcli_req_state *state =
2892                 tevent_req_data(req,
2893                 struct smbXcli_req_state);
2894
2895         state->smb2.notify_async = true;
2896 }
2897
2898 static void smb2cli_req_writev_done(struct tevent_req *subreq);
2899 static NTSTATUS smb2cli_conn_dispatch_incoming(struct smbXcli_conn *conn,
2900                                                TALLOC_CTX *tmp_mem,
2901                                                uint8_t *inbuf);
2902
2903 NTSTATUS smb2cli_req_compound_submit(struct tevent_req **reqs,
2904                                      int num_reqs)
2905 {
2906         struct smbXcli_req_state *state;
2907         struct tevent_req *subreq;
2908         struct iovec *iov;
2909         int i, num_iov, nbt_len;
2910         int tf_iov = -1;
2911         const DATA_BLOB *encryption_key = NULL;
2912         uint64_t encryption_session_id = 0;
2913         uint64_t nonce_high = UINT64_MAX;
2914         uint64_t nonce_low = UINT64_MAX;
2915
2916         /*
2917          * 1 for the nbt length, optional TRANSFORM
2918          * per request: HDR, fixed, dyn, padding
2919          * -1 because the last one does not need padding
2920          */
2921
2922         iov = talloc_array(reqs[0], struct iovec, 1 + 1 + 4*num_reqs - 1);
2923         if (iov == NULL) {
2924                 return NT_STATUS_NO_MEMORY;
2925         }
2926
2927         num_iov = 1;
2928         nbt_len = 0;
2929
2930         /*
2931          * the session of the first request that requires encryption
2932          * specifies the encryption key.
2933          */
2934         for (i=0; i<num_reqs; i++) {
2935                 if (!tevent_req_is_in_progress(reqs[i])) {
2936                         return NT_STATUS_INTERNAL_ERROR;
2937                 }
2938
2939                 state = tevent_req_data(reqs[i], struct smbXcli_req_state);
2940
2941                 if (!smbXcli_conn_is_connected(state->conn)) {
2942                         return NT_STATUS_CONNECTION_DISCONNECTED;
2943                 }
2944
2945                 if ((state->conn->protocol != PROTOCOL_NONE) &&
2946                     (state->conn->protocol < PROTOCOL_SMB2_02)) {
2947                         return NT_STATUS_REVISION_MISMATCH;
2948                 }
2949
2950                 if (state->session == NULL) {
2951                         continue;
2952                 }
2953
2954                 if (!state->smb2.should_encrypt) {
2955                         continue;
2956                 }
2957
2958                 encryption_key = &state->session->smb2->encryption_key;
2959                 if (encryption_key->length == 0) {
2960                         return NT_STATUS_INVALID_PARAMETER_MIX;
2961                 }
2962
2963                 encryption_session_id = state->session->smb2->session_id;
2964
2965                 state->session->smb2->nonce_low += 1;
2966                 if (state->session->smb2->nonce_low == 0) {
2967                         state->session->smb2->nonce_high += 1;
2968                         state->session->smb2->nonce_low += 1;
2969                 }
2970
2971                 /*
2972                  * CCM and GCM algorithms must never have their
2973                  * nonce wrap, or the security of the whole
2974                  * communication and the keys is destroyed.
2975                  * We must drop the connection once we have
2976                  * transfered too much data.
2977                  *
2978                  * NOTE: We assume nonces greater than 8 bytes.
2979                  */
2980                 if (state->session->smb2->nonce_high >=
2981                     state->session->smb2->nonce_high_max)
2982                 {
2983                         return NT_STATUS_ENCRYPTION_FAILED;
2984                 }
2985
2986                 nonce_high = state->session->smb2->nonce_high_random;
2987                 nonce_high += state->session->smb2->nonce_high;
2988                 nonce_low = state->session->smb2->nonce_low;
2989
2990                 tf_iov = num_iov;
2991                 iov[num_iov].iov_base = state->smb2.transform;
2992                 iov[num_iov].iov_len  = sizeof(state->smb2.transform);
2993                 num_iov += 1;
2994
2995                 SBVAL(state->smb2.transform, SMB2_TF_PROTOCOL_ID, SMB2_TF_MAGIC);
2996                 SBVAL(state->smb2.transform, SMB2_TF_NONCE,
2997                       nonce_low);
2998                 SBVAL(state->smb2.transform, SMB2_TF_NONCE+8,
2999                       nonce_high);
3000                 SBVAL(state->smb2.transform, SMB2_TF_SESSION_ID,
3001                       encryption_session_id);
3002
3003                 nbt_len += SMB2_TF_HDR_SIZE;
3004                 break;
3005         }
3006
3007         for (i=0; i<num_reqs; i++) {
3008                 int hdr_iov;
3009                 size_t reqlen;
3010                 bool ret;
3011                 uint16_t opcode;
3012                 uint64_t avail;
3013                 uint16_t charge;
3014                 uint16_t credits;
3015                 uint64_t mid;
3016                 const DATA_BLOB *signing_key = NULL;
3017
3018                 if (!tevent_req_is_in_progress(reqs[i])) {
3019                         return NT_STATUS_INTERNAL_ERROR;
3020                 }
3021
3022                 state = tevent_req_data(reqs[i], struct smbXcli_req_state);
3023
3024                 if (!smbXcli_conn_is_connected(state->conn)) {
3025                         return NT_STATUS_CONNECTION_DISCONNECTED;
3026                 }
3027
3028                 if ((state->conn->protocol != PROTOCOL_NONE) &&
3029                     (state->conn->protocol < PROTOCOL_SMB2_02)) {
3030                         return NT_STATUS_REVISION_MISMATCH;
3031                 }
3032
3033                 opcode = SVAL(state->smb2.hdr, SMB2_HDR_OPCODE);
3034                 if (opcode == SMB2_OP_CANCEL) {
3035                         goto skip_credits;
3036                 }
3037
3038                 avail = UINT64_MAX - state->conn->smb2.mid;
3039                 if (avail < 1) {
3040                         return NT_STATUS_CONNECTION_ABORTED;
3041                 }
3042
3043                 if (state->conn->smb2.server.capabilities & SMB2_CAP_LARGE_MTU) {
3044                         uint32_t max_dyn_len = 1;
3045
3046                         max_dyn_len = MAX(max_dyn_len, state->smb2.dyn_len);
3047                         max_dyn_len = MAX(max_dyn_len, state->smb2.max_dyn_len);
3048
3049                         charge = (max_dyn_len - 1)/ 65536 + 1;
3050                 } else {
3051                         charge = 1;
3052                 }
3053
3054                 charge = MAX(state->smb2.credit_charge, charge);
3055
3056                 avail = MIN(avail, state->conn->smb2.cur_credits);
3057                 if (avail < charge) {
3058                         return NT_STATUS_INTERNAL_ERROR;
3059                 }
3060
3061                 credits = 0;
3062                 if (state->conn->smb2.max_credits > state->conn->smb2.cur_credits) {
3063                         credits = state->conn->smb2.max_credits -
3064                                   state->conn->smb2.cur_credits;
3065                 }
3066                 if (state->conn->smb2.max_credits >= state->conn->smb2.cur_credits) {
3067                         credits += 1;
3068                 }
3069
3070                 mid = state->conn->smb2.mid;
3071                 state->conn->smb2.mid += charge;
3072                 state->conn->smb2.cur_credits -= charge;
3073
3074                 if (state->conn->smb2.server.capabilities & SMB2_CAP_LARGE_MTU) {
3075                         SSVAL(state->smb2.hdr, SMB2_HDR_CREDIT_CHARGE, charge);
3076                 }
3077                 SSVAL(state->smb2.hdr, SMB2_HDR_CREDIT, credits);
3078                 SBVAL(state->smb2.hdr, SMB2_HDR_MESSAGE_ID, mid);
3079
3080                 state->smb2.cancel_flags = 0;
3081                 state->smb2.cancel_mid = mid;
3082                 state->smb2.cancel_aid = 0;
3083
3084 skip_credits:
3085                 if (state->session && encryption_key == NULL) {
3086                         /*
3087                          * We prefer the channel signing key if it is
3088                          * already there.
3089                          */
3090                         if (state->smb2.should_sign) {
3091                                 signing_key = &state->session->smb2_channel.signing_key;
3092                         }
3093
3094                         /*
3095                          * If it is a channel binding, we already have the main
3096                          * signing key and try that one.
3097                          */
3098                         if (signing_key && signing_key->length == 0) {
3099                                 signing_key = &state->session->smb2->signing_key;
3100                         }
3101
3102                         /*
3103                          * If we do not have any session key yet, we skip the
3104                          * signing of SMB2_OP_SESSSETUP requests.
3105                          */
3106                         if (signing_key && signing_key->length == 0) {
3107                                 signing_key = NULL;
3108                         }
3109                 }
3110
3111                 hdr_iov = num_iov;
3112                 iov[num_iov].iov_base = state->smb2.hdr;
3113                 iov[num_iov].iov_len  = sizeof(state->smb2.hdr);
3114                 num_iov += 1;
3115
3116                 iov[num_iov].iov_base = discard_const(state->smb2.fixed);
3117                 iov[num_iov].iov_len  = state->smb2.fixed_len;
3118                 num_iov += 1;
3119
3120                 if (state->smb2.dyn != NULL) {
3121                         iov[num_iov].iov_base = discard_const(state->smb2.dyn);
3122                         iov[num_iov].iov_len  = state->smb2.dyn_len;
3123                         num_iov += 1;
3124                 }
3125
3126                 reqlen  = sizeof(state->smb2.hdr);
3127                 reqlen += state->smb2.fixed_len;
3128                 reqlen += state->smb2.dyn_len;
3129
3130                 if (i < num_reqs-1) {
3131                         if ((reqlen % 8) > 0) {
3132                                 uint8_t pad = 8 - (reqlen % 8);
3133                                 iov[num_iov].iov_base = state->smb2.pad;
3134                                 iov[num_iov].iov_len = pad;
3135                                 num_iov += 1;
3136                                 reqlen += pad;
3137                         }
3138                         SIVAL(state->smb2.hdr, SMB2_HDR_NEXT_COMMAND, reqlen);
3139                 }
3140
3141                 state->smb2.encryption_session_id = encryption_session_id;
3142
3143                 if (signing_key != NULL) {
3144                         NTSTATUS status;
3145
3146                         status = smb2_signing_sign_pdu(*signing_key,
3147                                                        state->session->conn->protocol,
3148                                                        &iov[hdr_iov], num_iov - hdr_iov);
3149                         if (!NT_STATUS_IS_OK(status)) {
3150                                 return status;
3151                         }
3152                 }
3153
3154                 nbt_len += reqlen;
3155
3156                 ret = smbXcli_req_set_pending(reqs[i]);
3157                 if (!ret) {
3158                         return NT_STATUS_NO_MEMORY;
3159                 }
3160         }
3161
3162         state = tevent_req_data(reqs[0], struct smbXcli_req_state);
3163         _smb_setlen_tcp(state->length_hdr, nbt_len);
3164         iov[0].iov_base = state->length_hdr;
3165         iov[0].iov_len  = sizeof(state->length_hdr);
3166
3167         if (encryption_key != NULL) {
3168                 NTSTATUS status;
3169                 size_t buflen = nbt_len - SMB2_TF_HDR_SIZE;
3170                 uint8_t *buf;
3171                 int vi;
3172
3173                 buf = talloc_array(iov, uint8_t, buflen);
3174                 if (buf == NULL) {
3175                         return NT_STATUS_NO_MEMORY;
3176                 }
3177
3178                 /*
3179                  * We copy the buffers before encrypting them,
3180                  * this is at least currently needed for the
3181                  * to keep state->smb2.hdr.
3182                  *
3183                  * Also the callers may expect there buffers
3184                  * to be const.
3185                  */
3186                 for (vi = tf_iov + 1; vi < num_iov; vi++) {
3187                         struct iovec *v = &iov[vi];
3188                         const uint8_t *o = (const uint8_t *)v->iov_base;
3189
3190                         memcpy(buf, o, v->iov_len);
3191                         v->iov_base = (void *)buf;
3192                         buf += v->iov_len;
3193                 }
3194
3195                 status = smb2_signing_encrypt_pdu(*encryption_key,
3196                                         state->conn->smb2.server.cipher,
3197                                         &iov[tf_iov], num_iov - tf_iov);
3198                 if (!NT_STATUS_IS_OK(status)) {
3199                         return status;
3200                 }
3201         }
3202
3203         if (state->conn->dispatch_incoming == NULL) {
3204                 state->conn->dispatch_incoming = smb2cli_conn_dispatch_incoming;
3205         }
3206
3207         subreq = writev_send(state, state->ev, state->conn->outgoing,
3208                              state->conn->sock_fd, false, iov, num_iov);
3209         if (subreq == NULL) {
3210                 return NT_STATUS_NO_MEMORY;
3211         }
3212         tevent_req_set_callback(subreq, smb2cli_req_writev_done, reqs[0]);
3213         return NT_STATUS_OK;
3214 }
3215
3216 void smb2cli_req_set_credit_charge(struct tevent_req *req, uint16_t charge)
3217 {
3218         struct smbXcli_req_state *state =
3219                 tevent_req_data(req,
3220                 struct smbXcli_req_state);
3221
3222         state->smb2.credit_charge = charge;
3223 }
3224
3225 struct tevent_req *smb2cli_req_send(TALLOC_CTX *mem_ctx,
3226                                     struct tevent_context *ev,
3227                                     struct smbXcli_conn *conn,
3228                                     uint16_t cmd,
3229                                     uint32_t additional_flags,
3230                                     uint32_t clear_flags,
3231                                     uint32_t timeout_msec,
3232                                     struct smbXcli_tcon *tcon,
3233                                     struct smbXcli_session *session,
3234                                     const uint8_t *fixed,
3235                                     uint16_t fixed_len,
3236                                     const uint8_t *dyn,
3237                                     uint32_t dyn_len,
3238                                     uint32_t max_dyn_len)
3239 {
3240         struct tevent_req *req;
3241         NTSTATUS status;
3242
3243         req = smb2cli_req_create(mem_ctx, ev, conn, cmd,
3244                                  additional_flags, clear_flags,
3245                                  timeout_msec,
3246                                  tcon, session,
3247                                  fixed, fixed_len,
3248                                  dyn, dyn_len,
3249                                  max_dyn_len);
3250         if (req == NULL) {
3251                 return NULL;
3252         }
3253         if (!tevent_req_is_in_progress(req)) {
3254                 return tevent_req_post(req, ev);
3255         }
3256         status = smb2cli_req_compound_submit(&req, 1);
3257         if (tevent_req_nterror(req, status)) {
3258                 return tevent_req_post(req, ev);
3259         }
3260         return req;
3261 }
3262
3263 static void smb2cli_req_writev_done(struct tevent_req *subreq)
3264 {
3265         struct tevent_req *req =
3266                 tevent_req_callback_data(subreq,
3267                 struct tevent_req);
3268         struct smbXcli_req_state *state =
3269                 tevent_req_data(req,
3270                 struct smbXcli_req_state);
3271         ssize_t nwritten;
3272         int err;
3273
3274         nwritten = writev_recv(subreq, &err);
3275         TALLOC_FREE(subreq);
3276         if (nwritten == -1) {
3277                 /* here, we need to notify all pending requests */
3278                 NTSTATUS status = map_nt_error_from_unix_common(err);
3279                 smbXcli_conn_disconnect(state->conn, status);
3280                 return;
3281         }
3282 }
3283
3284 static NTSTATUS smb2cli_inbuf_parse_compound(struct smbXcli_conn *conn,
3285                                              uint8_t *buf,
3286                                              size_t buflen,
3287                                              TALLOC_CTX *mem_ctx,
3288                                              struct iovec **piov, int *pnum_iov)
3289 {
3290         struct iovec *iov;
3291         int num_iov = 0;
3292         size_t taken = 0;
3293         uint8_t *first_hdr = buf;
3294         size_t verified_buflen = 0;
3295         uint8_t *tf = NULL;
3296         size_t tf_len = 0;
3297
3298         iov = talloc_array(mem_ctx, struct iovec, num_iov);
3299         if (iov == NULL) {
3300                 return NT_STATUS_NO_MEMORY;
3301         }
3302
3303         while (taken < buflen) {
3304                 size_t len = buflen - taken;
3305                 uint8_t *hdr = first_hdr + taken;
3306                 struct iovec *cur;
3307                 size_t full_size;
3308                 size_t next_command_ofs;
3309                 uint16_t body_size;
3310                 struct iovec *iov_tmp;
3311
3312                 if (verified_buflen > taken) {
3313                         len = verified_buflen - taken;
3314                 } else {
3315                         tf = NULL;
3316                         tf_len = 0;
3317                 }
3318
3319                 if (len < 4) {
3320                         DEBUG(10, ("%d bytes left, expected at least %d\n",
3321                                    (int)len, 4));
3322                         goto inval;
3323                 }
3324                 if (IVAL(hdr, 0) == SMB2_TF_MAGIC) {
3325                         struct smbXcli_session *s;
3326                         uint64_t uid;
3327                         struct iovec tf_iov[2];
3328                         size_t enc_len;
3329                         NTSTATUS status;
3330
3331                         if (len < SMB2_TF_HDR_SIZE) {
3332                                 DEBUG(10, ("%d bytes left, expected at least %d\n",
3333                                            (int)len, SMB2_TF_HDR_SIZE));
3334                                 goto inval;
3335                         }
3336                         tf = hdr;
3337                         tf_len = SMB2_TF_HDR_SIZE;
3338                         taken += tf_len;
3339
3340                         hdr = first_hdr + taken;
3341                         enc_len = IVAL(tf, SMB2_TF_MSG_SIZE);
3342                         uid = BVAL(tf, SMB2_TF_SESSION_ID);
3343
3344                         if (len < SMB2_TF_HDR_SIZE + enc_len) {
3345                                 DEBUG(10, ("%d bytes left, expected at least %d\n",
3346                                            (int)len,
3347                                            (int)(SMB2_TF_HDR_SIZE + enc_len)));
3348                                 goto inval;
3349                         }
3350
3351                         s = conn->sessions;
3352                         for (; s; s = s->next) {
3353                                 if (s->smb2->session_id != uid) {
3354                                         continue;
3355                                 }
3356                                 break;
3357                         }
3358
3359                         if (s == NULL) {
3360                                 DEBUG(10, ("unknown session_id %llu\n",
3361                                            (unsigned long long)uid));
3362                                 goto inval;
3363                         }
3364
3365                         tf_iov[0].iov_base = (void *)tf;
3366                         tf_iov[0].iov_len = tf_len;
3367                         tf_iov[1].iov_base = (void *)hdr;
3368                         tf_iov[1].iov_len = enc_len;
3369
3370                         status = smb2_signing_decrypt_pdu(s->smb2->decryption_key,
3371                                                           conn->smb2.server.cipher,
3372                                                           tf_iov, 2);
3373                         if (!NT_STATUS_IS_OK(status)) {
3374                                 TALLOC_FREE(iov);
3375                                 return status;
3376                         }
3377
3378                         verified_buflen = taken + enc_len;
3379                         len = enc_len;
3380                 }
3381
3382                 /*
3383                  * We need the header plus the body length field
3384                  */
3385
3386                 if (len < SMB2_HDR_BODY + 2) {
3387                         DEBUG(10, ("%d bytes left, expected at least %d\n",
3388                                    (int)len, SMB2_HDR_BODY));
3389                         goto inval;
3390                 }
3391                 if (IVAL(hdr, 0) != SMB2_MAGIC) {
3392                         DEBUG(10, ("Got non-SMB2 PDU: %x\n",
3393                                    IVAL(hdr, 0)));
3394                         goto inval;
3395                 }
3396                 if (SVAL(hdr, 4) != SMB2_HDR_BODY) {
3397                         DEBUG(10, ("Got HDR len %d, expected %d\n",
3398                                    SVAL(hdr, 4), SMB2_HDR_BODY));
3399                         goto inval;
3400                 }
3401
3402                 full_size = len;
3403                 next_command_ofs = IVAL(hdr, SMB2_HDR_NEXT_COMMAND);
3404                 body_size = SVAL(hdr, SMB2_HDR_BODY);
3405
3406                 if (next_command_ofs != 0) {
3407                         if (next_command_ofs < (SMB2_HDR_BODY + 2)) {
3408                                 goto inval;
3409                         }
3410                         if (next_command_ofs > full_size) {
3411                                 goto inval;
3412                         }
3413                         full_size = next_command_ofs;
3414                 }
3415                 if (body_size < 2) {
3416                         goto inval;
3417                 }
3418                 body_size &= 0xfffe;
3419
3420                 if (body_size > (full_size - SMB2_HDR_BODY)) {
3421                         goto inval;
3422                 }
3423
3424                 iov_tmp = talloc_realloc(mem_ctx, iov, struct iovec,
3425                                          num_iov + 4);
3426                 if (iov_tmp == NULL) {
3427                         TALLOC_FREE(iov);
3428                         return NT_STATUS_NO_MEMORY;
3429                 }
3430                 iov = iov_tmp;
3431                 cur = &iov[num_iov];
3432                 num_iov += 4;
3433
3434                 cur[0].iov_base = tf;
3435                 cur[0].iov_len  = tf_len;
3436                 cur[1].iov_base = hdr;
3437                 cur[1].iov_len  = SMB2_HDR_BODY;
3438                 cur[2].iov_base = hdr + SMB2_HDR_BODY;
3439                 cur[2].iov_len  = body_size;
3440                 cur[3].iov_base = hdr + SMB2_HDR_BODY + body_size;
3441                 cur[3].iov_len  = full_size - (SMB2_HDR_BODY + body_size);
3442
3443                 taken += full_size;
3444         }
3445
3446         *piov = iov;
3447         *pnum_iov = num_iov;
3448         return NT_STATUS_OK;
3449
3450 inval:
3451         TALLOC_FREE(iov);
3452         return NT_STATUS_INVALID_NETWORK_RESPONSE;
3453 }
3454
3455 static struct tevent_req *smb2cli_conn_find_pending(struct smbXcli_conn *conn,
3456                                                     uint64_t mid)
3457 {
3458         size_t num_pending = talloc_array_length(conn->pending);
3459         size_t i;
3460
3461         for (i=0; i<num_pending; i++) {
3462                 struct tevent_req *req = conn->pending[i];
3463                 struct smbXcli_req_state *state =
3464                         tevent_req_data(req,
3465                         struct smbXcli_req_state);
3466
3467                 if (mid == BVAL(state->smb2.hdr, SMB2_HDR_MESSAGE_ID)) {
3468                         return req;
3469                 }
3470         }
3471         return NULL;
3472 }
3473
3474 static NTSTATUS smb2cli_conn_dispatch_incoming(struct smbXcli_conn *conn,
3475                                                TALLOC_CTX *tmp_mem,
3476                                                uint8_t *inbuf)
3477 {
3478         struct tevent_req *req;
3479         struct smbXcli_req_state *state = NULL;
3480         struct iovec *iov;
3481         int i, num_iov;
3482         NTSTATUS status;
3483         bool defer = true;
3484         struct smbXcli_session *last_session = NULL;
3485         size_t inbuf_len = smb_len_tcp(inbuf);
3486
3487         status = smb2cli_inbuf_parse_compound(conn,
3488                                               inbuf + NBT_HDR_SIZE,
3489                                               inbuf_len,
3490                                               tmp_mem,
3491                                               &iov, &num_iov);
3492         if (!NT_STATUS_IS_OK(status)) {
3493                 return status;
3494         }
3495
3496         for (i=0; i<num_iov; i+=4) {
3497                 uint8_t *inbuf_ref = NULL;
3498                 struct iovec *cur = &iov[i];
3499                 uint8_t *inhdr = (uint8_t *)cur[1].iov_base;
3500                 uint16_t opcode = SVAL(inhdr, SMB2_HDR_OPCODE);
3501                 uint32_t flags = IVAL(inhdr, SMB2_HDR_FLAGS);
3502                 uint64_t mid = BVAL(inhdr, SMB2_HDR_MESSAGE_ID);
3503                 uint16_t req_opcode;
3504                 uint32_t req_flags;
3505                 uint16_t credits = SVAL(inhdr, SMB2_HDR_CREDIT);
3506                 uint32_t new_credits;
3507                 struct smbXcli_session *session = NULL;
3508                 const DATA_BLOB *signing_key = NULL;
3509                 bool was_encrypted = false;
3510
3511                 new_credits = conn->smb2.cur_credits;
3512                 new_credits += credits;
3513                 if (new_credits > UINT16_MAX) {
3514                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
3515                 }
3516                 conn->smb2.cur_credits += credits;
3517
3518                 req = smb2cli_conn_find_pending(conn, mid);
3519                 if (req == NULL) {
3520                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
3521                 }
3522                 state = tevent_req_data(req, struct smbXcli_req_state);
3523
3524                 req_opcode = SVAL(state->smb2.hdr, SMB2_HDR_OPCODE);
3525                 if (opcode != req_opcode) {
3526                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
3527                 }
3528                 req_flags = SVAL(state->smb2.hdr, SMB2_HDR_FLAGS);
3529
3530                 if (!(flags & SMB2_HDR_FLAG_REDIRECT)) {
3531                         return NT_STATUS_INVALID_NETWORK_RESPONSE;
3532                 }
3533
3534                 status = NT_STATUS(IVAL(inhdr, SMB2_HDR_STATUS));
3535                 if ((flags & SMB2_HDR_FLAG_ASYNC) &&
3536                     NT_STATUS_EQUAL(status, STATUS_PENDING)) {
3537                         uint64_t async_id = BVAL(inhdr, SMB2_HDR_ASYNC_ID);
3538
3539                         if (state->smb2.got_async) {
3540                                 /* We only expect one STATUS_PENDING response */
3541                                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
3542                         }
3543                         state->smb2.got_async = true;
3544
3545                         /*
3546                          * async interim responses are not signed,
3547                          * even if the SMB2_HDR_FLAG_SIGNED flag
3548                          * is set.
3549                          */
3550                         state->smb2.cancel_flags = SMB2_HDR_FLAG_ASYNC;
3551                         state->smb2.cancel_mid = 0;
3552                         state->smb2.cancel_aid = async_id;
3553
3554                         if (state->smb2.notify_async) {
3555                                 tevent_req_defer_callback(req, state->ev);
3556                                 tevent_req_notify_callback(req);
3557                         }
3558                         continue;
3559                 }
3560
3561                 session = state->session;
3562                 if (req_flags & SMB2_HDR_FLAG_CHAINED) {
3563                         session = last_session;
3564                 }
3565                 last_session = session;
3566
3567                 if (state->smb2.should_sign) {
3568                         if (!(flags & SMB2_HDR_FLAG_SIGNED)) {
3569                                 return NT_STATUS_ACCESS_DENIED;
3570                         }
3571                 }
3572
3573                 if (flags & SMB2_HDR_FLAG_SIGNED) {
3574                         uint64_t uid = BVAL(inhdr, SMB2_HDR_SESSION_ID);
3575
3576                         if (session == NULL) {
3577                                 struct smbXcli_session *s;
3578
3579                                 s = state->conn->sessions;
3580                                 for (; s; s = s->next) {
3581                                         if (s->smb2->session_id != uid) {
3582                                                 continue;
3583                                         }
3584
3585                                         session = s;
3586                                         break;
3587                                 }
3588                         }
3589
3590                         if (session == NULL) {
3591                                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
3592                         }
3593
3594                         last_session = session;
3595                         signing_key = &session->smb2_channel.signing_key;
3596                 }
3597
3598                 if (opcode == SMB2_OP_SESSSETUP) {
3599                         /*
3600                          * We prefer the channel signing key, if it is
3601                          * already there.
3602                          *
3603                          * If we do not have a channel signing key yet,
3604                          * we try the main signing key, if it is not
3605                          * the final response.
3606                          */
3607                         if (signing_key && signing_key->length == 0 &&
3608                             !NT_STATUS_IS_OK(status)) {
3609                                 signing_key = &session->smb2->signing_key;
3610                         }
3611
3612                         if (signing_key && signing_key->length == 0) {
3613                                 /*
3614                                  * If we do not have a session key to
3615                                  * verify the signature, we defer the
3616                                  * signing check to the caller.
3617                                  *
3618                                  * The caller gets NT_STATUS_OK, it
3619                                  * has to call
3620                                  * smb2cli_session_set_session_key()
3621                                  * or
3622                                  * smb2cli_session_set_channel_key()
3623                                  * which will check the signature
3624                                  * with the channel signing key.
3625                                  */
3626                                 signing_key = NULL;
3627                         }
3628                 }
3629
3630                 if (cur[0].iov_len == SMB2_TF_HDR_SIZE) {
3631                         const uint8_t *tf = (const uint8_t *)cur[0].iov_base;
3632                         uint64_t uid = BVAL(tf, SMB2_TF_SESSION_ID);
3633
3634                         /*
3635                          * If the response was encrypted in a SMB2_TRANSFORM
3636                          * pdu, which belongs to the correct session,
3637                          * we do not need to do signing checks
3638                          *
3639                          * It could be the session the response belongs to
3640                          * or the session that was used to encrypt the
3641                          * SMB2_TRANSFORM request.
3642                          */
3643                         if ((session && session->smb2->session_id == uid) ||
3644                             (state->smb2.encryption_session_id == uid)) {
3645                                 signing_key = NULL;
3646                                 was_encrypted = true;
3647                         }
3648                 }
3649
3650                 if (NT_STATUS_EQUAL(status, NT_STATUS_USER_SESSION_DELETED)) {
3651                         /*
3652                          * if the server returns NT_STATUS_USER_SESSION_DELETED
3653                          * the response is not signed and we should
3654                          * propagate the NT_STATUS_USER_SESSION_DELETED
3655                          * status to the caller.
3656                          */
3657                         state->smb2.signing_skipped = true;
3658                         signing_key = NULL;
3659                 }
3660
3661                 if (NT_STATUS_EQUAL(status, NT_STATUS_INVALID_PARAMETER)) {
3662                         /*
3663                          * if the server returns
3664                          * NT_STATUS_INVALID_PARAMETER
3665                          * the response might not be encrypted.
3666                          */
3667                         if (state->smb2.should_encrypt && !was_encrypted) {
3668                                 state->smb2.signing_skipped = true;
3669                                 signing_key = NULL;
3670                         }
3671                 }
3672
3673                 if (state->smb2.should_encrypt && !was_encrypted) {
3674                         if (!state->smb2.signing_skipped) {
3675                                 return NT_STATUS_ACCESS_DENIED;
3676                         }
3677                 }
3678
3679                 if (NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED) ||
3680                     NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) ||
3681                     NT_STATUS_EQUAL(status, NT_STATUS_INVALID_PARAMETER)) {
3682                         /*
3683                          * if the server returns
3684                          * NT_STATUS_NETWORK_NAME_DELETED
3685                          * NT_STATUS_FILE_CLOSED
3686                          * NT_STATUS_INVALID_PARAMETER
3687                          * the response might not be signed
3688                          * as this happens before the signing checks.
3689                          *
3690                          * If server echos the signature (or all zeros)
3691                          * we should report the status from the server
3692                          * to the caller.
3693                          */
3694                         if (signing_key) {
3695                                 int cmp;
3696
3697                                 cmp = memcmp(inhdr+SMB2_HDR_SIGNATURE,
3698                                              state->smb2.hdr+SMB2_HDR_SIGNATURE,
3699                                              16);
3700                                 if (cmp == 0) {
3701                                         state->smb2.signing_skipped = true;
3702                                         signing_key = NULL;
3703                                 }
3704                         }
3705                         if (signing_key) {
3706                                 int cmp;
3707                                 static const uint8_t zeros[16];
3708
3709                                 cmp = memcmp(inhdr+SMB2_HDR_SIGNATURE,
3710                                              zeros,
3711                                              16);
3712                                 if (cmp == 0) {
3713                                         state->smb2.signing_skipped = true;
3714                                         signing_key = NULL;
3715                                 }
3716                         }
3717                 }
3718
3719                 if (signing_key) {
3720                         status = smb2_signing_check_pdu(*signing_key,
3721                                                         state->conn->protocol,
3722                                                         &cur[1], 3);
3723                         if (!NT_STATUS_IS_OK(status)) {
3724                                 /*
3725                                  * If the signing check fails, we disconnect
3726                                  * the connection.
3727                                  */
3728                                 return status;
3729                         }
3730                 }
3731
3732                 if (NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_SESSION_EXPIRED) &&
3733                     (session != NULL) && session->disconnect_expired)
3734                 {
3735                         /*
3736                          * this should be a short term hack
3737                          * until the upper layers have implemented
3738                          * re-authentication.
3739                          */
3740                         return status;
3741                 }
3742
3743                 smbXcli_req_unset_pending(req);
3744
3745                 /*
3746                  * There might be more than one response
3747                  * we need to defer the notifications
3748                  */
3749                 if ((num_iov == 5) && (talloc_array_length(conn->pending) == 0)) {
3750                         defer = false;
3751                 }
3752
3753                 if (defer) {
3754                         tevent_req_defer_callback(req, state->ev);
3755                 }
3756
3757                 /*
3758                  * Note: here we use talloc_reference() in a way
3759                  *       that does not expose it to the caller.
3760                  */
3761                 inbuf_ref = talloc_reference(state->smb2.recv_iov, inbuf);
3762                 if (tevent_req_nomem(inbuf_ref, req)) {
3763                         continue;
3764                 }
3765
3766                 /* copy the related buffers */
3767                 state->smb2.recv_iov[0] = cur[1];
3768                 state->smb2.recv_iov[1] = cur[2];
3769                 state->smb2.recv_iov[2] = cur[3];
3770
3771                 tevent_req_done(req);
3772         }
3773
3774         if (defer) {
3775                 return NT_STATUS_RETRY;
3776         }
3777
3778         return NT_STATUS_OK;
3779 }
3780
3781 NTSTATUS smb2cli_req_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
3782                           struct iovec **piov,
3783                           const struct smb2cli_req_expected_response *expected,
3784                           size_t num_expected)
3785 {
3786         struct smbXcli_req_state *state =
3787                 tevent_req_data(req,
3788                 struct smbXcli_req_state);
3789         NTSTATUS status;
3790         size_t body_size;
3791         bool found_status = false;
3792         bool found_size = false;
3793         size_t i;
3794
3795         if (piov != NULL) {
3796                 *piov = NULL;
3797         }
3798
3799         if (tevent_req_is_in_progress(req) && state->smb2.got_async) {
3800                 return STATUS_PENDING;
3801         }
3802
3803         if (tevent_req_is_nterror(req, &status)) {
3804                 for (i=0; i < num_expected; i++) {
3805                         if (NT_STATUS_EQUAL(status, expected[i].status)) {
3806                                 found_status = true;
3807                                 break;
3808                         }
3809                 }
3810
3811                 if (found_status) {
3812                         return NT_STATUS_UNEXPECTED_NETWORK_ERROR;
3813                 }
3814
3815                 return status;
3816         }
3817
3818         if (num_expected == 0) {
3819                 found_status = true;
3820                 found_size = true;
3821         }
3822
3823         status = NT_STATUS(IVAL(state->smb2.recv_iov[0].iov_base, SMB2_HDR_STATUS));
3824         body_size = SVAL(state->smb2.recv_iov[1].iov_base, 0);
3825
3826         for (i=0; i < num_expected; i++) {
3827                 if (!NT_STATUS_EQUAL(status, expected[i].status)) {
3828                         continue;
3829                 }
3830
3831                 found_status = true;
3832                 if (expected[i].body_size == 0) {
3833                         found_size = true;
3834                         break;
3835                 }
3836
3837                 if (expected[i].body_size == body_size) {
3838                         found_size = true;
3839                         break;
3840                 }
3841         }
3842
3843         if (!found_status) {
3844                 return status;
3845         }
3846
3847         if (state->smb2.signing_skipped) {
3848                 if (num_expected > 0) {
3849                         return NT_STATUS_ACCESS_DENIED;
3850                 }
3851                 if (!NT_STATUS_IS_ERR(status)) {
3852                         return NT_STATUS_ACCESS_DENIED;
3853                 }
3854         }
3855
3856         if (!found_size) {
3857                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
3858         }
3859
3860         if (piov != NULL) {
3861                 *piov = talloc_move(mem_ctx, &state->smb2.recv_iov);
3862         }
3863
3864         return status;
3865 }
3866
3867 NTSTATUS smb2cli_req_get_sent_iov(struct tevent_req *req,
3868                                   struct iovec *sent_iov)
3869 {
3870         struct smbXcli_req_state *state =
3871                 tevent_req_data(req,
3872                 struct smbXcli_req_state);
3873
3874         if (tevent_req_is_in_progress(req)) {
3875                 return STATUS_PENDING;
3876         }
3877
3878         sent_iov[0].iov_base = state->smb2.hdr;
3879         sent_iov[0].iov_len  = sizeof(state->smb2.hdr);
3880
3881         sent_iov[1].iov_base = discard_const(state->smb2.fixed);
3882         sent_iov[1].iov_len  = state->smb2.fixed_len;
3883
3884         if (state->smb2.dyn != NULL) {
3885                 sent_iov[2].iov_base = discard_const(state->smb2.dyn);
3886                 sent_iov[2].iov_len  = state->smb2.dyn_len;
3887         } else {
3888                 sent_iov[2].iov_base = NULL;
3889                 sent_iov[2].iov_len  = 0;
3890         }
3891
3892         return NT_STATUS_OK;
3893 }
3894
3895 static const struct {
3896         enum protocol_types proto;
3897         const char *smb1_name;
3898 } smb1cli_prots[] = {
3899         {PROTOCOL_CORE,         "PC NETWORK PROGRAM 1.0"},
3900         {PROTOCOL_COREPLUS,     "MICROSOFT NETWORKS 1.03"},
3901         {PROTOCOL_LANMAN1,      "MICROSOFT NETWORKS 3.0"},
3902         {PROTOCOL_LANMAN1,      "LANMAN1.0"},
3903         {PROTOCOL_LANMAN2,      "LM1.2X002"},
3904         {PROTOCOL_LANMAN2,      "DOS LANMAN2.1"},
3905         {PROTOCOL_LANMAN2,      "LANMAN2.1"},
3906         {PROTOCOL_LANMAN2,      "Samba"},
3907         {PROTOCOL_NT1,          "NT LANMAN 1.0"},
3908         {PROTOCOL_NT1,          "NT LM 0.12"},
3909         {PROTOCOL_SMB2_02,      "SMB 2.002"},
3910         {PROTOCOL_SMB2_10,      "SMB 2.???"},
3911 };
3912
3913 static const struct {
3914         enum protocol_types proto;
3915         uint16_t smb2_dialect;
3916 } smb2cli_prots[] = {
3917         {PROTOCOL_SMB2_02,      SMB2_DIALECT_REVISION_202},
3918         {PROTOCOL_SMB2_10,      SMB2_DIALECT_REVISION_210},
3919         {PROTOCOL_SMB2_22,      SMB2_DIALECT_REVISION_222},
3920         {PROTOCOL_SMB2_24,      SMB2_DIALECT_REVISION_224},
3921         {PROTOCOL_SMB3_00,      SMB3_DIALECT_REVISION_300},
3922         {PROTOCOL_SMB3_02,      SMB3_DIALECT_REVISION_302},
3923         {PROTOCOL_SMB3_10,      SMB3_DIALECT_REVISION_310},
3924         {PROTOCOL_SMB3_11,      SMB3_DIALECT_REVISION_311},
3925 };
3926
3927 struct smbXcli_negprot_state {
3928         struct smbXcli_conn *conn;
3929         struct tevent_context *ev;
3930         uint32_t timeout_msec;
3931
3932         struct {
3933                 uint8_t fixed[36];
3934         } smb2;
3935 };
3936
3937 static void smbXcli_negprot_invalid_done(struct tevent_req *subreq);
3938 static struct tevent_req *smbXcli_negprot_smb1_subreq(struct smbXcli_negprot_state *state);
3939 static void smbXcli_negprot_smb1_done(struct tevent_req *subreq);
3940 static struct tevent_req *smbXcli_negprot_smb2_subreq(struct smbXcli_negprot_state *state);
3941 static void smbXcli_negprot_smb2_done(struct tevent_req *subreq);
3942 static NTSTATUS smbXcli_negprot_dispatch_incoming(struct smbXcli_conn *conn,
3943                                                   TALLOC_CTX *frame,
3944                                                   uint8_t *inbuf);
3945
3946 struct tevent_req *smbXcli_negprot_send(TALLOC_CTX *mem_ctx,
3947                                         struct tevent_context *ev,
3948                                         struct smbXcli_conn *conn,
3949                                         uint32_t timeout_msec,
3950                                         enum protocol_types min_protocol,
3951                                         enum protocol_types max_protocol)
3952 {
3953         struct tevent_req *req, *subreq;
3954         struct smbXcli_negprot_state *state;
3955
3956         req = tevent_req_create(mem_ctx, &state,
3957                                 struct smbXcli_negprot_state);
3958         if (req == NULL) {
3959                 return NULL;
3960         }
3961         state->conn = conn;
3962         state->ev = ev;
3963         state->timeout_msec = timeout_msec;
3964
3965         if (min_protocol == PROTOCOL_NONE) {
3966                 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER_MIX);
3967                 return tevent_req_post(req, ev);
3968         }
3969
3970         if (max_protocol == PROTOCOL_NONE) {
3971                 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER_MIX);
3972                 return tevent_req_post(req, ev);
3973         }
3974
3975         if (min_protocol > max_protocol) {
3976                 tevent_req_nterror(req, NT_STATUS_INVALID_PARAMETER_MIX);
3977                 return tevent_req_post(req, ev);
3978         }
3979
3980         conn->min_protocol = min_protocol;
3981         conn->max_protocol = max_protocol;
3982         conn->protocol = PROTOCOL_NONE;
3983
3984         if ((min_protocol < PROTOCOL_SMB2_02) &&
3985             (max_protocol < PROTOCOL_SMB2_02)) {
3986                 /*
3987                  * SMB1 only...
3988                  */
3989                 conn->dispatch_incoming = smb1cli_conn_dispatch_incoming;
3990
3991                 subreq = smbXcli_negprot_smb1_subreq(state);
3992                 if (tevent_req_nomem(subreq, req)) {
3993                         return tevent_req_post(req, ev);
3994                 }
3995                 tevent_req_set_callback(subreq, smbXcli_negprot_smb1_done, req);
3996                 return req;
3997         }
3998
3999         if ((min_protocol >= PROTOCOL_SMB2_02) &&
4000             (max_protocol >= PROTOCOL_SMB2_02)) {
4001                 /*
4002                  * SMB2 only...
4003                  */
4004                 conn->dispatch_incoming = smb2cli_conn_dispatch_incoming;
4005
4006                 /*
4007                  * As we're starting with an SMB2 negprot, emulate Windows
4008                  * and ask for 31 credits in the initial SMB2 negprot.
4009                  * If we don't and leave requested credits at
4010                  * zero, MacOSX servers return zero credits on
4011                  * the negprot reply and we fail to connect.
4012                  */
4013                 smb2cli_conn_set_max_credits(conn,
4014                         WINDOWS_CLIENT_PURE_SMB2_NEGPROT_INITIAL_CREDIT_ASK);
4015
4016                 subreq = smbXcli_negprot_smb2_subreq(state);
4017                 if (tevent_req_nomem(subreq, req)) {
4018                         return tevent_req_post(req, ev);
4019                 }
4020                 tevent_req_set_callback(subreq, smbXcli_negprot_smb2_done, req);
4021                 return req;
4022         }
4023
4024         /*
4025          * We send an SMB1 negprot with the SMB2 dialects
4026          * and expect a SMB1 or a SMB2 response.
4027          *
4028          * smbXcli_negprot_dispatch_incoming() will fix the
4029          * callback to match protocol of the response.
4030          */
4031         conn->dispatch_incoming = smbXcli_negprot_dispatch_incoming;
4032
4033         subreq = smbXcli_negprot_smb1_subreq(state);
4034         if (tevent_req_nomem(subreq, req)) {
4035                 return tevent_req_post(req, ev);
4036         }
4037         tevent_req_set_callback(subreq, smbXcli_negprot_invalid_done, req);
4038         return req;
4039 }
4040
4041 static void smbXcli_negprot_invalid_done(struct tevent_req *subreq)
4042 {
4043         struct tevent_req *req =
4044                 tevent_req_callback_data(subreq,
4045                 struct tevent_req);
4046         NTSTATUS status;
4047
4048         /*
4049          * we just want the low level error
4050          */
4051         status = tevent_req_simple_recv_ntstatus(subreq);
4052         TALLOC_FREE(subreq);
4053         if (tevent_req_nterror(req, status)) {
4054                 return;
4055         }
4056
4057         /* this should never happen */
4058         tevent_req_nterror(req, NT_STATUS_INTERNAL_ERROR);
4059 }
4060
4061 static struct tevent_req *smbXcli_negprot_smb1_subreq(struct smbXcli_negprot_state *state)
4062 {
4063         size_t i;
4064         DATA_BLOB bytes = data_blob_null;
4065         uint8_t flags;
4066         uint16_t flags2;
4067
4068         /* setup the protocol strings */
4069         for (i=0; i < ARRAY_SIZE(smb1cli_prots); i++) {
4070                 uint8_t c = 2;
4071                 bool ok;
4072
4073                 if (smb1cli_prots[i].proto < state->conn->min_protocol) {
4074                         continue;
4075                 }
4076
4077                 if (smb1cli_prots[i].proto > state->conn->max_protocol) {
4078                         continue;
4079                 }
4080
4081                 ok = data_blob_append(state, &bytes, &c, sizeof(c));
4082                 if (!ok) {
4083                         return NULL;
4084                 }
4085
4086                 /*
4087                  * We now it is already ascii and
4088                  * we want NULL termination.
4089                  */
4090                 ok = data_blob_append(state, &bytes,
4091                                       smb1cli_prots[i].smb1_name,
4092                                       strlen(smb1cli_prots[i].smb1_name)+1);
4093                 if (!ok) {
4094                         return NULL;
4095                 }
4096         }
4097
4098         smb1cli_req_flags(state->conn->max_protocol,
4099                           state->conn->smb1.client.capabilities,
4100                           SMBnegprot,
4101                           0, 0, &flags,
4102                           0, 0, &flags2);
4103
4104         return smb1cli_req_send(state, state->ev, state->conn,
4105                                 SMBnegprot,
4106                                 flags, ~flags,
4107                                 flags2, ~flags2,
4108                                 state->timeout_msec,
4109                                 0xFFFE, 0, NULL, /* pid, tid, session */
4110                                 0, NULL, /* wct, vwv */
4111                                 bytes.length, bytes.data);
4112 }
4113
4114 static void smbXcli_negprot_smb1_done(struct tevent_req *subreq)
4115 {
4116         struct tevent_req *req =
4117                 tevent_req_callback_data(subreq,
4118                 struct tevent_req);
4119         struct smbXcli_negprot_state *state =
4120                 tevent_req_data(req,
4121                 struct smbXcli_negprot_state);
4122         struct smbXcli_conn *conn = state->conn;
4123         struct iovec *recv_iov = NULL;
4124         uint8_t *inhdr;
4125         uint8_t wct;
4126         uint16_t *vwv;
4127         uint32_t num_bytes;
4128         uint8_t *bytes;
4129         NTSTATUS status;
4130         uint16_t protnum;
4131         size_t i;
4132         size_t num_prots = 0;
4133         uint8_t flags;
4134         uint32_t client_capabilities = conn->smb1.client.capabilities;
4135         uint32_t both_capabilities;
4136         uint32_t server_capabilities = 0;
4137         uint32_t capabilities;
4138         uint32_t client_max_xmit = conn->smb1.client.max_xmit;
4139         uint32_t server_max_xmit = 0;
4140         uint32_t max_xmit;
4141         uint32_t server_max_mux = 0;
4142         uint16_t server_security_mode = 0;
4143         uint32_t server_session_key = 0;
4144         bool server_readbraw = false;
4145         bool server_writebraw = false;
4146         bool server_lockread = false;
4147         bool server_writeunlock = false;
4148         struct GUID server_guid = GUID_zero();
4149         DATA_BLOB server_gss_blob = data_blob_null;
4150         uint8_t server_challenge[8];
4151         char *server_workgroup = NULL;
4152         char *server_name = NULL;
4153         int server_time_zone = 0;
4154         NTTIME server_system_time = 0;
4155         static const struct smb1cli_req_expected_response expected[] = {
4156         {
4157                 .status = NT_STATUS_OK,
4158                 .wct = 0x11, /* NT1 */
4159         },
4160         {
4161                 .status = NT_STATUS_OK,
4162                 .wct = 0x0D, /* LM */
4163         },
4164         {
4165                 .status = NT_STATUS_OK,
4166                 .wct = 0x01, /* CORE */
4167         }
4168         };
4169
4170         ZERO_STRUCT(server_challenge);
4171
4172         status = smb1cli_req_recv(subreq, state,
4173                                   &recv_iov,
4174                                   &inhdr,
4175                                   &wct,
4176                                   &vwv,
4177                                   NULL, /* pvwv_offset */
4178                                   &num_bytes,
4179                                   &bytes,
4180                                   NULL, /* pbytes_offset */
4181                                   NULL, /* pinbuf */
4182                                   expected, ARRAY_SIZE(expected));
4183         TALLOC_FREE(subreq);
4184         if (tevent_req_nterror(req, status)) {
4185                 return;
4186         }
4187
4188         flags = CVAL(inhdr, HDR_FLG);
4189
4190         protnum = SVAL(vwv, 0);
4191
4192         for (i=0; i < ARRAY_SIZE(smb1cli_prots); i++) {
4193                 if (smb1cli_prots[i].proto < state->conn->min_protocol) {
4194                         continue;
4195                 }
4196
4197                 if (smb1cli_prots[i].proto > state->conn->max_protocol) {
4198                         continue;
4199                 }
4200
4201                 if (protnum != num_prots) {
4202                         num_prots++;
4203                         continue;
4204                 }
4205
4206                 conn->protocol = smb1cli_prots[i].proto;
4207                 break;
4208         }
4209
4210         if (conn->protocol == PROTOCOL_NONE) {
4211                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4212                 return;
4213         }
4214
4215         if ((conn->protocol < PROTOCOL_NT1) && conn->mandatory_signing) {
4216                 DEBUG(0,("smbXcli_negprot: SMB signing is mandatory "
4217                          "and the selected protocol level doesn't support it.\n"));
4218                 tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
4219                 return;
4220         }
4221
4222         if (flags & FLAG_SUPPORT_LOCKREAD) {
4223                 server_lockread = true;
4224                 server_writeunlock = true;
4225         }
4226
4227         if (conn->protocol >= PROTOCOL_NT1) {
4228                 const char *client_signing = NULL;
4229                 bool server_mandatory = false;
4230                 bool server_allowed = false;
4231                 const char *server_signing = NULL;
4232                 bool ok;
4233                 uint8_t key_len;
4234
4235                 if (wct != 0x11) {
4236                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4237                         return;
4238                 }
4239
4240                 /* NT protocol */
4241                 server_security_mode = CVAL(vwv + 1, 0);
4242                 server_max_mux = SVAL(vwv + 1, 1);
4243                 server_max_xmit = IVAL(vwv + 3, 1);
4244                 server_session_key = IVAL(vwv + 7, 1);
4245                 server_time_zone = SVALS(vwv + 15, 1);
4246                 server_time_zone *= 60;
4247                 /* this time arrives in real GMT */
4248                 server_system_time = BVAL(vwv + 11, 1);
4249                 server_capabilities = IVAL(vwv + 9, 1);
4250
4251                 key_len = CVAL(vwv + 16, 1);
4252
4253                 if (server_capabilities & CAP_RAW_MODE) {
4254                         server_readbraw = true;
4255                         server_writebraw = true;
4256                 }
4257                 if (server_capabilities & CAP_LOCK_AND_READ) {
4258                         server_lockread = true;
4259                 }
4260
4261                 if (server_capabilities & CAP_EXTENDED_SECURITY) {
4262                         DATA_BLOB blob1, blob2;
4263
4264                         if (num_bytes < 16) {
4265                                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4266                                 return;
4267                         }
4268
4269                         blob1 = data_blob_const(bytes, 16);
4270                         status = GUID_from_data_blob(&blob1, &server_guid);
4271                         if (tevent_req_nterror(req, status)) {
4272                                 return;
4273                         }
4274
4275                         blob1 = data_blob_const(bytes+16, num_bytes-16);
4276                         blob2 = data_blob_dup_talloc(state, blob1);
4277                         if (blob1.length > 0 &&
4278                             tevent_req_nomem(blob2.data, req)) {
4279                                 return;
4280                         }
4281                         server_gss_blob = blob2;
4282                 } else {
4283                         DATA_BLOB blob1, blob2;
4284
4285                         if (num_bytes < key_len) {
4286                                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4287                                 return;
4288                         }
4289
4290                         if (key_len != 0 && key_len != 8) {
4291                                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4292                                 return;
4293                         }
4294
4295                         if (key_len == 8) {
4296                                 memcpy(server_challenge, bytes, 8);
4297                         }
4298
4299                         blob1 = data_blob_const(bytes+key_len, num_bytes-key_len);
4300                         blob2 = data_blob_const(bytes+key_len, num_bytes-key_len);
4301                         if (blob1.length > 0) {
4302                                 size_t len;
4303
4304                                 len = utf16_len_n(blob1.data,
4305                                                   blob1.length);
4306                                 blob1.length = len;
4307
4308                                 ok = convert_string_talloc(state,
4309                                                            CH_UTF16LE,
4310                                                            CH_UNIX,
4311                                                            blob1.data,
4312                                                            blob1.length,
4313                                                            &server_workgroup,
4314                                                            &len);
4315                                 if (!ok) {
4316                                         status = map_nt_error_from_unix_common(errno);
4317                                         tevent_req_nterror(req, status);
4318                                         return;
4319                                 }
4320                         }
4321
4322                         blob2.data += blob1.length;
4323                         blob2.length -= blob1.length;
4324                         if (blob2.length > 0) {
4325                                 size_t len;
4326
4327                                 len = utf16_len_n(blob1.data,
4328                                                   blob1.length);
4329                                 blob1.length = len;
4330
4331                                 ok = convert_string_talloc(state,
4332                                                            CH_UTF16LE,
4333                                                            CH_UNIX,
4334                                                            blob2.data,
4335                                                            blob2.length,
4336                                                            &server_name,
4337                                                            &len);
4338                                 if (!ok) {
4339                                         status = map_nt_error_from_unix_common(errno);
4340                                         tevent_req_nterror(req, status);
4341                                         return;
4342                                 }
4343                         }
4344                 }
4345
4346                 client_signing = "disabled";
4347                 if (conn->allow_signing) {
4348                         client_signing = "allowed";
4349                 }
4350                 if (conn->mandatory_signing) {
4351                         client_signing = "required";
4352                 }
4353
4354                 server_signing = "not supported";
4355                 if (server_security_mode & NEGOTIATE_SECURITY_SIGNATURES_ENABLED) {
4356                         server_signing = "supported";
4357                         server_allowed = true;
4358                 } else if (conn->mandatory_signing) {
4359                         /*
4360                          * We have mandatory signing as client
4361                          * lets assume the server will look at our
4362                          * FLAGS2_SMB_SECURITY_SIGNATURES_REQUIRED
4363                          * flag in the session setup
4364                          */
4365                         server_signing = "not announced";
4366                         server_allowed = true;
4367                 }
4368                 if (server_security_mode & NEGOTIATE_SECURITY_SIGNATURES_REQUIRED) {
4369                         server_signing = "required";
4370                         server_mandatory = true;
4371                 }
4372
4373                 ok = smb_signing_set_negotiated(conn->smb1.signing,
4374                                                 server_allowed,
4375                                                 server_mandatory);
4376                 if (!ok) {
4377                         DEBUG(1,("cli_negprot: SMB signing is required, "
4378                                  "but client[%s] and server[%s] mismatch\n",
4379                                  client_signing, server_signing));
4380                         tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
4381                         return;
4382                 }
4383
4384         } else if (conn->protocol >= PROTOCOL_LANMAN1) {
4385                 DATA_BLOB blob1;
4386                 uint8_t key_len;
4387                 time_t t;
4388
4389                 if (wct != 0x0D) {
4390                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4391                         return;
4392                 }
4393
4394                 server_security_mode = SVAL(vwv + 1, 0);
4395                 server_max_xmit = SVAL(vwv + 2, 0);
4396                 server_max_mux = SVAL(vwv + 3, 0);
4397                 server_readbraw = ((SVAL(vwv + 5, 0) & 0x1) != 0);
4398                 server_writebraw = ((SVAL(vwv + 5, 0) & 0x2) != 0);
4399                 server_session_key = IVAL(vwv + 6, 0);
4400                 server_time_zone = SVALS(vwv + 10, 0);
4401                 server_time_zone *= 60;
4402                 /* this time is converted to GMT by make_unix_date */
4403                 t = pull_dos_date((const uint8_t *)(vwv + 8), server_time_zone);
4404                 unix_to_nt_time(&server_system_time, t);
4405                 key_len = SVAL(vwv + 11, 0);
4406
4407                 if (num_bytes < key_len) {
4408                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4409                         return;
4410                 }
4411
4412                 if (key_len != 0 && key_len != 8) {
4413                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4414                         return;
4415                 }
4416
4417                 if (key_len == 8) {
4418                         memcpy(server_challenge, bytes, 8);
4419                 }
4420
4421                 blob1 = data_blob_const(bytes+key_len, num_bytes-key_len);
4422                 if (blob1.length > 0) {
4423                         size_t len;
4424                         bool ok;
4425
4426                         len = utf16_len_n(blob1.data,
4427                                           blob1.length);
4428                         blob1.length = len;
4429
4430                         ok = convert_string_talloc(state,
4431                                                    CH_DOS,
4432                                                    CH_UNIX,
4433                                                    blob1.data,
4434                                                    blob1.length,
4435                                                    &server_workgroup,
4436                                                    &len);
4437                         if (!ok) {
4438                                 status = map_nt_error_from_unix_common(errno);
4439                                 tevent_req_nterror(req, status);
4440                                 return;
4441                         }
4442                 }
4443
4444         } else {
4445                 /* the old core protocol */
4446                 server_time_zone = get_time_zone(time(NULL));
4447                 server_max_xmit = 1024;
4448                 server_max_mux = 1;
4449         }
4450
4451         if (server_max_xmit < 1024) {
4452                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4453                 return;
4454         }
4455
4456         if (server_max_mux < 1) {
4457                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4458                 return;
4459         }
4460
4461         /*
4462          * Now calculate the negotiated capabilities
4463          * based on the mask for:
4464          * - client only flags
4465          * - flags used in both directions
4466          * - server only flags
4467          */
4468         both_capabilities = client_capabilities & server_capabilities;
4469         capabilities = client_capabilities & SMB_CAP_CLIENT_MASK;
4470         capabilities |= both_capabilities & SMB_CAP_BOTH_MASK;
4471         capabilities |= server_capabilities & SMB_CAP_SERVER_MASK;
4472
4473         max_xmit = MIN(client_max_xmit, server_max_xmit);
4474
4475         conn->smb1.server.capabilities = server_capabilities;
4476         conn->smb1.capabilities = capabilities;
4477
4478         conn->smb1.server.max_xmit = server_max_xmit;
4479         conn->smb1.max_xmit = max_xmit;
4480
4481         conn->smb1.server.max_mux = server_max_mux;
4482
4483         conn->smb1.server.security_mode = server_security_mode;
4484
4485         conn->smb1.server.readbraw = server_readbraw;
4486         conn->smb1.server.writebraw = server_writebraw;
4487         conn->smb1.server.lockread = server_lockread;
4488         conn->smb1.server.writeunlock = server_writeunlock;
4489
4490         conn->smb1.server.session_key = server_session_key;
4491
4492         talloc_steal(conn, server_gss_blob.data);
4493         conn->smb1.server.gss_blob = server_gss_blob;
4494         conn->smb1.server.guid = server_guid;
4495         memcpy(conn->smb1.server.challenge, server_challenge, 8);
4496         conn->smb1.server.workgroup = talloc_move(conn, &server_workgroup);
4497         conn->smb1.server.name = talloc_move(conn, &server_name);
4498
4499         conn->smb1.server.time_zone = server_time_zone;
4500         conn->smb1.server.system_time = server_system_time;
4501
4502         tevent_req_done(req);
4503 }
4504
4505 static size_t smbXcli_padding_helper(uint32_t offset, size_t n)
4506 {
4507         if ((offset & (n-1)) == 0) return 0;
4508         return n - (offset & (n-1));
4509 }
4510
4511 static struct tevent_req *smbXcli_negprot_smb2_subreq(struct smbXcli_negprot_state *state)
4512 {
4513         size_t i;
4514         uint8_t *buf;
4515         uint16_t dialect_count = 0;
4516         DATA_BLOB dyn = data_blob_null;
4517
4518         for (i=0; i < ARRAY_SIZE(smb2cli_prots); i++) {
4519                 bool ok;
4520                 uint8_t val[2];
4521
4522                 if (smb2cli_prots[i].proto < state->conn->min_protocol) {
4523                         continue;
4524                 }
4525
4526                 if (smb2cli_prots[i].proto > state->conn->max_protocol) {
4527                         continue;
4528                 }
4529
4530                 SSVAL(val, 0, smb2cli_prots[i].smb2_dialect);
4531
4532                 ok = data_blob_append(state, &dyn, val, sizeof(val));
4533                 if (!ok) {
4534                         return NULL;
4535                 }
4536
4537                 dialect_count++;
4538         }
4539
4540         buf = state->smb2.fixed;
4541         SSVAL(buf, 0, 36);
4542         SSVAL(buf, 2, dialect_count);
4543         SSVAL(buf, 4, state->conn->smb2.client.security_mode);
4544         SSVAL(buf, 6, 0);       /* Reserved */
4545         if (state->conn->max_protocol >= PROTOCOL_SMB2_22) {
4546                 SIVAL(buf, 8, state->conn->smb2.client.capabilities);
4547         } else {
4548                 SIVAL(buf, 8, 0);       /* Capabilities */
4549         }
4550         if (state->conn->max_protocol >= PROTOCOL_SMB2_10) {
4551                 NTSTATUS status;
4552                 DATA_BLOB blob;
4553
4554                 status = GUID_to_ndr_blob(&state->conn->smb2.client.guid,
4555                                           state, &blob);
4556                 if (!NT_STATUS_IS_OK(status)) {
4557                         return NULL;
4558                 }
4559                 memcpy(buf+12, blob.data, 16); /* ClientGuid */
4560         } else {
4561                 memset(buf+12, 0, 16);  /* ClientGuid */
4562         }
4563
4564         if (state->conn->max_protocol >= PROTOCOL_SMB3_10) {
4565                 NTSTATUS status;
4566                 struct smb2_negotiate_contexts c = { .num_contexts = 0, };
4567                 uint32_t offset;
4568                 DATA_BLOB b;
4569                 uint8_t p[38];
4570                 const uint8_t zeros[8] = {0, };
4571                 size_t pad;
4572                 bool ok;
4573
4574                 SSVAL(p, 0,  1); /* HashAlgorithmCount */
4575                 SSVAL(p, 2, 32); /* SaltLength */
4576                 SSVAL(p, 4, SMB2_PREAUTH_INTEGRITY_SHA512);
4577                 generate_random_buffer(p + 6, 32);
4578
4579                 b = data_blob_const(p, 38);
4580                 status = smb2_negotiate_context_add(state, &c,
4581                                         SMB2_PREAUTH_INTEGRITY_CAPABILITIES, b);
4582                 if (!NT_STATUS_IS_OK(status)) {
4583                         return NULL;
4584                 }
4585
4586                 SSVAL(p, 0, 2); /* ChiperCount */
4587                 SSVAL(p, 2, SMB2_ENCRYPTION_AES128_GCM);
4588                 SSVAL(p, 4, SMB2_ENCRYPTION_AES128_CCM);
4589
4590                 b = data_blob_const(p, 6);
4591                 status = smb2_negotiate_context_add(state, &c,
4592                                         SMB2_ENCRYPTION_CAPABILITIES, b);
4593                 if (!NT_STATUS_IS_OK(status)) {
4594                         return NULL;
4595                 }
4596
4597                 status = smb2_negotiate_context_push(state, &b, c);
4598                 if (!NT_STATUS_IS_OK(status)) {
4599                         return NULL;
4600                 }
4601
4602                 offset = SMB2_HDR_BODY + sizeof(state->smb2.fixed) + dyn.length;
4603                 pad = smbXcli_padding_helper(offset, 8);
4604
4605                 ok = data_blob_append(state, &dyn, zeros, pad);
4606                 if (!ok) {
4607                         return NULL;
4608                 }
4609                 offset += pad;
4610
4611                 ok = data_blob_append(state, &dyn, b.data, b.length);
4612                 if (!ok) {
4613                         return NULL;
4614                 }
4615
4616                 SIVAL(buf, 28, offset);   /* NegotiateContextOffset */
4617                 SSVAL(buf, 32, c.num_contexts); /* NegotiateContextCount */
4618                 SSVAL(buf, 34, 0);        /* Reserved */
4619         } else {
4620                 SBVAL(buf, 28, 0);      /* Reserved/ClientStartTime */
4621         }
4622
4623         return smb2cli_req_send(state, state->ev,
4624                                 state->conn, SMB2_OP_NEGPROT,
4625                                 0, 0, /* flags */
4626                                 state->timeout_msec,
4627                                 NULL, NULL, /* tcon, session */
4628                                 state->smb2.fixed, sizeof(state->smb2.fixed),
4629                                 dyn.data, dyn.length,
4630                                 UINT16_MAX); /* max_dyn_len */
4631 }
4632
4633 static void smbXcli_negprot_smb2_done(struct tevent_req *subreq)
4634 {
4635         struct tevent_req *req =
4636                 tevent_req_callback_data(subreq,
4637                 struct tevent_req);
4638         struct smbXcli_negprot_state *state =
4639                 tevent_req_data(req,
4640                 struct smbXcli_negprot_state);
4641         struct smbXcli_conn *conn = state->conn;
4642         size_t security_offset, security_length;
4643         DATA_BLOB blob;
4644         NTSTATUS status;
4645         struct iovec *iov;
4646         uint8_t *body;
4647         size_t i;
4648         uint16_t dialect_revision;
4649         struct smb2_negotiate_contexts c = { .num_contexts = 0, };
4650         uint32_t negotiate_context_offset = 0;
4651         uint16_t negotiate_context_count = 0;
4652         DATA_BLOB negotiate_context_blob = data_blob_null;
4653         size_t avail;
4654         size_t ctx_ofs;
4655         size_t needed;
4656         struct smb2_negotiate_context *preauth = NULL;
4657         uint16_t hash_count;
4658         uint16_t salt_length;
4659         uint16_t hash_selected;
4660         struct hc_sha512state sctx;
4661         struct smb2_negotiate_context *cipher = NULL;
4662         struct iovec sent_iov[3];
4663         static const struct smb2cli_req_expected_response expected[] = {
4664         {
4665                 .status = NT_STATUS_OK,
4666                 .body_size = 0x41
4667         }
4668         };
4669
4670         status = smb2cli_req_recv(subreq, state, &iov,
4671                                   expected, ARRAY_SIZE(expected));
4672         if (tevent_req_nterror(req, status)) {
4673                 return;
4674         }
4675
4676         body = (uint8_t *)iov[1].iov_base;
4677
4678         dialect_revision = SVAL(body, 4);
4679
4680         for (i=0; i < ARRAY_SIZE(smb2cli_prots); i++) {
4681                 if (smb2cli_prots[i].proto < state->conn->min_protocol) {
4682                         continue;
4683                 }
4684
4685                 if (smb2cli_prots[i].proto > state->conn->max_protocol) {
4686                         continue;
4687                 }
4688
4689                 if (smb2cli_prots[i].smb2_dialect != dialect_revision) {
4690                         continue;
4691                 }
4692
4693                 conn->protocol = smb2cli_prots[i].proto;
4694                 break;
4695         }
4696
4697         if (conn->protocol == PROTOCOL_NONE) {
4698                 TALLOC_FREE(subreq);
4699
4700                 if (state->conn->min_protocol >= PROTOCOL_SMB2_02) {
4701                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4702                         return;
4703                 }
4704
4705                 if (dialect_revision != SMB2_DIALECT_REVISION_2FF) {
4706                         tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4707                         return;
4708                 }
4709
4710                 /* make sure we do not loop forever */
4711                 state->conn->min_protocol = PROTOCOL_SMB2_02;
4712
4713                 /*
4714                  * send a SMB2 negprot, in order to negotiate
4715                  * the SMB2 dialect.
4716                  */
4717                 subreq = smbXcli_negprot_smb2_subreq(state);
4718                 if (tevent_req_nomem(subreq, req)) {
4719                         return;
4720                 }
4721                 tevent_req_set_callback(subreq, smbXcli_negprot_smb2_done, req);
4722                 return;
4723         }
4724
4725         conn->smb2.server.security_mode = SVAL(body, 2);
4726         if (conn->protocol >= PROTOCOL_SMB3_10) {
4727                 negotiate_context_count = SVAL(body, 6);
4728         }
4729
4730         blob = data_blob_const(body + 8, 16);
4731         status = GUID_from_data_blob(&blob, &conn->smb2.server.guid);
4732         if (tevent_req_nterror(req, status)) {
4733                 return;
4734         }
4735
4736         conn->smb2.server.capabilities  = IVAL(body, 24);
4737         conn->smb2.server.max_trans_size= IVAL(body, 28);
4738         conn->smb2.server.max_read_size = IVAL(body, 32);
4739         conn->smb2.server.max_write_size= IVAL(body, 36);
4740         conn->smb2.server.system_time   = BVAL(body, 40);
4741         conn->smb2.server.start_time    = BVAL(body, 48);
4742
4743         security_offset = SVAL(body, 56);
4744         security_length = SVAL(body, 58);
4745
4746         if (security_offset != SMB2_HDR_BODY + iov[1].iov_len) {
4747                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4748                 return;
4749         }
4750
4751         if (security_length > iov[2].iov_len) {
4752                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4753                 return;
4754         }
4755
4756         conn->smb2.server.gss_blob = data_blob_talloc(conn,
4757                                                 iov[2].iov_base,
4758                                                 security_length);
4759         if (tevent_req_nomem(conn->smb2.server.gss_blob.data, req)) {
4760                 return;
4761         }
4762
4763         if (conn->protocol < PROTOCOL_SMB3_10) {
4764                 TALLOC_FREE(subreq);
4765
4766                 if (conn->smb2.server.capabilities & SMB2_CAP_ENCRYPTION) {
4767                         conn->smb2.server.cipher = SMB2_ENCRYPTION_AES128_CCM;
4768                 }
4769                 tevent_req_done(req);
4770                 return;
4771         }
4772
4773         if (conn->smb2.server.capabilities & SMB2_CAP_ENCRYPTION) {
4774                 tevent_req_nterror(req,
4775                                 NT_STATUS_INVALID_NETWORK_RESPONSE);
4776                 return;
4777         }
4778
4779         negotiate_context_offset = IVAL(body, 60);
4780         if (negotiate_context_offset < security_offset) {
4781                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4782                 return;
4783         }
4784
4785         ctx_ofs = negotiate_context_offset - security_offset;
4786         if (ctx_ofs > iov[2].iov_len) {
4787                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4788                 return;
4789         }
4790         avail = iov[2].iov_len - security_length;
4791         needed = iov[2].iov_len - ctx_ofs;
4792         if (needed > avail) {
4793                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4794                 return;
4795         }
4796
4797         negotiate_context_blob.data = (uint8_t *)iov[2].iov_base;
4798         negotiate_context_blob.length = iov[2].iov_len;
4799
4800         negotiate_context_blob.data += ctx_ofs;
4801         negotiate_context_blob.length -= ctx_ofs;
4802
4803         status = smb2_negotiate_context_parse(state, negotiate_context_blob, &c);
4804         if (tevent_req_nterror(req, status)) {
4805                 return;
4806         }
4807
4808         if (negotiate_context_count != c.num_contexts) {
4809                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4810                 return;
4811         }
4812
4813         preauth = smb2_negotiate_context_find(&c,
4814                                         SMB2_PREAUTH_INTEGRITY_CAPABILITIES);
4815         if (preauth == NULL) {
4816                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4817                 return;
4818         }
4819
4820         if (preauth->data.length < 6) {
4821                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4822                 return;
4823         }
4824
4825         hash_count = SVAL(preauth->data.data, 0);
4826         salt_length = SVAL(preauth->data.data, 2);
4827         hash_selected = SVAL(preauth->data.data, 4);
4828
4829         if (hash_count != 1) {
4830                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4831                 return;
4832         }
4833
4834         if (preauth->data.length != (6 + salt_length)) {
4835                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4836                 return;
4837         }
4838
4839         if (hash_selected != SMB2_PREAUTH_INTEGRITY_SHA512) {
4840                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
4841                 return;
4842         }
4843
4844         cipher = smb2_negotiate_context_find(&c, SMB2_ENCRYPTION_CAPABILITIES);
4845         if (cipher != NULL) {
4846                 uint16_t cipher_count;
4847
4848                 if (cipher->data.length < 2) {
4849                         tevent_req_nterror(req,
4850                                         NT_STATUS_INVALID_NETWORK_RESPONSE);
4851                         return;
4852                 }
4853
4854                 cipher_count = SVAL(cipher->data.data, 0);
4855
4856                 if (cipher_count > 1) {
4857                         tevent_req_nterror(req,
4858                                         NT_STATUS_INVALID_NETWORK_RESPONSE);
4859                         return;
4860                 }
4861
4862                 if (cipher->data.length != (2 + 2 * cipher_count)) {
4863                         tevent_req_nterror(req,
4864                                         NT_STATUS_INVALID_NETWORK_RESPONSE);
4865                         return;
4866                 }
4867
4868                 if (cipher_count == 1) {
4869                         uint16_t cipher_selected;
4870
4871                         cipher_selected = SVAL(cipher->data.data, 2);
4872
4873                         switch (cipher_selected) {
4874                         case SMB2_ENCRYPTION_AES128_GCM:
4875                         case SMB2_ENCRYPTION_AES128_CCM:
4876                                 conn->smb2.server.cipher = cipher_selected;
4877                                 break;
4878                         }
4879                 }
4880         }
4881
4882         /* First we hash the request */
4883         smb2cli_req_get_sent_iov(subreq, sent_iov);
4884         samba_SHA512_Init(&sctx);
4885         samba_SHA512_Update(&sctx, conn->smb2.preauth_sha512,
4886                       sizeof(conn->smb2.preauth_sha512));
4887         for (i = 0; i < 3; i++) {
4888                 samba_SHA512_Update(&sctx, sent_iov[i].iov_base, sent_iov[i].iov_len);
4889         }
4890         samba_SHA512_Final(conn->smb2.preauth_sha512, &sctx);
4891         TALLOC_FREE(subreq);
4892
4893         /* And now we hash the response */
4894         samba_SHA512_Init(&sctx);
4895         samba_SHA512_Update(&sctx, conn->smb2.preauth_sha512,
4896                       sizeof(conn->smb2.preauth_sha512));
4897         for (i = 0; i < 3; i++) {
4898                 samba_SHA512_Update(&sctx, iov[i].iov_base, iov[i].iov_len);
4899         }
4900         samba_SHA512_Final(conn->smb2.preauth_sha512, &sctx);
4901
4902         tevent_req_done(req);
4903 }
4904
4905 static NTSTATUS smbXcli_negprot_dispatch_incoming(struct smbXcli_conn *conn,
4906                                                   TALLOC_CTX *tmp_mem,
4907                                                   uint8_t *inbuf)
4908 {
4909         size_t num_pending = talloc_array_length(conn->pending);
4910         struct tevent_req *subreq;
4911         struct smbXcli_req_state *substate;
4912         struct tevent_req *req;
4913         uint32_t protocol_magic;
4914         size_t inbuf_len = smb_len_nbt(inbuf);
4915
4916         if (num_pending != 1) {
4917                 return NT_STATUS_INTERNAL_ERROR;
4918         }
4919
4920         if (inbuf_len < 4) {
4921                 return NT_STATUS_INVALID_NETWORK_RESPONSE;
4922         }
4923
4924         subreq = conn->pending[0];
4925         substate = tevent_req_data(subreq, struct smbXcli_req_state);
4926         req = tevent_req_callback_data(subreq, struct tevent_req);
4927
4928         protocol_magic = IVAL(inbuf, 4);
4929
4930         switch (protocol_magic) {
4931         case SMB_MAGIC:
4932                 tevent_req_set_callback(subreq, smbXcli_negprot_smb1_done, req);
4933                 conn->dispatch_incoming = smb1cli_conn_dispatch_incoming;
4934                 return smb1cli_conn_dispatch_incoming(conn, tmp_mem, inbuf);
4935
4936         case SMB2_MAGIC:
4937                 if (substate->smb2.recv_iov == NULL) {
4938                         /*
4939                          * For the SMB1 negprot we have move it.
4940                          */
4941                         substate->smb2.recv_iov = substate->smb1.recv_iov;
4942                         substate->smb1.recv_iov = NULL;
4943                 }
4944
4945                 /*
4946                  * we got an SMB2 answer, which consumed sequence number 0
4947                  * so we need to use 1 as the next one.
4948                  *
4949                  * we also need to set the current credits to 0
4950                  * as we consumed the initial one. The SMB2 answer
4951                  * hopefully grant us a new credit.
4952                  */
4953                 conn->smb2.mid = 1;
4954                 conn->smb2.cur_credits = 0;
4955                 tevent_req_set_callback(subreq, smbXcli_negprot_smb2_done, req);
4956                 conn->dispatch_incoming = smb2cli_conn_dispatch_incoming;
4957                 return smb2cli_conn_dispatch_incoming(conn, tmp_mem, inbuf);
4958         }
4959
4960         DEBUG(10, ("Got non-SMB PDU\n"));
4961         return NT_STATUS_INVALID_NETWORK_RESPONSE;
4962 }
4963
4964 NTSTATUS smbXcli_negprot_recv(struct tevent_req *req)
4965 {
4966         return tevent_req_simple_recv_ntstatus(req);
4967 }
4968
4969 NTSTATUS smbXcli_negprot(struct smbXcli_conn *conn,
4970                          uint32_t timeout_msec,
4971                          enum protocol_types min_protocol,
4972                          enum protocol_types max_protocol)
4973 {
4974         TALLOC_CTX *frame = talloc_stackframe();
4975         struct tevent_context *ev;
4976         struct tevent_req *req;
4977         NTSTATUS status = NT_STATUS_NO_MEMORY;
4978         bool ok;
4979
4980         if (smbXcli_conn_has_async_calls(conn)) {
4981                 /*
4982                  * Can't use sync call while an async call is in flight
4983                  */
4984                 status = NT_STATUS_INVALID_PARAMETER_MIX;
4985                 goto fail;
4986         }
4987         ev = samba_tevent_context_init(frame);
4988         if (ev == NULL) {
4989                 goto fail;
4990         }
4991         req = smbXcli_negprot_send(frame, ev, conn, timeout_msec,
4992                                    min_protocol, max_protocol);
4993         if (req == NULL) {
4994                 goto fail;
4995         }
4996         ok = tevent_req_poll_ntstatus(req, ev, &status);
4997         if (!ok) {
4998                 goto fail;
4999         }
5000         status = smbXcli_negprot_recv(req);
5001  fail:
5002         TALLOC_FREE(frame);
5003         return status;
5004 }
5005
5006 struct smb2cli_validate_negotiate_info_state {
5007         struct smbXcli_conn *conn;
5008         DATA_BLOB in_input_buffer;
5009         DATA_BLOB in_output_buffer;
5010         DATA_BLOB out_input_buffer;
5011         DATA_BLOB out_output_buffer;
5012         uint16_t dialect;
5013 };
5014
5015 static void smb2cli_validate_negotiate_info_done(struct tevent_req *subreq);
5016
5017 struct tevent_req *smb2cli_validate_negotiate_info_send(TALLOC_CTX *mem_ctx,
5018                                                 struct tevent_context *ev,
5019                                                 struct smbXcli_conn *conn,
5020                                                 uint32_t timeout_msec,
5021                                                 struct smbXcli_session *session,
5022                                                 struct smbXcli_tcon *tcon)
5023 {
5024         struct tevent_req *req;
5025         struct smb2cli_validate_negotiate_info_state *state;
5026         uint8_t *buf;
5027         uint16_t dialect_count = 0;
5028         struct tevent_req *subreq;
5029         bool _save_should_sign;
5030         size_t i;
5031
5032         req = tevent_req_create(mem_ctx, &state,
5033                                 struct smb2cli_validate_negotiate_info_state);
5034         if (req == NULL) {
5035                 return NULL;
5036         }
5037         state->conn = conn;
5038
5039         state->in_input_buffer = data_blob_talloc_zero(state,
5040                                         4 + 16 + 1 + 1 + 2);
5041         if (tevent_req_nomem(state->in_input_buffer.data, req)) {
5042                 return tevent_req_post(req, ev);
5043         }
5044         buf = state->in_input_buffer.data;
5045
5046         if (state->conn->max_protocol >= PROTOCOL_SMB2_22) {
5047                 SIVAL(buf, 0, conn->smb2.client.capabilities);
5048         } else {
5049                 SIVAL(buf, 0, 0); /* Capabilities */
5050         }
5051         if (state->conn->max_protocol >= PROTOCOL_SMB2_10) {
5052                 NTSTATUS status;
5053                 DATA_BLOB blob;
5054
5055                 status = GUID_to_ndr_blob(&conn->smb2.client.guid,
5056                                           state, &blob);
5057                 if (!NT_STATUS_IS_OK(status)) {
5058                         return NULL;
5059                 }
5060                 memcpy(buf+4, blob.data, 16); /* ClientGuid */
5061         } else {
5062                 memset(buf+4, 0, 16);   /* ClientGuid */
5063         }
5064         if (state->conn->min_protocol >= PROTOCOL_SMB2_02) {
5065                 SCVAL(buf, 20, conn->smb2.client.security_mode);
5066         } else {
5067                 SCVAL(buf, 20, 0);
5068         }
5069         SCVAL(buf, 21, 0); /* reserved */
5070
5071         for (i=0; i < ARRAY_SIZE(smb2cli_prots); i++) {
5072                 bool ok;
5073                 size_t ofs;
5074
5075                 if (smb2cli_prots[i].proto < state->conn->min_protocol) {
5076                         continue;
5077                 }
5078
5079                 if (smb2cli_prots[i].proto > state->conn->max_protocol) {
5080                         continue;
5081                 }
5082
5083                 if (smb2cli_prots[i].proto == state->conn->protocol) {
5084                         state->dialect = smb2cli_prots[i].smb2_dialect;
5085                 }
5086
5087                 ofs = state->in_input_buffer.length;
5088                 ok = data_blob_realloc(state, &state->in_input_buffer,
5089                                        ofs + 2);
5090                 if (!ok) {
5091                         tevent_req_oom(req);
5092                         return tevent_req_post(req, ev);
5093                 }
5094
5095                 buf = state->in_input_buffer.data;
5096                 SSVAL(buf, ofs, smb2cli_prots[i].smb2_dialect);
5097
5098                 dialect_count++;
5099         }
5100         buf = state->in_input_buffer.data;
5101         SSVAL(buf, 22, dialect_count);
5102
5103         _save_should_sign = smb2cli_tcon_is_signing_on(tcon);
5104         smb2cli_tcon_should_sign(tcon, true);
5105         subreq = smb2cli_ioctl_send(state, ev, conn,
5106                                     timeout_msec, session, tcon,
5107                                     UINT64_MAX, /* in_fid_persistent */
5108                                     UINT64_MAX, /* in_fid_volatile */
5109                                     FSCTL_VALIDATE_NEGOTIATE_INFO,
5110                                     0, /* in_max_input_length */
5111                                     &state->in_input_buffer,
5112                                     24, /* in_max_output_length */
5113                                     &state->in_output_buffer,
5114                                     SMB2_IOCTL_FLAG_IS_FSCTL);
5115         smb2cli_tcon_should_sign(tcon, _save_should_sign);
5116         if (tevent_req_nomem(subreq, req)) {
5117                 return tevent_req_post(req, ev);
5118         }
5119         tevent_req_set_callback(subreq,
5120                                 smb2cli_validate_negotiate_info_done,
5121                                 req);
5122
5123         return req;
5124 }
5125
5126 static void smb2cli_validate_negotiate_info_done(struct tevent_req *subreq)
5127 {
5128         struct tevent_req *req =
5129                 tevent_req_callback_data(subreq,
5130                 struct tevent_req);
5131         struct smb2cli_validate_negotiate_info_state *state =
5132                 tevent_req_data(req,
5133                 struct smb2cli_validate_negotiate_info_state);
5134         NTSTATUS status;
5135         const uint8_t *buf;
5136         uint32_t capabilities;
5137         DATA_BLOB guid_blob;
5138         struct GUID server_guid;
5139         uint16_t security_mode;
5140         uint16_t dialect;
5141
5142         status = smb2cli_ioctl_recv(subreq, state,
5143                                     &state->out_input_buffer,
5144                                     &state->out_output_buffer);
5145         TALLOC_FREE(subreq);
5146         if (NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED)) {
5147                 /*
5148                  * The response was signed, but not supported
5149                  *
5150                  * Older Windows and Samba releases return
5151                  * NT_STATUS_FILE_CLOSED.
5152                  */
5153                 tevent_req_done(req);
5154                 return;
5155         }
5156         if (NT_STATUS_EQUAL(status, NT_STATUS_INVALID_DEVICE_REQUEST)) {
5157                 /*
5158                  * The response was signed, but not supported
5159                  *
5160                  * This is returned by the NTVFS based Samba 4.x file server
5161                  * for file shares.
5162                  */
5163                 tevent_req_done(req);
5164                 return;
5165         }
5166         if (NT_STATUS_EQUAL(status, NT_STATUS_FS_DRIVER_REQUIRED)) {
5167                 /*
5168                  * The response was signed, but not supported
5169                  *
5170                  * This is returned by the NTVFS based Samba 4.x file server
5171                  * for ipc shares.
5172                  */
5173                 tevent_req_done(req);
5174                 return;
5175         }
5176         if (tevent_req_nterror(req, status)) {
5177                 return;
5178         }
5179
5180         if (state->out_output_buffer.length != 24) {
5181                 tevent_req_nterror(req, NT_STATUS_INVALID_NETWORK_RESPONSE);
5182                 return;
5183         }
5184
5185         buf = state->out_output_buffer.data;
5186
5187         capabilities = IVAL(buf, 0);
5188         guid_blob = data_blob_const(buf + 4, 16);
5189         status = GUID_from_data_blob(&guid_blob, &server_guid);
5190         if (tevent_req_nterror(req, status)) {
5191                 return;
5192         }
5193         security_mode = CVAL(buf, 20);
5194         dialect = SVAL(buf, 22);
5195
5196         if (capabilities != state->conn->smb2.server.capabilities) {
5197                 tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
5198                 return;
5199         }
5200
5201         if (!GUID_equal(&server_guid, &state->conn->smb2.server.guid)) {
5202                 tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
5203                 return;
5204         }
5205
5206         if (security_mode != state->conn->smb2.server.security_mode) {
5207                 tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
5208                 return;
5209         }
5210
5211         if (dialect != state->dialect) {
5212                 tevent_req_nterror(req, NT_STATUS_ACCESS_DENIED);
5213                 return;
5214         }
5215
5216         tevent_req_done(req);
5217 }
5218
5219 NTSTATUS smb2cli_validate_negotiate_info_recv(struct tevent_req *req)
5220 {
5221         return tevent_req_simple_recv_ntstatus(req);
5222 }
5223
5224 static int smbXcli_session_destructor(struct smbXcli_session *session)
5225 {
5226         if (session->conn == NULL) {
5227                 return 0;
5228         }
5229
5230         DLIST_REMOVE(session->conn->sessions, session);
5231         return 0;
5232 }
5233
5234 struct smbXcli_session *smbXcli_session_create(TALLOC_CTX *mem_ctx,
5235                                                struct smbXcli_conn *conn)
5236 {
5237         struct smbXcli_session *session;
5238
5239         session = talloc_zero(mem_ctx, struct smbXcli_session);
5240         if (session == NULL) {
5241                 return NULL;
5242         }
5243         session->smb2 = talloc_zero(session, struct smb2cli_session);
5244         if (session->smb2 == NULL) {
5245                 talloc_free(session);
5246                 return NULL;
5247         }
5248         talloc_set_destructor(session, smbXcli_session_destructor);
5249
5250         DLIST_ADD_END(conn->sessions, session, struct smbXcli_session *);
5251         session->conn = conn;
5252
5253         memcpy(session->smb2_channel.preauth_sha512,
5254                conn->smb2.preauth_sha512,
5255                sizeof(session->smb2_channel.preauth_sha512));
5256
5257         return session;
5258 }
5259
5260 struct smbXcli_session *smbXcli_session_copy(TALLOC_CTX *mem_ctx,
5261                                                 struct smbXcli_session *src)
5262 {
5263         struct smbXcli_session *session;
5264
5265         session = talloc_zero(mem_ctx, struct smbXcli_session);
5266         if (session == NULL) {
5267                 return NULL;
5268         }
5269         session->smb2 = talloc_zero(session, struct smb2cli_session);
5270         if (session->smb2 == NULL) {
5271                 talloc_free(session);
5272                 return NULL;
5273         }
5274
5275         session->conn = src->conn;
5276         *session->smb2 = *src->smb2;
5277         session->smb2_channel = src->smb2_channel;
5278         session->disconnect_expired = src->disconnect_expired;
5279
5280         DLIST_ADD_END(src->conn->sessions, session, struct smbXcli_session *);
5281         talloc_set_destructor(session, smbXcli_session_destructor);
5282
5283         return session;
5284 }
5285
5286 bool smbXcli_session_is_authenticated(struct smbXcli_session *session)
5287 {
5288         const DATA_BLOB *application_key;
5289
5290         if (session->conn == NULL) {
5291                 return false;
5292         }
5293
5294         /*
5295          * If we have an application key we had a session key negotiated
5296          * at auth time.
5297          */
5298         if (session->conn->protocol >= PROTOCOL_SMB2_02) {
5299                 application_key = &session->smb2->application_key;
5300         } else {
5301                 application_key = &session->smb1.application_key;
5302         }
5303
5304         if (application_key->length == 0) {
5305                 return false;
5306         }
5307
5308         return true;
5309 }
5310
5311 NTSTATUS smbXcli_session_application_key(struct smbXcli_session *session,
5312                                          TALLOC_CTX *mem_ctx,
5313                                          DATA_BLOB *key)
5314 {
5315         const DATA_BLOB *application_key;
5316
5317         *key = data_blob_null;
5318
5319         if (session->conn == NULL) {
5320                 return NT_STATUS_NO_USER_SESSION_KEY;
5321         }
5322
5323         if (session->conn->protocol >= PROTOCOL_SMB2_02) {
5324                 application_key = &session->smb2->application_key;
5325         } else {
5326                 application_key = &session->smb1.application_key;
5327         }
5328
5329         if (application_key->length == 0) {
5330                 return NT_STATUS_NO_USER_SESSION_KEY;
5331         }
5332
5333         *key = data_blob_dup_talloc(mem_ctx, *application_key);
5334         if (key->data == NULL) {
5335                 return NT_STATUS_NO_MEMORY;
5336         }
5337
5338         return NT_STATUS_OK;
5339 }
5340
5341 void smbXcli_session_set_disconnect_expired(struct smbXcli_session *session)
5342 {
5343         session->disconnect_expired = true;
5344 }
5345
5346 uint16_t smb1cli_session_current_id(struct smbXcli_session *session)
5347 {
5348         return session->smb1.session_id;
5349 }
5350
5351 void smb1cli_session_set_id(struct smbXcli_session *session,
5352                             uint16_t session_id)
5353 {
5354         session->smb1.session_id = session_id;
5355 }
5356
5357 NTSTATUS smb1cli_session_set_session_key(struct smbXcli_session *session,
5358                                          const DATA_BLOB _session_key)
5359 {
5360         struct smbXcli_conn *conn = session->conn;
5361         uint8_t session_key[16];
5362
5363         if (conn == NULL) {
5364                 return NT_STATUS_INVALID_PARAMETER_MIX;
5365         }
5366
5367         if (session->smb1.application_key.length != 0) {
5368                 /*
5369                  * TODO: do not allow this...
5370                  *
5371                  * return NT_STATUS_INVALID_PARAMETER_MIX;
5372                  */
5373                 data_blob_clear_free(&session->smb1.application_key);
5374                 session->smb1.protected_key = false;
5375         }
5376
5377         if (_session_key.length == 0) {
5378                 return NT_STATUS_OK;
5379         }
5380
5381         ZERO_STRUCT(session_key);
5382         memcpy(session_key, _session_key.data,
5383                MIN(_session_key.length, sizeof(session_key)));
5384
5385         session->smb1.application_key = data_blob_talloc(session,
5386                                                          session_key,
5387                                                          sizeof(session_key));
5388         ZERO_STRUCT(session_key);
5389         if (session->smb1.application_key.data == NULL) {
5390                 return NT_STATUS_NO_MEMORY;
5391         }
5392
5393         session->smb1.protected_key = false;
5394
5395         return NT_STATUS_OK;
5396 }
5397
5398 NTSTATUS smb1cli_session_protect_session_key(struct smbXcli_session *session)
5399 {
5400         if (session->smb1.protected_key) {
5401                 /* already protected */
5402                 return NT_STATUS_OK;
5403         }
5404
5405         if (session->smb1.application_key.length != 16) {
5406                 return NT_STATUS_INVALID_PARAMETER_MIX;
5407         }
5408
5409         smb_key_derivation(session->smb1.application_key.data,
5410                            session->smb1.application_key.length,
5411                            session->smb1.application_key.data);
5412
5413         session->smb1.protected_key = true;
5414
5415         return NT_STATUS_OK;
5416 }
5417
5418 uint8_t smb2cli_session_security_mode(struct smbXcli_session *session)
5419 {
5420         struct smbXcli_conn *conn = session->conn;
5421         uint8_t security_mode = 0;
5422
5423         if (conn == NULL) {
5424                 return security_mode;
5425         }
5426
5427         security_mode = SMB2_NEGOTIATE_SIGNING_ENABLED;
5428         if (conn->mandatory_signing) {
5429                 security_mode |= SMB2_NEGOTIATE_SIGNING_REQUIRED;
5430         }
5431
5432         return security_mode;
5433 }
5434
5435 uint64_t smb2cli_session_current_id(struct smbXcli_session *session)
5436 {
5437         return session->smb2->session_id;
5438 }
5439
5440 uint16_t smb2cli_session_get_flags(struct smbXcli_session *session)
5441 {
5442         return session->smb2->session_flags;
5443 }
5444
5445 void smb2cli_session_set_id_and_flags(struct smbXcli_session *session,
5446                                       uint64_t session_id,
5447                                       uint16_t session_flags)
5448 {
5449         session->smb2->session_id = session_id;
5450         session->smb2->session_flags = session_flags;
5451 }
5452
5453 void smb2cli_session_increment_channel_sequence(struct smbXcli_session *session)
5454 {
5455         session->smb2->channel_sequence += 1;
5456 }
5457
5458 uint16_t smb2cli_session_reset_channel_sequence(struct smbXcli_session *session,
5459                                                 uint16_t channel_sequence)
5460 {
5461         uint16_t prev_cs;
5462
5463         prev_cs = session->smb2->channel_sequence;
5464         session->smb2->channel_sequence = channel_sequence;
5465
5466         return prev_cs;
5467 }
5468
5469 void smb2cli_session_start_replay(struct smbXcli_session *session)
5470 {
5471         session->smb2->replay_active = true;
5472 }
5473
5474 void smb2cli_session_stop_replay(struct smbXcli_session *session)
5475 {
5476         session->smb2->replay_active = false;
5477 }
5478
5479 NTSTATUS smb2cli_session_update_preauth(struct smbXcli_session *session,
5480                                         const struct iovec *iov)
5481 {
5482         struct hc_sha512state sctx;
5483         size_t i;
5484
5485         if (session->conn == NULL) {
5486                 return NT_STATUS_INTERNAL_ERROR;
5487         }
5488
5489         if (session->conn->protocol < PROTOCOL_SMB3_10) {
5490                 return NT_STATUS_OK;
5491         }
5492
5493         if (session->smb2_channel.signing_key.length != 0) {
5494                 return NT_STATUS_OK;
5495         }
5496
5497         samba_SHA512_Init(&sctx);
5498         samba_SHA512_Update(&sctx, session->smb2_channel.preauth_sha512,
5499                       sizeof(session->smb2_channel.preauth_sha512));
5500         for (i = 0; i < 3; i++) {
5501                 samba_SHA512_Update(&sctx, iov[i].iov_base, iov[i].iov_len);
5502         }
5503         samba_SHA512_Final(session->smb2_channel.preauth_sha512, &sctx);
5504
5505         return NT_STATUS_OK;
5506 }
5507
5508 NTSTATUS smb2cli_session_set_session_key(struct smbXcli_session *session,
5509                                          const DATA_BLOB _session_key,
5510                                          const struct iovec *recv_iov)
5511 {
5512         struct smbXcli_conn *conn = session->conn;
5513         uint16_t no_sign_flags;
5514         uint8_t session_key[16];
5515         bool check_signature = true;
5516         uint32_t hdr_flags;
5517         NTSTATUS status;
5518         struct _derivation {
5519                 DATA_BLOB label;
5520                 DATA_BLOB context;
5521         };
5522         struct {
5523                 struct _derivation signing;
5524                 struct _derivation encryption;
5525                 struct _derivation decryption;
5526                 struct _derivation application;
5527         } derivation = { };
5528         size_t nonce_size = 0;
5529
5530         if (conn == NULL) {
5531                 return NT_STATUS_INVALID_PARAMETER_MIX;
5532         }
5533
5534         if (recv_iov[0].iov_len != SMB2_HDR_BODY) {
5535                 return NT_STATUS_INVALID_PARAMETER_MIX;
5536         }
5537
5538         no_sign_flags = SMB2_SESSION_FLAG_IS_GUEST | SMB2_SESSION_FLAG_IS_NULL;
5539
5540         if (session->smb2->session_flags & no_sign_flags) {
5541                 session->smb2->should_sign = false;
5542                 return NT_STATUS_OK;
5543         }
5544
5545         if (session->smb2->signing_key.length != 0) {
5546                 return NT_STATUS_INVALID_PARAMETER_MIX;
5547         }
5548
5549         if (conn->protocol >= PROTOCOL_SMB3_10) {
5550                 struct _derivation *d;
5551                 DATA_BLOB p;
5552
5553                 p = data_blob_const(session->smb2_channel.preauth_sha512,
5554                                 sizeof(session->smb2_channel.preauth_sha512));
5555
5556                 d = &derivation.signing;
5557                 d->label = data_blob_string_const_null("SMBSigningKey");
5558                 d->context = p;
5559
5560                 d = &derivation.encryption;
5561                 d->label = data_blob_string_const_null("SMBC2SCipherKey");
5562                 d->context = p;
5563
5564                 d = &derivation.decryption;
5565                 d->label = data_blob_string_const_null("SMBS2CCipherKey");
5566                 d->context = p;
5567
5568                 d = &derivation.application;
5569                 d->label = data_blob_string_const_null("SMBAppKey");
5570                 d->context = p;
5571
5572         } else if (conn->protocol >= PROTOCOL_SMB2_24) {
5573                 struct _derivation *d;
5574
5575                 d = &derivation.signing;
5576                 d->label = data_blob_string_const_null("SMB2AESCMAC");
5577                 d->context = data_blob_string_const_null("SmbSign");
5578
5579                 d = &derivation.encryption;
5580                 d->label = data_blob_string_const_null("SMB2AESCCM");
5581                 d->context = data_blob_string_const_null("ServerIn ");
5582
5583                 d = &derivation.decryption;
5584                 d->label = data_blob_string_const_null("SMB2AESCCM");
5585                 d->context = data_blob_string_const_null("ServerOut");
5586
5587                 d = &derivation.application;
5588                 d->label = data_blob_string_const_null("SMB2APP");
5589                 d->context = data_blob_string_const_null("SmbRpc");
5590         }
5591
5592         ZERO_STRUCT(session_key);
5593         memcpy(session_key, _session_key.data,
5594                MIN(_session_key.length, sizeof(session_key)));
5595
5596         session->smb2->signing_key = data_blob_talloc(session,
5597                                                      session_key,
5598                                                      sizeof(session_key));
5599         if (session->smb2->signing_key.data == NULL) {
5600                 ZERO_STRUCT(session_key);
5601                 return NT_STATUS_NO_MEMORY;
5602         }
5603
5604         if (conn->protocol >= PROTOCOL_SMB2_24) {
5605                 struct _derivation *d = &derivation.signing;
5606
5607                 smb2_key_derivation(session_key, sizeof(session_key),
5608                                     d->label.data, d->label.length,
5609                                     d->context.data, d->context.length,
5610                                     session->smb2->signing_key.data);
5611         }
5612
5613         session->smb2->encryption_key = data_blob_dup_talloc(session,
5614                                                 session->smb2->signing_key);
5615         if (session->smb2->encryption_key.data == NULL) {
5616                 ZERO_STRUCT(session_key);
5617                 return NT_STATUS_NO_MEMORY;
5618         }
5619
5620         if (conn->protocol >= PROTOCOL_SMB2_24) {
5621                 struct _derivation *d = &derivation.encryption;
5622
5623                 smb2_key_derivation(session_key, sizeof(session_key),
5624                                     d->label.data, d->label.length,
5625                                     d->context.data, d->context.length,
5626                                     session->smb2->encryption_key.data);
5627         }
5628
5629         session->smb2->decryption_key = data_blob_dup_talloc(session,
5630                                                 session->smb2->signing_key);
5631         if (session->smb2->decryption_key.data == NULL) {
5632                 ZERO_STRUCT(session_key);
5633                 return NT_STATUS_NO_MEMORY;
5634         }
5635
5636         if (conn->protocol >= PROTOCOL_SMB2_24) {
5637                 struct _derivation *d = &derivation.decryption;
5638
5639                 smb2_key_derivation(session_key, sizeof(session_key),
5640                                     d->label.data, d->label.length,
5641                                     d->context.data, d->context.length,
5642                                     session->smb2->decryption_key.data);
5643         }
5644
5645         session->smb2->application_key = data_blob_dup_talloc(session,
5646                                                 session->smb2->signing_key);
5647         if (session->smb2->application_key.data == NULL) {
5648                 ZERO_STRUCT(session_key);
5649                 return NT_STATUS_NO_MEMORY;
5650         }
5651
5652         if (conn->protocol >= PROTOCOL_SMB2_24) {
5653                 struct _derivation *d = &derivation.application;
5654
5655                 smb2_key_derivation(session_key, sizeof(session_key),
5656                                     d->label.data, d->label.length,
5657                                     d->context.data, d->context.length,
5658                                     session->smb2->application_key.data);
5659         }
5660         ZERO_STRUCT(session_key);
5661
5662         session->smb2_channel.signing_key = data_blob_dup_talloc(session,
5663                                                 session->smb2->signing_key);
5664         if (session->smb2_channel.signing_key.data == NULL) {
5665                 return NT_STATUS_NO_MEMORY;
5666         }
5667
5668         check_signature = conn->mandatory_signing;
5669
5670         hdr_flags = IVAL(recv_iov[0].iov_base, SMB2_HDR_FLAGS);
5671         if (hdr_flags & SMB2_HDR_FLAG_SIGNED) {
5672                 /*
5673                  * Sadly some vendors don't sign the
5674                  * final SMB2 session setup response
5675                  *
5676                  * At least Windows and Samba are always doing this
5677                  * if there's a session key available.
5678                  *
5679                  * We only check the signature if it's mandatory
5680                  * or SMB2_HDR_FLAG_SIGNED is provided.
5681                  */
5682                 check_signature = true;
5683         }
5684
5685         if (conn->protocol >= PROTOCOL_SMB3_10) {
5686                 check_signature = true;
5687         }
5688
5689         if (check_signature) {
5690                 status = smb2_signing_check_pdu(session->smb2_channel.signing_key,
5691                                                 session->conn->protocol,
5692                                                 recv_iov, 3);
5693                 if (!NT_STATUS_IS_OK(status)) {
5694                         return status;
5695                 }
5696         }
5697
5698         session->smb2->should_sign = false;
5699         session->smb2->should_encrypt = false;
5700
5701         if (conn->desire_signing) {
5702                 session->smb2->should_sign = true;
5703         }
5704
5705         if (conn->smb2.server.security_mode & SMB2_NEGOTIATE_SIGNING_REQUIRED) {
5706                 session->smb2->should_sign = true;
5707         }
5708
5709         if (session->smb2->session_flags & SMB2_SESSION_FLAG_ENCRYPT_DATA) {
5710                 session->smb2->should_encrypt = true;
5711         }
5712
5713         if (conn->protocol < PROTOCOL_SMB2_24) {
5714                 session->smb2->should_encrypt = false;
5715         }
5716
5717         if (conn->smb2.server.cipher == 0) {
5718                 session->smb2->should_encrypt = false;
5719         }
5720
5721         /*
5722          * CCM and GCM algorithms must never have their
5723          * nonce wrap, or the security of the whole
5724          * communication and the keys is destroyed.
5725          * We must drop the connection once we have
5726          * transfered too much data.
5727          *
5728          * NOTE: We assume nonces greater than 8 bytes.
5729          */
5730         generate_random_buffer((uint8_t *)&session->smb2->nonce_high_random,
5731                                sizeof(session->smb2->nonce_high_random));
5732         switch (conn->smb2.server.cipher) {
5733         case SMB2_ENCRYPTION_AES128_CCM:
5734                 nonce_size = AES_CCM_128_NONCE_SIZE;
5735                 break;
5736         case SMB2_ENCRYPTION_AES128_GCM:
5737                 nonce_size = AES_GCM_128_IV_SIZE;
5738                 break;
5739         default:
5740                 nonce_size = 0;
5741                 break;
5742         }
5743         session->smb2->nonce_high_max = SMB2_NONCE_HIGH_MAX(nonce_size);
5744         session->smb2->nonce_high = 0;
5745         session->smb2->nonce_low = 0;
5746
5747         return NT_STATUS_OK;
5748 }
5749
5750 NTSTATUS smb2cli_session_create_channel(TALLOC_CTX *mem_ctx,
5751                                         struct smbXcli_session *session1,
5752                                         struct smbXcli_conn *conn,
5753                                         struct smbXcli_session **_session2)
5754 {
5755         struct smbXcli_session *session2;
5756
5757         if (session1->smb2->signing_key.length == 0) {
5758                 return NT_STATUS_INVALID_PARAMETER_MIX;
5759         }
5760
5761         if (conn == NULL) {
5762                 return NT_STATUS_INVALID_PARAMETER_MIX;
5763         }
5764
5765         session2 = talloc_zero(mem_ctx, struct smbXcli_session);
5766         if (session2 == NULL) {
5767                 return NT_STATUS_NO_MEMORY;
5768         }
5769         session2->smb2 = talloc_reference(session2, session1->smb2);
5770         if (session2->smb2 == NULL) {
5771                 talloc_free(session2);
5772                 return NT_STATUS_NO_MEMORY;
5773         }
5774
5775         talloc_set_destructor(session2, smbXcli_session_destructor);
5776         DLIST_ADD_END(conn->sessions, session2, struct smbXcli_session *);
5777         session2->conn = conn;
5778
5779         memcpy(session2->smb2_channel.preauth_sha512,
5780                conn->smb2.preauth_sha512,
5781                sizeof(session2->smb2_channel.preauth_sha512));
5782
5783         *_session2 = session2;
5784         return NT_STATUS_OK;
5785 }
5786
5787 NTSTATUS smb2cli_session_set_channel_key(struct smbXcli_session *session,
5788                                          const DATA_BLOB _channel_key,
5789                                          const struct iovec *recv_iov)
5790 {
5791         struct smbXcli_conn *conn = session->conn;
5792         uint8_t channel_key[16];
5793         NTSTATUS status;
5794         struct _derivation {
5795                 DATA_BLOB label;
5796                 DATA_BLOB context;
5797         };
5798         struct {
5799                 struct _derivation signing;
5800         } derivation = { };
5801
5802         if (conn == NULL) {
5803                 return NT_STATUS_INVALID_PARAMETER_MIX;
5804         }
5805
5806         if (session->smb2_channel.signing_key.length != 0) {
5807                 return NT_STATUS_INVALID_PARAMETER_MIX;
5808         }
5809
5810         if (conn->protocol >= PROTOCOL_SMB3_10) {
5811                 struct _derivation *d;
5812                 DATA_BLOB p;
5813
5814                 p = data_blob_const(session->smb2_channel.preauth_sha512,
5815                                 sizeof(session->smb2_channel.preauth_sha512));
5816
5817                 d = &derivation.signing;
5818                 d->label = data_blob_string_const_null("SMBSigningKey");
5819                 d->context = p;
5820         } else if (conn->protocol >= PROTOCOL_SMB2_24) {
5821                 struct _derivation *d;
5822
5823                 d = &derivation.signing;
5824                 d->label = data_blob_string_const_null("SMB2AESCMAC");
5825                 d->context = data_blob_string_const_null("SmbSign");
5826         }
5827
5828         ZERO_STRUCT(channel_key);
5829         memcpy(channel_key, _channel_key.data,
5830                MIN(_channel_key.length, sizeof(channel_key)));
5831
5832         session->smb2_channel.signing_key = data_blob_talloc(session,
5833                                                 channel_key,
5834                                                 sizeof(channel_key));
5835         if (session->smb2_channel.signing_key.data == NULL) {
5836                 ZERO_STRUCT(channel_key);
5837                 return NT_STATUS_NO_MEMORY;
5838         }
5839
5840         if (conn->protocol >= PROTOCOL_SMB2_24) {
5841                 struct _derivation *d = &derivation.signing;
5842
5843                 smb2_key_derivation(channel_key, sizeof(channel_key),
5844                                     d->label.data, d->label.length,
5845                                     d->context.data, d->context.length,
5846                                     session->smb2_channel.signing_key.data);
5847         }
5848         ZERO_STRUCT(channel_key);
5849
5850         status = smb2_signing_check_pdu(session->smb2_channel.signing_key,
5851                                         session->conn->protocol,
5852                                         recv_iov, 3);
5853         if (!NT_STATUS_IS_OK(status)) {
5854                 return status;
5855         }
5856
5857         return NT_STATUS_OK;
5858 }
5859
5860 NTSTATUS smb2cli_session_encryption_on(struct smbXcli_session *session)
5861 {
5862         if (session->smb2->should_encrypt) {
5863                 return NT_STATUS_OK;
5864         }
5865
5866         if (session->conn->protocol < PROTOCOL_SMB2_24) {
5867                 return NT_STATUS_NOT_SUPPORTED;
5868         }
5869
5870         if (session->conn->smb2.server.cipher == 0) {
5871                 return NT_STATUS_NOT_SUPPORTED;
5872         }
5873
5874         if (session->smb2->signing_key.data == NULL) {
5875                 return NT_STATUS_NOT_SUPPORTED;
5876         }
5877         session->smb2->should_encrypt = true;
5878         return NT_STATUS_OK;
5879 }
5880
5881 struct smbXcli_tcon *smbXcli_tcon_create(TALLOC_CTX *mem_ctx)
5882 {
5883         struct smbXcli_tcon *tcon;
5884
5885         tcon = talloc_zero(mem_ctx, struct smbXcli_tcon);
5886         if (tcon == NULL) {
5887                 return NULL;
5888         }
5889
5890         return tcon;
5891 }
5892
5893 void smbXcli_tcon_set_fs_attributes(struct smbXcli_tcon *tcon,
5894                                     uint32_t fs_attributes)
5895 {
5896         tcon->fs_attributes = fs_attributes;
5897 }
5898
5899 uint32_t smbXcli_tcon_get_fs_attributes(struct smbXcli_tcon *tcon)
5900 {
5901         return tcon->fs_attributes;
5902 }
5903
5904 bool smbXcli_tcon_is_dfs_share(struct smbXcli_tcon *tcon)
5905 {
5906         if (tcon == NULL) {
5907                 return false;
5908         }
5909
5910         if (tcon->is_smb1) {
5911                 if (tcon->smb1.optional_support & SMB_SHARE_IN_DFS) {
5912                         return true;
5913                 }
5914
5915                 return false;
5916         }
5917
5918         if (tcon->smb2.capabilities & SMB2_SHARE_CAP_DFS) {
5919                 return true;
5920         }
5921
5922         return false;
5923 }
5924
5925 uint16_t smb1cli_tcon_current_id(struct smbXcli_tcon *tcon)
5926 {
5927         return tcon->smb1.tcon_id;
5928 }
5929
5930 void smb1cli_tcon_set_id(struct smbXcli_tcon *tcon, uint16_t tcon_id)
5931 {
5932         tcon->is_smb1 = true;
5933         tcon->smb1.tcon_id = tcon_id;
5934 }
5935
5936 bool smb1cli_tcon_set_values(struct smbXcli_tcon *tcon,
5937                              uint16_t tcon_id,
5938                              uint16_t optional_support,
5939                              uint32_t maximal_access,
5940                              uint32_t guest_maximal_access,
5941                              const char *service,
5942                              const char *fs_type)
5943 {
5944         tcon->is_smb1 = true;
5945         tcon->fs_attributes = 0;
5946         tcon->smb1.tcon_id = tcon_id;
5947         tcon->smb1.optional_support = optional_support;
5948         tcon->smb1.maximal_access = maximal_access;
5949         tcon->smb1.guest_maximal_access = guest_maximal_access;
5950
5951         TALLOC_FREE(tcon->smb1.service);
5952         tcon->smb1.service = talloc_strdup(tcon, service);
5953         if (service != NULL && tcon->smb1.service == NULL) {
5954                 return false;
5955         }
5956
5957         TALLOC_FREE(tcon->smb1.fs_type);
5958         tcon->smb1.fs_type = talloc_strdup(tcon, fs_type);
5959         if (fs_type != NULL && tcon->smb1.fs_type == NULL) {
5960                 return false;
5961         }
5962
5963         return true;
5964 }
5965
5966 uint32_t smb2cli_tcon_current_id(struct smbXcli_tcon *tcon)
5967 {
5968         return tcon->smb2.tcon_id;
5969 }
5970
5971 uint32_t smb2cli_tcon_capabilities(struct smbXcli_tcon *tcon)
5972 {
5973         return tcon->smb2.capabilities;
5974 }
5975
5976 void smb2cli_tcon_set_values(struct smbXcli_tcon *tcon,
5977                              struct smbXcli_session *session,
5978                              uint32_t tcon_id,
5979                              uint8_t type,
5980                              uint32_t flags,
5981                              uint32_t capabilities,
5982                              uint32_t maximal_access)
5983 {
5984         tcon->is_smb1 = false;
5985         tcon->fs_attributes = 0;
5986         tcon->smb2.tcon_id = tcon_id;
5987         tcon->smb2.type = type;
5988         tcon->smb2.flags = flags;
5989         tcon->smb2.capabilities = capabilities;
5990         tcon->smb2.maximal_access = maximal_access;
5991
5992         tcon->smb2.should_sign = false;
5993         tcon->smb2.should_encrypt = false;
5994
5995         if (session == NULL) {
5996                 return;
5997         }
5998
5999         tcon->smb2.should_sign = session->smb2->should_sign;
6000         tcon->smb2.should_encrypt = session->smb2->should_encrypt;
6001
6002         if (flags & SMB2_SHAREFLAG_ENCRYPT_DATA) {
6003                 tcon->smb2.should_encrypt = true;
6004         }
6005 }
6006
6007 void smb2cli_tcon_should_sign(struct smbXcli_tcon *tcon,
6008                               bool should_sign)
6009 {
6010         tcon->smb2.should_sign = should_sign;
6011 }
6012
6013 bool smb2cli_tcon_is_signing_on(struct smbXcli_tcon *tcon)
6014 {
6015         if (tcon->smb2.should_encrypt) {
6016                 return true;
6017         }
6018
6019         return tcon->smb2.should_sign;
6020 }
6021
6022 void smb2cli_tcon_should_encrypt(struct smbXcli_tcon *tcon,
6023                                  bool should_encrypt)
6024 {
6025         tcon->smb2.should_encrypt = should_encrypt;
6026 }
6027
6028 bool smb2cli_tcon_is_encryption_on(struct smbXcli_tcon *tcon)
6029 {
6030         return tcon->smb2.should_encrypt;
6031 }