s4:kdc: split out a sdb_keys_free() helper function
[Samba.git] / source3 / torture / test_smb2.c
blobc3f014100d92c803eb54e7356cf14f244dbb6c5d
1 /*
2 Unix SMB/CIFS implementation.
3 Initial test for the smb2 client lib
4 Copyright (C) Volker Lendecke 2011
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program. If not, see <http://www.gnu.org/licenses/>.
20 #include "includes.h"
21 #include "torture/proto.h"
22 #include "client.h"
23 #include "trans2.h"
24 #include "../libcli/smb/smbXcli_base.h"
25 #include "libcli/security/security.h"
26 #include "libsmb/proto.h"
27 #include "auth/credentials/credentials.h"
28 #include "auth/gensec/gensec.h"
29 #include "auth_generic.h"
30 #include "../librpc/ndr/libndr.h"
31 #include "libsmb/clirap.h"
32 #include "libsmb/cli_smb2_fnum.h"
34 extern fstring host, workgroup, share, password, username, myname;
35 extern struct cli_credentials *torture_creds;
37 bool run_smb2_basic(int dummy)
39 struct cli_state *cli;
40 NTSTATUS status;
41 uint64_t fid_persistent, fid_volatile;
42 const char *hello = "Hello, world\n";
43 uint8_t *result;
44 uint32_t nread;
45 uint8_t *dir_data;
46 uint32_t dir_data_length;
47 uint32_t saved_tid = 0;
48 struct smbXcli_tcon *saved_tcon = NULL;
49 uint64_t saved_uid = 0;
51 printf("Starting SMB2-BASIC\n");
53 if (!torture_init_connection(&cli)) {
54 return false;
57 status = smbXcli_negprot(cli->conn, cli->timeout,
58 PROTOCOL_SMB2_02, PROTOCOL_SMB2_02);
59 if (!NT_STATUS_IS_OK(status)) {
60 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
61 return false;
64 status = cli_session_setup_creds(cli, torture_creds);
65 if (!NT_STATUS_IS_OK(status)) {
66 printf("cli_session_setup returned %s\n", nt_errstr(status));
67 return false;
70 status = cli_tree_connect(cli, share, "?????", NULL);
71 if (!NT_STATUS_IS_OK(status)) {
72 printf("cli_tree_connect returned %s\n", nt_errstr(status));
73 return false;
76 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
77 cli->smb2.tcon, "smb2-basic.txt",
78 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
79 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
80 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
81 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
82 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
83 FILE_CREATE, /* create_disposition, */
84 FILE_DELETE_ON_CLOSE, /* create_options, */
85 NULL, /* smb2_create_blobs *blobs */
86 &fid_persistent,
87 &fid_volatile,
88 NULL, NULL, NULL);
89 if (!NT_STATUS_IS_OK(status)) {
90 printf("smb2cli_create returned %s\n", nt_errstr(status));
91 return false;
94 status = smb2cli_write(cli->conn, cli->timeout, cli->smb2.session,
95 cli->smb2.tcon, strlen(hello), 0, fid_persistent,
96 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
97 if (!NT_STATUS_IS_OK(status)) {
98 printf("smb2cli_write returned %s\n", nt_errstr(status));
99 return false;
102 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
103 cli->smb2.tcon, fid_persistent, fid_volatile);
104 if (!NT_STATUS_IS_OK(status)) {
105 printf("smb2cli_flush returned %s\n", nt_errstr(status));
106 return false;
109 status = smb2cli_read(cli->conn, cli->timeout, cli->smb2.session,
110 cli->smb2.tcon, 0x10000, 0, fid_persistent,
111 fid_volatile, 2, 0,
112 talloc_tos(), &result, &nread);
113 if (!NT_STATUS_IS_OK(status)) {
114 printf("smb2cli_read returned %s\n", nt_errstr(status));
115 return false;
118 if (nread != strlen(hello)) {
119 printf("smb2cli_read returned %d bytes, expected %d\n",
120 (int)nread, (int)strlen(hello));
121 return false;
124 if (memcmp(hello, result, nread) != 0) {
125 printf("smb2cli_read returned '%s', expected '%s'\n",
126 result, hello);
127 return false;
130 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
131 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
132 if (!NT_STATUS_IS_OK(status)) {
133 printf("smb2cli_close returned %s\n", nt_errstr(status));
134 return false;
137 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
138 cli->smb2.tcon, "",
139 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
140 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
141 SEC_STD_SYNCHRONIZE|
142 SEC_DIR_LIST|
143 SEC_DIR_READ_ATTRIBUTE, /* desired_access, */
144 0, /* file_attributes, */
145 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
146 FILE_OPEN, /* create_disposition, */
147 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
148 NULL, /* smb2_create_blobs *blobs */
149 &fid_persistent,
150 &fid_volatile,
151 NULL, NULL, NULL);
152 if (!NT_STATUS_IS_OK(status)) {
153 printf("smb2cli_create returned %s\n", nt_errstr(status));
154 return false;
157 status = smb2cli_query_directory(
158 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
159 1, 0, 0, fid_persistent, fid_volatile, "*", 0xffff,
160 talloc_tos(), &dir_data, &dir_data_length);
162 if (!NT_STATUS_IS_OK(status)) {
163 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
164 return false;
167 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
168 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
169 if (!NT_STATUS_IS_OK(status)) {
170 printf("smb2cli_close returned %s\n", nt_errstr(status));
171 return false;
174 saved_tid = smb2cli_tcon_current_id(cli->smb2.tcon);
175 saved_tcon = cli_state_save_tcon(cli);
176 if (saved_tcon == NULL) {
177 return false;
179 cli->smb2.tcon = smbXcli_tcon_create(cli);
180 smb2cli_tcon_set_values(cli->smb2.tcon,
181 NULL, /* session */
182 saved_tid,
183 0, /* type */
184 0, /* flags */
185 0, /* capabilities */
186 0 /* maximal_access */);
187 status = smb2cli_tdis(cli->conn,
188 cli->timeout,
189 cli->smb2.session,
190 cli->smb2.tcon);
191 cli_state_restore_tcon(cli, saved_tcon);
192 if (!NT_STATUS_IS_OK(status)) {
193 printf("smb2cli_tdis returned %s\n", nt_errstr(status));
194 return false;
197 status = smb2cli_tdis(cli->conn,
198 cli->timeout,
199 cli->smb2.session,
200 cli->smb2.tcon);
201 if (!NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED)) {
202 printf("2nd smb2cli_tdis returned %s\n", nt_errstr(status));
203 return false;
206 saved_uid = smb2cli_session_current_id(cli->smb2.session);
207 status = smb2cli_logoff(cli->conn, cli->timeout, cli->smb2.session);
208 if (!NT_STATUS_IS_OK(status)) {
209 printf("smb2cli_logoff returned %s\n", nt_errstr(status));
210 return false;
213 cli->smb2.session = smbXcli_session_create(cli, cli->conn);
214 if (cli->smb2.session == NULL) {
215 printf("smbXcli_session_create() returned NULL\n");
216 return false;
219 smb2cli_session_set_id_and_flags(cli->smb2.session, saved_uid, 0);
221 status = smb2cli_logoff(cli->conn, cli->timeout, cli->smb2.session);
222 if (!NT_STATUS_EQUAL(status, NT_STATUS_USER_SESSION_DELETED)) {
223 printf("2nd smb2cli_logoff returned %s\n", nt_errstr(status));
224 return false;
227 return true;
230 bool run_smb2_negprot(int dummy)
232 struct cli_state *cli;
233 NTSTATUS status;
234 enum protocol_types protocol;
235 const char *name = NULL;
237 printf("Starting SMB2-NEGPROT\n");
239 if (!torture_init_connection(&cli)) {
240 return false;
243 status = smbXcli_negprot(cli->conn, cli->timeout,
244 PROTOCOL_CORE, PROTOCOL_LATEST);
245 if (!NT_STATUS_IS_OK(status)) {
246 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
247 return false;
250 protocol = smbXcli_conn_protocol(cli->conn);
251 name = smb_protocol_types_string(protocol);
253 if (protocol >= PROTOCOL_SMB2_02) {
254 printf("Server supports %s\n", name);
255 } else {
256 printf("Server DOES NOT support SMB2, only %s\n", name);
257 return false;
260 status = smbXcli_negprot(cli->conn, cli->timeout,
261 protocol, protocol);
262 if (!NT_STATUS_EQUAL(status, NT_STATUS_CONNECTION_RESET) &&
263 !NT_STATUS_EQUAL(status, NT_STATUS_CONNECTION_DISCONNECTED) &&
264 !NT_STATUS_EQUAL(status, NT_STATUS_CONNECTION_ABORTED)) {
265 printf("2nd smbXcli_negprot should disconnect - returned %s\n",
266 nt_errstr(status));
267 return false;
270 if (smbXcli_conn_is_connected(cli->conn)) {
271 printf("2nd smbXcli_negprot should disconnect "
272 "- still connected\n");
273 return false;
276 return true;
279 bool run_smb2_anonymous(int dummy)
281 struct cli_state *cli = NULL;
282 NTSTATUS status;
283 struct cli_credentials *anon_creds = NULL;
284 bool guest = false;
286 printf("Starting SMB2-ANONYMOUS\n");
288 if (!torture_init_connection(&cli)) {
289 return false;
292 status = smbXcli_negprot(cli->conn, cli->timeout,
293 PROTOCOL_SMB2_02, PROTOCOL_LATEST);
294 if (!NT_STATUS_IS_OK(status)) {
295 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
296 return false;
299 anon_creds = cli_credentials_init_anon(talloc_tos());
300 if (anon_creds == NULL) {
301 printf("cli_credentials_init_anon failed\n");
302 return false;
305 status = cli_session_setup_creds(cli, anon_creds);
306 if (!NT_STATUS_IS_OK(status)) {
307 printf("cli_session_setup returned %s\n", nt_errstr(status));
308 return false;
311 guest = smbXcli_session_is_guest(cli->smb2.session);
312 if (guest) {
313 printf("anonymous session should not have guest authentication\n");
314 return false;
317 return true;
320 bool run_smb2_session_reconnect(int dummy)
322 struct cli_state *cli1;
323 struct cli_state *cli2;
324 NTSTATUS status;
325 bool ok;
326 uint64_t fid_persistent, fid_volatile;
327 struct tevent_context *ev;
328 struct tevent_req *subreq;
329 DATA_BLOB in_blob = data_blob_null;
330 DATA_BLOB out_blob;
331 DATA_BLOB session_key;
332 struct auth_generic_state *auth_generic_state;
333 struct iovec *recv_iov;
334 const char *hello = "Hello, world\n";
335 uint8_t *result;
336 uint32_t nread;
338 printf("Starting SMB2-SESSION-RECONNECT\n");
340 if (!torture_init_connection(&cli1)) {
341 return false;
344 status = smbXcli_negprot(cli1->conn, cli1->timeout,
345 PROTOCOL_SMB2_02, PROTOCOL_LATEST);
346 if (!NT_STATUS_IS_OK(status)) {
347 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
348 return false;
351 status = cli_session_setup_creds(cli1, torture_creds);
352 if (!NT_STATUS_IS_OK(status)) {
353 printf("cli_session_setup returned %s\n", nt_errstr(status));
354 return false;
357 status = cli_tree_connect(cli1, share, "?????", NULL);
358 if (!NT_STATUS_IS_OK(status)) {
359 printf("cli_tree_connect returned %s\n", nt_errstr(status));
360 return false;
363 status = smb2cli_create(cli1->conn, cli1->timeout, cli1->smb2.session,
364 cli1->smb2.tcon, "session-reconnect.txt",
365 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
366 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
367 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
368 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
369 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
370 FILE_CREATE, /* create_disposition, */
371 FILE_DELETE_ON_CLOSE, /* create_options, */
372 NULL, /* smb2_create_blobs *blobs */
373 &fid_persistent,
374 &fid_volatile,
375 NULL, NULL, NULL);
376 if (!NT_STATUS_IS_OK(status)) {
377 printf("smb2cli_create on cli1 %s\n", nt_errstr(status));
378 return false;
381 status = smb2cli_write(cli1->conn, cli1->timeout, cli1->smb2.session,
382 cli1->smb2.tcon, strlen(hello), 0, fid_persistent,
383 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
384 if (!NT_STATUS_IS_OK(status)) {
385 printf("smb2cli_write returned %s\n", nt_errstr(status));
386 return false;
389 status = smb2cli_flush(cli1->conn, cli1->timeout, cli1->smb2.session,
390 cli1->smb2.tcon, fid_persistent, fid_volatile);
391 if (!NT_STATUS_IS_OK(status)) {
392 printf("smb2cli_flush returned %s\n", nt_errstr(status));
393 return false;
396 status = smb2cli_read(cli1->conn, cli1->timeout, cli1->smb2.session,
397 cli1->smb2.tcon, 0x10000, 0, fid_persistent,
398 fid_volatile, 2, 0,
399 talloc_tos(), &result, &nread);
400 if (!NT_STATUS_IS_OK(status)) {
401 printf("smb2cli_read returned %s\n", nt_errstr(status));
402 return false;
405 if (nread != strlen(hello)) {
406 printf("smb2cli_read returned %d bytes, expected %d\n",
407 (int)nread, (int)strlen(hello));
408 return false;
411 if (memcmp(hello, result, nread) != 0) {
412 printf("smb2cli_read returned '%s', expected '%s'\n",
413 result, hello);
414 return false;
417 /* prepare second session */
419 if (!torture_init_connection(&cli2)) {
420 return false;
423 status = smbXcli_negprot(cli2->conn, cli2->timeout,
424 PROTOCOL_SMB2_02, PROTOCOL_LATEST);
425 if (!NT_STATUS_IS_OK(status)) {
426 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
427 return false;
430 status = auth_generic_client_prepare(talloc_tos(), &auth_generic_state);
431 if (!NT_STATUS_IS_OK(status)) {
432 printf("auth_generic_client_prepare returned %s\n", nt_errstr(status));
433 return false;
436 gensec_want_feature(auth_generic_state->gensec_security,
437 GENSEC_FEATURE_SESSION_KEY);
439 status = auth_generic_set_creds(auth_generic_state, torture_creds);
440 if (!NT_STATUS_IS_OK(status)) {
441 printf("auth_generic_set_creds returned %s\n", nt_errstr(status));
442 return false;
445 status = auth_generic_client_start(auth_generic_state, GENSEC_OID_NTLMSSP);
446 if (!NT_STATUS_IS_OK(status)) {
447 printf("auth_generic_client_start returned %s\n", nt_errstr(status));
448 return false;
451 ev = samba_tevent_context_init(talloc_tos());
452 if (ev == NULL) {
453 printf("samba_tevent_context_init() returned NULL\n");
454 return false;
457 status = gensec_update(auth_generic_state->gensec_security,
458 talloc_tos(), data_blob_null, &in_blob);
459 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
460 printf("gensec_update returned %s\n", nt_errstr(status));
461 return false;
464 cli2->smb2.session = smbXcli_session_create(cli2, cli2->conn);
466 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
467 cli2->conn,
468 cli2->timeout,
469 cli2->smb2.session,
470 0x0, /* in_flags */
471 SMB2_CAP_DFS, /* in_capabilities */
472 0, /* in_channel */
473 /* in_previous_session_id: */
474 smb2cli_session_current_id(cli1->smb2.session),
475 &in_blob); /* in_security_buffer */
476 if (subreq == NULL) {
477 printf("smb2cli_session_setup_send() returned NULL\n");
478 return false;
481 ok = tevent_req_poll(subreq, ev);
482 if (!ok) {
483 printf("tevent_req_poll() returned false\n");
484 return false;
487 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
488 NULL, &out_blob);
489 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
490 printf("smb2cli_session_setup_recv returned %s\n",
491 nt_errstr(status));
492 return false;
495 status = gensec_update(auth_generic_state->gensec_security,
496 talloc_tos(), out_blob, &in_blob);
497 if (!NT_STATUS_IS_OK(status)) {
498 printf("auth_generic_update returned %s\n", nt_errstr(status));
499 return false;
502 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
503 cli2->conn,
504 cli2->timeout,
505 cli2->smb2.session,
506 0x0, /* in_flags */
507 SMB2_CAP_DFS, /* in_capabilities */
508 0, /* in_channel */
509 /* in_previous_session_id: */
510 smb2cli_session_current_id(cli1->smb2.session),
511 &in_blob); /* in_security_buffer */
512 if (subreq == NULL) {
513 printf("smb2cli_session_setup_send() returned NULL\n");
514 return false;
517 ok = tevent_req_poll(subreq, ev);
518 if (!ok) {
519 printf("tevent_req_poll() returned false\n");
520 return false;
523 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
524 &recv_iov, &out_blob);
525 if (!NT_STATUS_IS_OK(status)) {
526 printf("smb2cli_session_setup_recv returned %s\n",
527 nt_errstr(status));
528 return false;
531 status = gensec_session_key(auth_generic_state->gensec_security, talloc_tos(),
532 &session_key);
533 if (!NT_STATUS_IS_OK(status)) {
534 printf("gensec_session_key returned %s\n",
535 nt_errstr(status));
536 return false;
539 /* check file operation on the old client */
541 status = smb2cli_flush(cli1->conn, cli1->timeout, cli1->smb2.session,
542 cli1->smb2.tcon, fid_persistent, fid_volatile);
543 if (!NT_STATUS_EQUAL(status, NT_STATUS_USER_SESSION_DELETED)) {
544 printf("smb2cli_flush returned %s\n", nt_errstr(status));
545 return false;
548 status = cli_tree_connect(cli1, share, "?????", NULL);
549 if (!NT_STATUS_EQUAL(status, NT_STATUS_USER_SESSION_DELETED)) {
550 printf("cli_tree_connect returned %s\n", nt_errstr(status));
551 return false;
555 * checking file operations without signing.
556 * on w2k8r2 at least, flush, read and write also work the same way,
557 * while create gives ACCESS_DENIED without signing
559 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
560 cli2->smb2.tcon, fid_persistent, fid_volatile);
561 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
562 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
564 printf("smb2cli_flush returned %s\n", nt_errstr(status));
565 return false;
568 status = smb2cli_write(cli2->conn, cli2->timeout, cli2->smb2.session,
569 cli2->smb2.tcon, strlen(hello), 0, fid_persistent,
570 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
571 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
572 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
574 printf("smb2cli_write returned %s\n", nt_errstr(status));
575 return false;
578 status = smb2cli_read(cli2->conn, cli2->timeout, cli2->smb2.session,
579 cli2->smb2.tcon, 0x10000, 0, fid_persistent,
580 fid_volatile, 2, 0,
581 talloc_tos(), &result, &nread);
582 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
583 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
585 printf("smb2cli_read returned %s\n", nt_errstr(status));
586 return false;
589 status = smb2cli_create(cli2->conn, cli2->timeout, cli2->smb2.session,
590 cli2->smb2.tcon, "session-reconnect.txt",
591 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
592 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
593 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
594 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
595 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
596 FILE_CREATE, /* create_disposition, */
597 FILE_DELETE_ON_CLOSE, /* create_options, */
598 NULL, /* smb2_create_blobs *blobs */
599 &fid_persistent,
600 &fid_volatile,
601 NULL, NULL, NULL);
602 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED) &&
603 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED)) {
604 printf("smb2cli_create on cli2 %s\n", nt_errstr(status));
605 return false;
608 /* now grab the session key and try with signing */
610 status = smb2cli_session_set_session_key(cli2->smb2.session,
611 session_key,
612 recv_iov);
613 if (!NT_STATUS_IS_OK(status)) {
614 printf("smb2cli_session_set_session_key %s\n", nt_errstr(status));
615 return false;
618 /* the tid seems to be irrelevant at this stage */
620 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
621 cli1->smb2.tcon, fid_persistent, fid_volatile);
622 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
623 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
625 printf("smb2cli_flush returned %s\n", nt_errstr(status));
626 return false;
629 status = smb2cli_write(cli2->conn, cli2->timeout, cli2->smb2.session,
630 cli1->smb2.tcon, strlen(hello), 0, fid_persistent,
631 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
632 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
633 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
635 printf("smb2cli_write returned %s\n", nt_errstr(status));
636 return false;
639 status = smb2cli_read(cli2->conn, cli2->timeout, cli2->smb2.session,
640 cli1->smb2.tcon, 0x10000, 0, fid_persistent,
641 fid_volatile, 2, 0,
642 talloc_tos(), &result, &nread);
643 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED) &&
644 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
646 printf("smb2cli_read returned %s\n", nt_errstr(status));
647 return false;
650 status = smb2cli_create(cli2->conn, cli2->timeout, cli2->smb2.session,
651 cli1->smb2.tcon, "session-reconnect.txt",
652 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
653 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
654 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
655 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
656 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
657 FILE_CREATE, /* create_disposition, */
658 FILE_DELETE_ON_CLOSE, /* create_options, */
659 NULL, /* smb2_create_blobs *blobs */
660 &fid_persistent,
661 &fid_volatile,
662 NULL, NULL, NULL);
663 if (!NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED) &&
664 !NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED))
666 printf("smb2cli_create on cli2 %s\n", nt_errstr(status));
667 return false;
670 /* now do a new tcon and test file calls again */
672 status = cli_tree_connect(cli2, share, "?????", NULL);
673 if (!NT_STATUS_IS_OK(status)) {
674 printf("cli_tree_connect returned %s\n", nt_errstr(status));
675 return false;
678 status = smb2cli_create(cli2->conn, cli2->timeout, cli2->smb2.session,
679 cli2->smb2.tcon, "session-reconnect.txt",
680 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
681 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
682 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
683 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
684 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
685 FILE_CREATE, /* create_disposition, */
686 FILE_DELETE_ON_CLOSE, /* create_options, */
687 NULL, /* smb2_create_blobs *blobs */
688 &fid_persistent,
689 &fid_volatile,
690 NULL, NULL, NULL);
691 if (!NT_STATUS_IS_OK(status)) {
692 printf("smb2cli_create on cli2 %s\n", nt_errstr(status));
693 return false;
696 status = smb2cli_write(cli2->conn, cli2->timeout, cli2->smb2.session,
697 cli2->smb2.tcon, strlen(hello), 0, fid_persistent,
698 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
699 if (!NT_STATUS_IS_OK(status)) {
700 printf("smb2cli_write returned %s\n", nt_errstr(status));
701 return false;
704 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
705 cli2->smb2.tcon, fid_persistent, fid_volatile);
706 if (!NT_STATUS_IS_OK(status)) {
707 printf("smb2cli_flush returned %s\n", nt_errstr(status));
708 return false;
711 status = smb2cli_read(cli2->conn, cli2->timeout, cli2->smb2.session,
712 cli2->smb2.tcon, 0x10000, 0, fid_persistent,
713 fid_volatile, 2, 0,
714 talloc_tos(), &result, &nread);
715 if (!NT_STATUS_IS_OK(status)) {
716 printf("smb2cli_read returned %s\n", nt_errstr(status));
717 return false;
720 if (nread != strlen(hello)) {
721 printf("smb2cli_read returned %d bytes, expected %d\n",
722 (int)nread, (int)strlen(hello));
723 return false;
726 if (memcmp(hello, result, nread) != 0) {
727 printf("smb2cli_read returned '%s', expected '%s'\n",
728 result, hello);
729 return false;
732 return true;
735 bool run_smb2_tcon_dependence(int dummy)
737 struct cli_state *cli;
738 NTSTATUS status;
739 uint64_t fid_persistent, fid_volatile;
740 const char *hello = "Hello, world\n";
741 uint8_t *result;
742 uint32_t nread;
743 struct smbXcli_tcon *tcon2;
744 uint32_t tcon2_id;
746 printf("Starting SMB2-TCON-DEPENDENCE\n");
748 if (!torture_init_connection(&cli)) {
749 return false;
752 status = smbXcli_negprot(cli->conn, cli->timeout,
753 PROTOCOL_SMB2_02, PROTOCOL_LATEST);
754 if (!NT_STATUS_IS_OK(status)) {
755 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
756 return false;
759 status = cli_session_setup_creds(cli, torture_creds);
760 if (!NT_STATUS_IS_OK(status)) {
761 printf("cli_session_setup returned %s\n", nt_errstr(status));
762 return false;
765 status = cli_tree_connect(cli, share, "?????", NULL);
766 if (!NT_STATUS_IS_OK(status)) {
767 printf("cli_tree_connect returned %s\n", nt_errstr(status));
768 return false;
771 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
772 cli->smb2.tcon, "tcon_depedence.txt",
773 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
774 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
775 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
776 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
777 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
778 FILE_CREATE, /* create_disposition, */
779 FILE_DELETE_ON_CLOSE, /* create_options, */
780 NULL, /* smb2_create_blobs *blobs */
781 &fid_persistent,
782 &fid_volatile,
783 NULL, NULL, NULL);
784 if (!NT_STATUS_IS_OK(status)) {
785 printf("smb2cli_create on cli %s\n", nt_errstr(status));
786 return false;
789 status = smb2cli_write(cli->conn, cli->timeout, cli->smb2.session,
790 cli->smb2.tcon, strlen(hello), 0, fid_persistent,
791 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
792 if (!NT_STATUS_IS_OK(status)) {
793 printf("smb2cli_write returned %s\n", nt_errstr(status));
794 return false;
797 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
798 cli->smb2.tcon, fid_persistent, fid_volatile);
799 if (!NT_STATUS_IS_OK(status)) {
800 printf("smb2cli_flush returned %s\n", nt_errstr(status));
801 return false;
804 status = smb2cli_read(cli->conn, cli->timeout, cli->smb2.session,
805 cli->smb2.tcon, 0x10000, 0, fid_persistent,
806 fid_volatile, 2, 0,
807 talloc_tos(), &result, &nread);
808 if (!NT_STATUS_IS_OK(status)) {
809 printf("smb2cli_read returned %s\n", nt_errstr(status));
810 return false;
813 if (nread != strlen(hello)) {
814 printf("smb2cli_read returned %d bytes, expected %d\n",
815 (int)nread, (int)strlen(hello));
816 return false;
819 if (memcmp(hello, result, nread) != 0) {
820 printf("smb2cli_read returned '%s', expected '%s'\n",
821 result, hello);
822 return false;
825 /* check behaviour with wrong tid... */
827 tcon2 = smbXcli_tcon_create(cli);
828 tcon2_id = smb2cli_tcon_current_id(cli->smb2.tcon);
829 tcon2_id++;
830 smb2cli_tcon_set_values(tcon2,
831 NULL, /* session */
832 tcon2_id,
833 0, /* type */
834 0, /* flags */
835 0, /* capabilities */
836 0 /* maximal_access */);
838 status = smb2cli_read(cli->conn, cli->timeout, cli->smb2.session,
839 tcon2, 0x10000, 0, fid_persistent,
840 fid_volatile, 2, 0,
841 talloc_tos(), &result, &nread);
842 if (!NT_STATUS_EQUAL(status, NT_STATUS_NETWORK_NAME_DELETED)) {
843 printf("smb2cli_read returned %s\n", nt_errstr(status));
844 return false;
847 talloc_free(tcon2);
849 return true;
852 bool run_smb2_multi_channel(int dummy)
854 struct cli_state *cli1;
855 struct cli_state *cli2;
856 struct cli_state *cli3;
857 NTSTATUS status;
858 bool ok;
859 uint64_t fid_persistent, fid_volatile;
860 struct tevent_context *ev;
861 struct tevent_req *subreq;
862 DATA_BLOB in_blob = data_blob_null;
863 DATA_BLOB out_blob;
864 DATA_BLOB channel_session_key;
865 struct auth_generic_state *auth_generic_state;
866 struct iovec *recv_iov;
867 const char *hello = "Hello, world\n";
868 uint8_t *result;
869 uint32_t nread;
870 struct GUID saved_guid = cli_state_client_guid;
872 printf("Starting SMB2-MULTI-CHANNEL\n");
874 cli_state_client_guid = GUID_random();
876 if (!torture_init_connection(&cli1)) {
877 return false;
880 if (!torture_init_connection(&cli2)) {
881 return false;
884 if (!torture_init_connection(&cli3)) {
885 return false;
888 cli_state_client_guid = saved_guid;
890 status = smbXcli_negprot(cli1->conn, cli1->timeout,
891 PROTOCOL_SMB3_00, PROTOCOL_LATEST);
892 if (!NT_STATUS_IS_OK(status)) {
893 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
894 return false;
897 status = smbXcli_negprot(cli2->conn, cli2->timeout,
898 PROTOCOL_SMB3_00, PROTOCOL_LATEST);
899 if (!NT_STATUS_IS_OK(status)) {
900 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
901 return false;
904 status = smbXcli_negprot(cli3->conn, cli3->timeout,
905 PROTOCOL_SMB3_00, PROTOCOL_LATEST);
906 if (!NT_STATUS_IS_OK(status)) {
907 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
908 return false;
911 status = cli_session_setup_creds(cli1, torture_creds);
912 if (!NT_STATUS_IS_OK(status)) {
913 printf("smb2cli_sesssetup returned %s\n", nt_errstr(status));
914 return false;
917 status = cli_tree_connect(cli1, share, "?????", NULL);
918 if (!NT_STATUS_IS_OK(status)) {
919 printf("cli_tree_connect returned %s\n", nt_errstr(status));
920 return false;
923 status = smb2cli_session_create_channel(cli2,
924 cli1->smb2.session,
925 cli2->conn,
926 &cli2->smb2.session);
927 if (!NT_STATUS_IS_OK(status)) {
928 printf("smb2cli_session_create_channel returned %s\n",
929 nt_errstr(status));
930 return false;
933 status = auth_generic_client_prepare(talloc_tos(), &auth_generic_state);
934 if (!NT_STATUS_IS_OK(status)) {
935 printf("auth_generic_client_prepare returned %s\n", nt_errstr(status));
936 return false;
939 gensec_want_feature(auth_generic_state->gensec_security,
940 GENSEC_FEATURE_SESSION_KEY);
942 status = auth_generic_set_creds(auth_generic_state, torture_creds);
943 if (!NT_STATUS_IS_OK(status)) {
944 printf("auth_generic_set_creds returned %s\n", nt_errstr(status));
945 return false;
948 status = auth_generic_client_start(auth_generic_state, GENSEC_OID_NTLMSSP);
949 if (!NT_STATUS_IS_OK(status)) {
950 printf("auth_generic_client_start returned %s\n", nt_errstr(status));
951 return false;
954 ev = samba_tevent_context_init(talloc_tos());
955 if (ev == NULL) {
956 printf("samba_tevent_context_init() returned NULL\n");
957 return false;
960 status = gensec_update(auth_generic_state->gensec_security,
961 talloc_tos(), data_blob_null, &in_blob);
962 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
963 printf("gensec_update returned %s\n", nt_errstr(status));
964 return false;
967 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
968 cli2->conn,
969 cli2->timeout,
970 cli2->smb2.session,
971 0x01, /* in_flags */
972 SMB2_CAP_DFS, /* in_capabilities */
973 0, /* in_channel */
974 0, /* in_previous_session_id */
975 &in_blob); /* in_security_buffer */
976 if (subreq == NULL) {
977 printf("smb2cli_session_setup_send() returned NULL\n");
978 return false;
981 ok = tevent_req_poll(subreq, ev);
982 if (!ok) {
983 printf("tevent_req_poll() returned false\n");
984 return false;
987 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
988 NULL, &out_blob);
989 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
990 printf("smb2cli_session_setup_recv returned %s\n",
991 nt_errstr(status));
992 return false;
995 status = gensec_update(auth_generic_state->gensec_security,
996 talloc_tos(), out_blob, &in_blob);
997 if (!NT_STATUS_IS_OK(status)) {
998 printf("auth_generic_update returned %s\n", nt_errstr(status));
999 return false;
1002 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1003 cli2->conn,
1004 cli2->timeout,
1005 cli2->smb2.session,
1006 0x01, /* in_flags */
1007 SMB2_CAP_DFS, /* in_capabilities */
1008 0, /* in_channel */
1009 0, /* in_previous_session_id */
1010 &in_blob); /* in_security_buffer */
1011 if (subreq == NULL) {
1012 printf("smb2cli_session_setup_send() returned NULL\n");
1013 return false;
1016 ok = tevent_req_poll(subreq, ev);
1017 if (!ok) {
1018 printf("tevent_req_poll() returned false\n");
1019 return false;
1022 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1023 &recv_iov, &out_blob);
1024 if (!NT_STATUS_IS_OK(status)) {
1025 printf("smb2cli_session_setup_recv returned %s\n",
1026 nt_errstr(status));
1027 return false;
1030 status = gensec_session_key(auth_generic_state->gensec_security, talloc_tos(),
1031 &channel_session_key);
1032 if (!NT_STATUS_IS_OK(status)) {
1033 printf("gensec_session_key returned %s\n",
1034 nt_errstr(status));
1035 return false;
1038 status = smb2cli_session_set_channel_key(cli2->smb2.session,
1039 channel_session_key,
1040 recv_iov);
1041 if (!NT_STATUS_IS_OK(status)) {
1042 printf("smb2cli_session_set_channel_key %s\n", nt_errstr(status));
1043 return false;
1046 status = smb2cli_session_create_channel(cli3,
1047 cli1->smb2.session,
1048 cli3->conn,
1049 &cli3->smb2.session);
1050 if (!NT_STATUS_IS_OK(status)) {
1051 printf("smb2cli_session_create_channel returned %s\n",
1052 nt_errstr(status));
1053 return false;
1056 status = auth_generic_client_prepare(talloc_tos(), &auth_generic_state);
1057 if (!NT_STATUS_IS_OK(status)) {
1058 printf("auth_generic_client_prepare returned %s\n", nt_errstr(status));
1059 return false;
1062 gensec_want_feature(auth_generic_state->gensec_security,
1063 GENSEC_FEATURE_SESSION_KEY);
1065 status = auth_generic_set_creds(auth_generic_state, torture_creds);
1066 if (!NT_STATUS_IS_OK(status)) {
1067 printf("auth_generic_set_creds returned %s\n", nt_errstr(status));
1068 return false;
1071 status = auth_generic_client_start(auth_generic_state, GENSEC_OID_NTLMSSP);
1072 if (!NT_STATUS_IS_OK(status)) {
1073 printf("auth_generic_client_start returned %s\n", nt_errstr(status));
1074 return false;
1077 status = gensec_update(auth_generic_state->gensec_security,
1078 talloc_tos(), data_blob_null, &in_blob);
1079 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1080 printf("gensec_update returned %s\n", nt_errstr(status));
1081 return false;
1084 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1085 cli3->conn,
1086 cli3->timeout,
1087 cli3->smb2.session,
1088 0x01, /* in_flags */
1089 SMB2_CAP_DFS, /* in_capabilities */
1090 0, /* in_channel */
1091 0, /* in_previous_session_id */
1092 &in_blob); /* in_security_buffer */
1093 if (subreq == NULL) {
1094 printf("smb2cli_session_setup_send() returned NULL\n");
1095 return false;
1098 ok = tevent_req_poll(subreq, ev);
1099 if (!ok) {
1100 printf("tevent_req_poll() returned false\n");
1101 return false;
1104 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1105 NULL, &out_blob);
1106 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1107 printf("smb2cli_session_setup_recv returned %s\n",
1108 nt_errstr(status));
1109 return false;
1112 status = gensec_update(auth_generic_state->gensec_security,
1113 talloc_tos(), out_blob, &in_blob);
1114 if (!NT_STATUS_IS_OK(status)) {
1115 printf("auth_generic_update returned %s\n", nt_errstr(status));
1116 return false;
1119 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1120 cli3->conn,
1121 cli3->timeout,
1122 cli3->smb2.session,
1123 0x01, /* in_flags */
1124 SMB2_CAP_DFS, /* in_capabilities */
1125 0, /* in_channel */
1126 0, /* in_previous_session_id */
1127 &in_blob); /* in_security_buffer */
1128 if (subreq == NULL) {
1129 printf("smb2cli_session_setup_send() returned NULL\n");
1130 return false;
1133 ok = tevent_req_poll(subreq, ev);
1134 if (!ok) {
1135 printf("tevent_req_poll() returned false\n");
1136 return false;
1139 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1140 &recv_iov, &out_blob);
1141 if (!NT_STATUS_IS_OK(status)) {
1142 printf("smb2cli_session_setup_recv returned %s\n",
1143 nt_errstr(status));
1144 return false;
1147 status = gensec_session_key(auth_generic_state->gensec_security, talloc_tos(),
1148 &channel_session_key);
1149 if (!NT_STATUS_IS_OK(status)) {
1150 printf("gensec_session_key returned %s\n",
1151 nt_errstr(status));
1152 return false;
1155 status = smb2cli_session_set_channel_key(cli3->smb2.session,
1156 channel_session_key,
1157 recv_iov);
1158 if (!NT_STATUS_IS_OK(status)) {
1159 printf("smb2cli_session_set_channel_key %s\n", nt_errstr(status));
1160 return false;
1163 status = smb2cli_create(cli2->conn, cli2->timeout, cli2->smb2.session,
1164 cli1->smb2.tcon, "multi-channel.txt",
1165 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1166 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1167 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1168 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1169 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1170 FILE_CREATE, /* create_disposition, */
1171 FILE_DELETE_ON_CLOSE, /* create_options, */
1172 NULL, /* smb2_create_blobs *blobs */
1173 &fid_persistent,
1174 &fid_volatile,
1175 NULL, NULL, NULL);
1176 if (!NT_STATUS_IS_OK(status)) {
1177 printf("smb2cli_create on cli2 %s\n", nt_errstr(status));
1178 return false;
1181 status = smb2cli_write(cli1->conn, cli1->timeout, cli1->smb2.session,
1182 cli1->smb2.tcon, strlen(hello), 0, fid_persistent,
1183 fid_volatile, 0, 0, (const uint8_t *)hello, NULL);
1184 if (!NT_STATUS_IS_OK(status)) {
1185 printf("smb2cli_write returned %s\n", nt_errstr(status));
1186 return false;
1189 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
1190 cli1->smb2.tcon, fid_persistent, fid_volatile);
1191 if (!NT_STATUS_IS_OK(status)) {
1192 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1193 return false;
1196 status = smb2cli_flush(cli1->conn, cli1->timeout, cli1->smb2.session,
1197 cli1->smb2.tcon, fid_persistent, fid_volatile);
1198 if (!NT_STATUS_IS_OK(status)) {
1199 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1200 return false;
1203 status = smb2cli_flush(cli3->conn, cli3->timeout, cli3->smb2.session,
1204 cli1->smb2.tcon, fid_persistent, fid_volatile);
1205 if (!NT_STATUS_IS_OK(status)) {
1206 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1207 return false;
1210 status = smb2cli_read(cli2->conn, cli2->timeout, cli2->smb2.session,
1211 cli1->smb2.tcon, 0x10000, 0, fid_persistent,
1212 fid_volatile, 2, 0,
1213 talloc_tos(), &result, &nread);
1214 if (!NT_STATUS_IS_OK(status)) {
1215 printf("smb2cli_read returned %s\n", nt_errstr(status));
1216 return false;
1219 if (nread != strlen(hello)) {
1220 printf("smb2cli_read returned %d bytes, expected %d\n",
1221 (int)nread, (int)strlen(hello));
1222 return false;
1225 if (memcmp(hello, result, nread) != 0) {
1226 printf("smb2cli_read returned '%s', expected '%s'\n",
1227 result, hello);
1228 return false;
1231 status = auth_generic_client_prepare(talloc_tos(), &auth_generic_state);
1232 if (!NT_STATUS_IS_OK(status)) {
1233 printf("auth_generic_client_prepare returned %s\n", nt_errstr(status));
1234 return false;
1237 gensec_want_feature(auth_generic_state->gensec_security,
1238 GENSEC_FEATURE_SESSION_KEY);
1240 status = auth_generic_set_creds(auth_generic_state, torture_creds);
1241 if (!NT_STATUS_IS_OK(status)) {
1242 printf("auth_generic_set_creds returned %s\n", nt_errstr(status));
1243 return false;
1246 status = auth_generic_client_start(auth_generic_state, GENSEC_OID_NTLMSSP);
1247 if (!NT_STATUS_IS_OK(status)) {
1248 printf("auth_generic_client_start returned %s\n", nt_errstr(status));
1249 return false;
1252 status = gensec_update(auth_generic_state->gensec_security,
1253 talloc_tos(), data_blob_null, &in_blob);
1254 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1255 printf("gensec_update returned %s\n", nt_errstr(status));
1256 return false;
1259 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1260 cli3->conn,
1261 cli3->timeout,
1262 cli3->smb2.session,
1263 0x0, /* in_flags */
1264 SMB2_CAP_DFS, /* in_capabilities */
1265 0, /* in_channel */
1266 0, /* in_previous_session_id */
1267 &in_blob); /* in_security_buffer */
1268 if (subreq == NULL) {
1269 printf("smb2cli_session_setup_send() returned NULL\n");
1270 return false;
1273 ok = tevent_req_poll(subreq, ev);
1274 if (!ok) {
1275 printf("tevent_req_poll() returned false\n");
1276 return false;
1279 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1280 NULL, &out_blob);
1281 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1282 printf("smb2cli_session_setup_recv returned %s\n",
1283 nt_errstr(status));
1284 return false;
1287 status = gensec_update(auth_generic_state->gensec_security,
1288 talloc_tos(), out_blob, &in_blob);
1289 if (!NT_STATUS_IS_OK(status)) {
1290 printf("auth_generic_update returned %s\n", nt_errstr(status));
1291 return false;
1294 status = smb2cli_flush(cli1->conn, cli1->timeout, cli1->smb2.session,
1295 cli1->smb2.tcon, fid_persistent, fid_volatile);
1296 if (!NT_STATUS_IS_OK(status)) {
1297 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1298 return false;
1301 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
1302 cli1->smb2.tcon, fid_persistent, fid_volatile);
1303 if (!NT_STATUS_IS_OK(status)) {
1304 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1305 return false;
1308 status = smb2cli_flush(cli3->conn, cli3->timeout, cli3->smb2.session,
1309 cli1->smb2.tcon, fid_persistent, fid_volatile);
1310 if (!NT_STATUS_IS_OK(status)) {
1311 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1312 return false;
1315 status = smb2cli_create(cli1->conn, cli1->timeout, cli1->smb2.session,
1316 cli1->smb2.tcon, "multi-channel-invalid.txt",
1317 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1318 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1319 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1320 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1321 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1322 FILE_CREATE, /* create_disposition, */
1323 FILE_DELETE_ON_CLOSE, /* create_options, */
1324 NULL, /* smb2_create_blobs *blobs */
1325 &fid_persistent,
1326 &fid_volatile,
1327 NULL, NULL, NULL);
1328 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1329 printf("smb2cli_create %s\n", nt_errstr(status));
1330 return false;
1333 status = smb2cli_create(cli2->conn, cli2->timeout, cli2->smb2.session,
1334 cli1->smb2.tcon, "multi-channel-invalid.txt",
1335 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1336 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1337 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1338 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1339 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1340 FILE_CREATE, /* create_disposition, */
1341 FILE_DELETE_ON_CLOSE, /* create_options, */
1342 NULL, /* smb2_create_blobs *blobs */
1343 &fid_persistent,
1344 &fid_volatile,
1345 NULL, NULL, NULL);
1346 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1347 printf("smb2cli_create %s\n", nt_errstr(status));
1348 return false;
1351 status = smb2cli_create(cli3->conn, cli3->timeout, cli3->smb2.session,
1352 cli1->smb2.tcon, "multi-channel-invalid.txt",
1353 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1354 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1355 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1356 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1357 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1358 FILE_CREATE, /* create_disposition, */
1359 FILE_DELETE_ON_CLOSE, /* create_options, */
1360 NULL, /* smb2_create_blobs *blobs */
1361 &fid_persistent,
1362 &fid_volatile,
1363 NULL, NULL, NULL);
1364 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1365 printf("smb2cli_create %s\n", nt_errstr(status));
1366 return false;
1369 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1370 cli2->conn,
1371 cli2->timeout,
1372 cli2->smb2.session,
1373 0x0, /* in_flags */
1374 SMB2_CAP_DFS, /* in_capabilities */
1375 0, /* in_channel */
1376 0, /* in_previous_session_id */
1377 &in_blob); /* in_security_buffer */
1378 if (subreq == NULL) {
1379 printf("smb2cli_session_setup_send() returned NULL\n");
1380 return false;
1383 ok = tevent_req_poll(subreq, ev);
1384 if (!ok) {
1385 printf("tevent_req_poll() returned false\n");
1386 return false;
1389 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1390 &recv_iov, &out_blob);
1391 if (!NT_STATUS_IS_OK(status)) {
1392 printf("smb2cli_session_setup_recv returned %s\n",
1393 nt_errstr(status));
1394 return false;
1397 status = smb2cli_close(cli3->conn, cli3->timeout, cli3->smb2.session,
1398 cli1->smb2.tcon, 0, fid_persistent, fid_volatile);
1399 if (!NT_STATUS_IS_OK(status)) {
1400 printf("smb2cli_close returned %s\n", nt_errstr(status));
1401 return false;
1404 status = smb2cli_flush(cli3->conn, cli3->timeout, cli3->smb2.session,
1405 cli1->smb2.tcon, fid_persistent, fid_volatile);
1406 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED)) {
1407 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1408 return false;
1411 status = smb2cli_flush(cli2->conn, cli2->timeout, cli2->smb2.session,
1412 cli1->smb2.tcon, fid_persistent, fid_volatile);
1413 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED)) {
1414 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1415 return false;
1418 status = smb2cli_flush(cli1->conn, cli1->timeout, cli1->smb2.session,
1419 cli1->smb2.tcon, fid_persistent, fid_volatile);
1420 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_CLOSED)) {
1421 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1422 return false;
1425 return true;
1428 bool run_smb2_session_reauth(int dummy)
1430 struct cli_state *cli;
1431 NTSTATUS status;
1432 bool ok;
1433 uint64_t fid_persistent, fid_volatile;
1434 uint64_t dir_persistent, dir_volatile;
1435 uint8_t *dir_data;
1436 uint32_t dir_data_length;
1437 struct tevent_context *ev;
1438 struct tevent_req *subreq;
1439 DATA_BLOB in_blob = data_blob_null;
1440 DATA_BLOB out_blob;
1441 DATA_BLOB in_input_buffer;
1442 DATA_BLOB out_output_buffer;
1443 uint8_t in_file_info_class;
1444 struct auth_generic_state *auth_generic_state;
1445 struct iovec *recv_iov;
1446 uint32_t saved_tid;
1447 struct smbXcli_tcon *saved_tcon;
1449 printf("Starting SMB2-SESSION_REAUTH\n");
1451 if (!torture_init_connection(&cli)) {
1452 return false;
1456 * PROTOCOL_SMB2_22 has a bug in win8pre0
1457 * it behaves like PROTOCOL_SMB2_02
1458 * and returns NT_STATUS_REQUEST_NOT_ACCEPTED,
1459 * while it allows it on PROTOCOL_SMB2_10.
1461 status = smbXcli_negprot(cli->conn, cli->timeout,
1462 PROTOCOL_SMB2_10, PROTOCOL_SMB2_10);
1463 if (!NT_STATUS_IS_OK(status)) {
1464 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
1465 return false;
1468 status = cli_session_setup_creds(cli, torture_creds);
1469 if (!NT_STATUS_IS_OK(status)) {
1470 printf("smb2cli_sesssetup returned %s\n", nt_errstr(status));
1471 return false;
1474 status = cli_tree_connect(cli, share, "?????", NULL);
1475 if (!NT_STATUS_IS_OK(status)) {
1476 printf("cli_tree_connect returned %s\n", nt_errstr(status));
1477 return false;
1480 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
1481 cli->smb2.tcon, "session-reauth.txt",
1482 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1483 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1484 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1485 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1486 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1487 FILE_CREATE, /* create_disposition, */
1488 FILE_DELETE_ON_CLOSE, /* create_options, */
1489 NULL, /* smb2_create_blobs *blobs */
1490 &fid_persistent,
1491 &fid_volatile,
1492 NULL, NULL, NULL);
1493 if (!NT_STATUS_IS_OK(status)) {
1494 printf("smb2cli_create %s\n", nt_errstr(status));
1495 return false;
1498 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
1499 cli->smb2.tcon, "",
1500 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1501 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1502 SEC_STD_SYNCHRONIZE|
1503 SEC_DIR_LIST|
1504 SEC_DIR_READ_ATTRIBUTE, /* desired_access, */
1505 0, /* file_attributes, */
1506 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1507 FILE_OPEN, /* create_disposition, */
1508 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
1509 NULL, /* smb2_create_blobs *blobs */
1510 &dir_persistent,
1511 &dir_volatile,
1512 NULL, NULL, NULL);
1513 if (!NT_STATUS_IS_OK(status)) {
1514 printf("smb2cli_create returned %s\n", nt_errstr(status));
1515 return false;
1518 status = smb2cli_query_directory(
1519 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
1520 1, 0x3, 0, dir_persistent, dir_volatile,
1521 "session-reauth.txt", 0xffff,
1522 talloc_tos(), &dir_data, &dir_data_length);
1523 if (!NT_STATUS_IS_OK(status)) {
1524 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
1525 return false;
1528 status = auth_generic_client_prepare(talloc_tos(), &auth_generic_state);
1529 if (!NT_STATUS_IS_OK(status)) {
1530 printf("auth_generic_client_prepare returned %s\n", nt_errstr(status));
1531 return false;
1534 gensec_want_feature(auth_generic_state->gensec_security,
1535 GENSEC_FEATURE_SESSION_KEY);
1537 status = auth_generic_set_creds(auth_generic_state, torture_creds);
1538 if (!NT_STATUS_IS_OK(status)) {
1539 printf("auth_generic_set_creds returned %s\n", nt_errstr(status));
1540 return false;
1543 status = auth_generic_client_start(auth_generic_state, GENSEC_OID_NTLMSSP);
1544 if (!NT_STATUS_IS_OK(status)) {
1545 printf("auth_generic_client_start returned %s\n", nt_errstr(status));
1546 return false;
1549 ev = samba_tevent_context_init(talloc_tos());
1550 if (ev == NULL) {
1551 printf("samba_tevent_context_init() returned NULL\n");
1552 return false;
1555 status = gensec_update(auth_generic_state->gensec_security,
1556 talloc_tos(), data_blob_null, &in_blob);
1557 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1558 printf("gensec_update returned %s\n", nt_errstr(status));
1559 return false;
1562 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1563 cli->conn,
1564 cli->timeout,
1565 cli->smb2.session,
1566 0x0, /* in_flags */
1567 SMB2_CAP_DFS, /* in_capabilities */
1568 0, /* in_channel */
1569 0, /* in_previous_session_id */
1570 &in_blob); /* in_security_buffer */
1571 if (subreq == NULL) {
1572 printf("smb2cli_session_setup_send() returned NULL\n");
1573 return false;
1576 ok = tevent_req_poll(subreq, ev);
1577 if (!ok) {
1578 printf("tevent_req_poll() returned false\n");
1579 return false;
1582 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1583 NULL, &out_blob);
1584 if (!NT_STATUS_EQUAL(status, NT_STATUS_MORE_PROCESSING_REQUIRED)) {
1585 printf("smb2cli_session_setup_recv returned %s\n",
1586 nt_errstr(status));
1587 return false;
1590 status = gensec_update(auth_generic_state->gensec_security,
1591 talloc_tos(), out_blob, &in_blob);
1592 if (!NT_STATUS_IS_OK(status)) {
1593 printf("auth_generic_update returned %s\n", nt_errstr(status));
1594 return false;
1597 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
1598 cli->smb2.tcon, fid_persistent, fid_volatile);
1599 if (!NT_STATUS_IS_OK(status)) {
1600 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1601 return false;
1604 status = smb2cli_query_directory(
1605 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
1606 1, 0x3, 0, dir_persistent, dir_volatile,
1607 "session-reauth.txt", 0xffff,
1608 talloc_tos(), &dir_data, &dir_data_length);
1609 if (!NT_STATUS_IS_OK(status)) {
1610 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
1611 return false;
1615 * query_info seems to be a path based operation on Windows...
1617 status = smb2cli_query_info(cli->conn,
1618 cli->timeout,
1619 cli->smb2.session,
1620 cli->smb2.tcon,
1621 SMB2_0_INFO_SECURITY,
1622 0, /* in_file_info_class */
1623 1024, /* in_max_output_length */
1624 NULL, /* in_input_buffer */
1625 SECINFO_OWNER, /* in_additional_info */
1626 0, /* in_flags */
1627 fid_persistent,
1628 fid_volatile,
1629 talloc_tos(),
1630 &out_output_buffer);
1631 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1632 printf("smb2cli_query_info (security) returned %s\n", nt_errstr(status));
1633 return false;
1636 in_file_info_class = SMB_FILE_POSITION_INFORMATION - 1000;
1637 status = smb2cli_query_info(cli->conn,
1638 cli->timeout,
1639 cli->smb2.session,
1640 cli->smb2.tcon,
1641 SMB2_0_INFO_FILE,
1642 in_file_info_class,
1643 1024, /* in_max_output_length */
1644 NULL, /* in_input_buffer */
1645 0, /* in_additional_info */
1646 0, /* in_flags */
1647 fid_persistent,
1648 fid_volatile,
1649 talloc_tos(),
1650 &out_output_buffer);
1651 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1652 printf("smb2cli_query_info (position) returned %s\n", nt_errstr(status));
1653 return false;
1656 in_input_buffer = data_blob_talloc(talloc_tos(), NULL, 8);
1657 SBVAL(in_input_buffer.data, 0, 512);
1659 in_file_info_class = SMB_FILE_POSITION_INFORMATION - 1000;
1660 status = smb2cli_set_info(cli->conn,
1661 cli->timeout,
1662 cli->smb2.session,
1663 cli->smb2.tcon,
1664 SMB2_0_INFO_FILE,
1665 in_file_info_class,
1666 &in_input_buffer,
1667 0, /* in_additional_info */
1668 fid_persistent,
1669 fid_volatile);
1670 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1671 printf("smb2cli_set_info (position) returned %s\n", nt_errstr(status));
1672 return false;
1675 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
1676 cli->smb2.tcon, "session-reauth-invalid.txt",
1677 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1678 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1679 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1680 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1681 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1682 FILE_CREATE, /* create_disposition, */
1683 FILE_DELETE_ON_CLOSE, /* create_options, */
1684 NULL, /* smb2_create_blobs *blobs */
1685 &fid_persistent,
1686 &fid_volatile,
1687 NULL, NULL, NULL);
1688 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1689 printf("smb2cli_create %s\n", nt_errstr(status));
1690 return false;
1693 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
1694 cli->smb2.tcon, "",
1695 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1696 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1697 SEC_STD_SYNCHRONIZE|
1698 SEC_DIR_LIST|
1699 SEC_DIR_READ_ATTRIBUTE, /* desired_access, */
1700 0, /* file_attributes, */
1701 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1702 FILE_OPEN, /* create_disposition, */
1703 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
1704 NULL, /* smb2_create_blobs *blobs */
1705 &dir_persistent,
1706 &dir_volatile,
1707 NULL, NULL, NULL);
1708 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1709 printf("smb2cli_create returned %s\n", nt_errstr(status));
1710 return false;
1713 saved_tid = smb2cli_tcon_current_id(cli->smb2.tcon);
1714 saved_tcon = cli->smb2.tcon;
1715 cli->smb2.tcon = smbXcli_tcon_create(cli);
1716 smb2cli_tcon_set_values(cli->smb2.tcon,
1717 NULL, /* session */
1718 saved_tid,
1719 0, /* type */
1720 0, /* flags */
1721 0, /* capabilities */
1722 0 /* maximal_access */);
1723 status = cli_tree_connect(cli, share, "?????", NULL);
1724 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
1725 printf("cli_tree_connect returned %s\n", nt_errstr(status));
1726 return false;
1728 talloc_free(cli->smb2.tcon);
1729 cli->smb2.tcon = saved_tcon;
1731 subreq = smb2cli_session_setup_send(talloc_tos(), ev,
1732 cli->conn,
1733 cli->timeout,
1734 cli->smb2.session,
1735 0x0, /* in_flags */
1736 SMB2_CAP_DFS, /* in_capabilities */
1737 0, /* in_channel */
1738 0, /* in_previous_session_id */
1739 &in_blob); /* in_security_buffer */
1740 if (subreq == NULL) {
1741 printf("smb2cli_session_setup_send() returned NULL\n");
1742 return false;
1745 ok = tevent_req_poll(subreq, ev);
1746 if (!ok) {
1747 printf("tevent_req_poll() returned false\n");
1748 return false;
1751 status = smb2cli_session_setup_recv(subreq, talloc_tos(),
1752 &recv_iov, &out_blob);
1753 if (!NT_STATUS_IS_OK(status)) {
1754 printf("smb2cli_session_setup_recv returned %s\n",
1755 nt_errstr(status));
1756 return false;
1759 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
1760 cli->smb2.tcon, fid_persistent, fid_volatile);
1761 if (!NT_STATUS_IS_OK(status)) {
1762 printf("smb2cli_flush returned %s\n", nt_errstr(status));
1763 return false;
1766 status = smb2cli_query_info(cli->conn,
1767 cli->timeout,
1768 cli->smb2.session,
1769 cli->smb2.tcon,
1770 SMB2_0_INFO_SECURITY,
1771 0, /* in_file_info_class */
1772 1024, /* in_max_output_length */
1773 NULL, /* in_input_buffer */
1774 SECINFO_OWNER, /* in_additional_info */
1775 0, /* in_flags */
1776 fid_persistent,
1777 fid_volatile,
1778 talloc_tos(),
1779 &out_output_buffer);
1780 if (!NT_STATUS_IS_OK(status)) {
1781 printf("smb2cli_query_info (security) returned %s\n", nt_errstr(status));
1782 return false;
1785 in_file_info_class = SMB_FILE_POSITION_INFORMATION - 1000;
1786 status = smb2cli_query_info(cli->conn,
1787 cli->timeout,
1788 cli->smb2.session,
1789 cli->smb2.tcon,
1790 SMB2_0_INFO_FILE,
1791 in_file_info_class,
1792 1024, /* in_max_output_length */
1793 NULL, /* in_input_buffer */
1794 0, /* in_additional_info */
1795 0, /* in_flags */
1796 fid_persistent,
1797 fid_volatile,
1798 talloc_tos(),
1799 &out_output_buffer);
1800 if (!NT_STATUS_IS_OK(status)) {
1801 printf("smb2cli_query_info (position) returned %s\n", nt_errstr(status));
1802 return false;
1805 in_input_buffer = data_blob_talloc(talloc_tos(), NULL, 8);
1806 SBVAL(in_input_buffer.data, 0, 512);
1808 in_file_info_class = SMB_FILE_POSITION_INFORMATION - 1000;
1809 status = smb2cli_set_info(cli->conn,
1810 cli->timeout,
1811 cli->smb2.session,
1812 cli->smb2.tcon,
1813 SMB2_0_INFO_FILE,
1814 in_file_info_class,
1815 &in_input_buffer,
1816 0, /* in_additional_info */
1817 fid_persistent,
1818 fid_volatile);
1819 if (!NT_STATUS_IS_OK(status)) {
1820 printf("smb2cli_set_info (position) returned %s\n", nt_errstr(status));
1821 return false;
1824 in_file_info_class = SMB_FILE_POSITION_INFORMATION - 1000;
1825 status = smb2cli_query_info(cli->conn,
1826 cli->timeout,
1827 cli->smb2.session,
1828 cli->smb2.tcon,
1829 SMB2_0_INFO_FILE,
1830 in_file_info_class,
1831 1024, /* in_max_output_length */
1832 NULL, /* in_input_buffer */
1833 0, /* in_additional_info */
1834 0, /* in_flags */
1835 fid_persistent,
1836 fid_volatile,
1837 talloc_tos(),
1838 &out_output_buffer);
1839 if (!NT_STATUS_IS_OK(status)) {
1840 printf("smb2cli_query_info (position) returned %s\n", nt_errstr(status));
1841 return false;
1844 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
1845 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
1846 if (!NT_STATUS_IS_OK(status)) {
1847 printf("smb2cli_close returned %s\n", nt_errstr(status));
1848 return false;
1851 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
1852 cli->smb2.tcon, "session-reauth.txt",
1853 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
1854 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
1855 SEC_STD_ALL | SEC_FILE_ALL, /* desired_access, */
1856 FILE_ATTRIBUTE_NORMAL, /* file_attributes, */
1857 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
1858 FILE_CREATE, /* create_disposition, */
1859 FILE_DELETE_ON_CLOSE, /* create_options, */
1860 NULL, /* smb2_create_blobs *blobs */
1861 &fid_persistent,
1862 &fid_volatile,
1863 NULL, NULL, NULL);
1864 if (!NT_STATUS_IS_OK(status)) {
1865 printf("smb2cli_create %s\n", nt_errstr(status));
1866 return false;
1869 status = smb2cli_query_directory(
1870 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
1871 1, 0x3, 0, dir_persistent, dir_volatile,
1872 "session-reauth.txt", 0xffff,
1873 talloc_tos(), &dir_data, &dir_data_length);
1874 if (!NT_STATUS_IS_OK(status)) {
1875 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
1876 return false;
1879 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
1880 cli->smb2.tcon, 0, dir_persistent, dir_volatile);
1881 if (!NT_STATUS_IS_OK(status)) {
1882 printf("smb2cli_close returned %s\n", nt_errstr(status));
1883 return false;
1886 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
1887 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
1888 if (!NT_STATUS_IS_OK(status)) {
1889 printf("smb2cli_close returned %s\n", nt_errstr(status));
1890 return false;
1893 saved_tid = smb2cli_tcon_current_id(cli->smb2.tcon);
1894 saved_tcon = cli->smb2.tcon;
1895 cli->smb2.tcon = smbXcli_tcon_create(cli);
1896 smb2cli_tcon_set_values(cli->smb2.tcon,
1897 NULL, /* session */
1898 saved_tid,
1899 0, /* type */
1900 0, /* flags */
1901 0, /* capabilities */
1902 0 /* maximal_access */);
1903 status = cli_tree_connect(cli, share, "?????", NULL);
1904 if (!NT_STATUS_IS_OK(status)) {
1905 printf("cli_tree_connect returned %s\n", nt_errstr(status));
1906 return false;
1908 talloc_free(cli->smb2.tcon);
1909 cli->smb2.tcon = saved_tcon;
1911 return true;
1914 static NTSTATUS check_size(struct cli_state *cli,
1915 uint16_t fnum,
1916 const char *fname,
1917 size_t size)
1919 off_t size_read = 0;
1921 NTSTATUS status = cli_qfileinfo_basic(cli,
1922 fnum,
1923 NULL,
1924 &size_read,
1925 NULL,
1926 NULL,
1927 NULL,
1928 NULL,
1929 NULL);
1931 if (!NT_STATUS_IS_OK(status)) {
1932 printf("cli_qfileinfo_basic of %s failed (%s)\n",
1933 fname,
1934 nt_errstr(status));
1935 return status;
1938 if (size != size_read) {
1939 printf("size (%u) != size_read(%u) for %s\n",
1940 (unsigned int)size,
1941 (unsigned int)size_read,
1942 fname);
1943 /* Use EOF to mean bad size. */
1944 return NT_STATUS_END_OF_FILE;
1946 return NT_STATUS_OK;
1949 /* Ensure cli_ftruncate() works for SMB2. */
1951 bool run_smb2_ftruncate(int dummy)
1953 struct cli_state *cli = NULL;
1954 const char *fname = "smb2_ftruncate.txt";
1955 uint16_t fnum = (uint16_t)-1;
1956 bool correct = false;
1957 size_t buflen = 1024*1024;
1958 uint8_t *buf = NULL;
1959 unsigned int i;
1960 NTSTATUS status;
1962 printf("Starting SMB2-FTRUNCATE\n");
1964 if (!torture_init_connection(&cli)) {
1965 goto fail;
1968 status = smbXcli_negprot(cli->conn, cli->timeout,
1969 PROTOCOL_SMB2_02, PROTOCOL_SMB2_02);
1970 if (!NT_STATUS_IS_OK(status)) {
1971 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
1972 goto fail;
1975 status = cli_session_setup_creds(cli, torture_creds);
1976 if (!NT_STATUS_IS_OK(status)) {
1977 printf("cli_session_setup returned %s\n", nt_errstr(status));
1978 goto fail;
1981 status = cli_tree_connect(cli, share, "?????", NULL);
1982 if (!NT_STATUS_IS_OK(status)) {
1983 printf("cli_tree_connect returned %s\n", nt_errstr(status));
1984 goto fail;
1987 cli_setatr(cli, fname, 0, 0);
1988 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1990 status = cli_ntcreate(cli,
1991 fname,
1993 GENERIC_ALL_ACCESS,
1994 FILE_ATTRIBUTE_NORMAL,
1995 FILE_SHARE_NONE,
1996 FILE_CREATE,
1999 &fnum,
2000 NULL);
2002 if (!NT_STATUS_IS_OK(status)) {
2003 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
2004 goto fail;
2007 buf = talloc_zero_array(cli, uint8_t, buflen);
2008 if (buf == NULL) {
2009 goto fail;
2012 /* Write 1MB. */
2013 status = cli_writeall(cli,
2014 fnum,
2016 buf,
2018 buflen,
2019 NULL);
2021 if (!NT_STATUS_IS_OK(status)) {
2022 printf("write of %u to %s failed (%s)\n",
2023 (unsigned int)buflen,
2024 fname,
2025 nt_errstr(status));
2026 goto fail;
2029 status = check_size(cli, fnum, fname, buflen);
2030 if (!NT_STATUS_IS_OK(status)) {
2031 goto fail;
2034 /* Now ftruncate. */
2035 for ( i = 0; i < 10; i++) {
2036 status = cli_ftruncate(cli, fnum, i*1024);
2037 if (!NT_STATUS_IS_OK(status)) {
2038 printf("cli_ftruncate %u of %s failed (%s)\n",
2039 (unsigned int)i*1024,
2040 fname,
2041 nt_errstr(status));
2042 goto fail;
2044 status = check_size(cli, fnum, fname, i*1024);
2045 if (!NT_STATUS_IS_OK(status)) {
2046 goto fail;
2050 correct = true;
2052 fail:
2054 if (cli == NULL) {
2055 return false;
2058 if (fnum != (uint16_t)-1) {
2059 cli_close(cli, fnum);
2061 cli_setatr(cli, fname, 0, 0);
2062 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2064 if (!torture_close_connection(cli)) {
2065 correct = false;
2067 return correct;
2070 /* Ensure SMB2 flush on directories behaves correctly. */
2072 static bool test_dir_fsync(struct cli_state *cli, const char *path)
2074 NTSTATUS status;
2075 uint64_t fid_persistent, fid_volatile;
2076 uint8_t *dir_data = NULL;
2077 uint32_t dir_data_length = 0;
2079 /* Open directory - no write abilities. */
2080 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
2081 cli->smb2.tcon, path,
2082 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2083 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2084 SEC_STD_SYNCHRONIZE|
2085 SEC_DIR_LIST|
2086 SEC_DIR_READ_ATTRIBUTE, /* desired_access, */
2087 0, /* file_attributes, */
2088 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2089 FILE_OPEN, /* create_disposition, */
2090 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
2091 NULL, /* smb2_create_blobs *blobs */
2092 &fid_persistent,
2093 &fid_volatile,
2094 NULL, NULL, NULL);
2095 if (!NT_STATUS_IS_OK(status)) {
2096 printf("smb2cli_create '%s' (readonly) returned %s\n",
2097 path,
2098 nt_errstr(status));
2099 return false;
2102 status = smb2cli_query_directory(
2103 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
2104 1, 0, 0, fid_persistent, fid_volatile, "*", 0xffff,
2105 talloc_tos(), &dir_data, &dir_data_length);
2107 if (!NT_STATUS_IS_OK(status)) {
2108 printf("smb2cli_query_directory returned %s\n",
2109 nt_errstr(status));
2110 return false;
2113 /* Open directory no write access. Flush should fail. */
2115 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
2116 cli->smb2.tcon, fid_persistent, fid_volatile);
2117 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2118 printf("smb2cli_flush on a read-only directory returned %s\n",
2119 nt_errstr(status));
2120 return false;
2123 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
2124 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
2125 if (!NT_STATUS_IS_OK(status)) {
2126 printf("smb2cli_close returned %s\n", nt_errstr(status));
2127 return false;
2130 /* Open directory write-attributes only. Flush should still fail. */
2132 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
2133 cli->smb2.tcon, path,
2134 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2135 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2136 SEC_STD_SYNCHRONIZE|
2137 SEC_DIR_LIST|
2138 SEC_DIR_WRITE_ATTRIBUTE|
2139 SEC_DIR_READ_ATTRIBUTE, /* desired_access, */
2140 0, /* file_attributes, */
2141 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2142 FILE_OPEN, /* create_disposition, */
2143 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
2144 NULL, /* smb2_create_blobs *blobs */
2145 &fid_persistent,
2146 &fid_volatile,
2147 NULL, NULL, NULL);
2148 if (!NT_STATUS_IS_OK(status)) {
2149 printf("smb2cli_create '%s' (write attr) returned %s\n",
2150 path,
2151 nt_errstr(status));
2152 return false;
2155 status = smb2cli_query_directory(
2156 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
2157 1, 0, 0, fid_persistent, fid_volatile, "*", 0xffff,
2158 talloc_tos(), &dir_data, &dir_data_length);
2160 if (!NT_STATUS_IS_OK(status)) {
2161 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
2162 return false;
2165 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
2166 cli->smb2.tcon, fid_persistent, fid_volatile);
2167 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2168 printf("smb2cli_flush on a write-attributes directory "
2169 "returned %s\n",
2170 nt_errstr(status));
2171 return false;
2174 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
2175 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
2176 if (!NT_STATUS_IS_OK(status)) {
2177 printf("smb2cli_close returned %s\n", nt_errstr(status));
2178 return false;
2181 /* Open directory with SEC_DIR_ADD_FILE access. Flush should now succeed. */
2183 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
2184 cli->smb2.tcon, path,
2185 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2186 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2187 SEC_STD_SYNCHRONIZE|
2188 SEC_DIR_LIST|
2189 SEC_DIR_ADD_FILE, /* desired_access, */
2190 0, /* file_attributes, */
2191 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2192 FILE_OPEN, /* create_disposition, */
2193 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
2194 NULL, /* smb2_create_blobs *blobs */
2195 &fid_persistent,
2196 &fid_volatile,
2197 NULL, NULL, NULL);
2198 if (!NT_STATUS_IS_OK(status)) {
2199 printf("smb2cli_create '%s' (write FILE access) returned %s\n",
2200 path,
2201 nt_errstr(status));
2202 return false;
2205 status = smb2cli_query_directory(
2206 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
2207 1, 0, 0, fid_persistent, fid_volatile, "*", 0xffff,
2208 talloc_tos(), &dir_data, &dir_data_length);
2210 if (!NT_STATUS_IS_OK(status)) {
2211 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
2212 return false;
2215 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
2216 cli->smb2.tcon, fid_persistent, fid_volatile);
2217 if (!NT_STATUS_IS_OK(status)) {
2218 printf("smb2cli_flush on a directory returned %s\n",
2219 nt_errstr(status));
2220 return false;
2223 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
2224 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
2225 if (!NT_STATUS_IS_OK(status)) {
2226 printf("smb2cli_close returned %s\n", nt_errstr(status));
2227 return false;
2230 /* Open directory with SEC_DIR_ADD_FILE access. Flush should now succeed. */
2232 status = smb2cli_create(cli->conn, cli->timeout, cli->smb2.session,
2233 cli->smb2.tcon, path,
2234 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2235 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2236 SEC_STD_SYNCHRONIZE|
2237 SEC_DIR_LIST|
2238 SEC_DIR_ADD_SUBDIR, /* desired_access, */
2239 0, /* file_attributes, */
2240 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2241 FILE_OPEN, /* create_disposition, */
2242 FILE_SYNCHRONOUS_IO_NONALERT|FILE_DIRECTORY_FILE, /* create_options, */
2243 NULL, /* smb2_create_blobs *blobs */
2244 &fid_persistent,
2245 &fid_volatile,
2246 NULL, NULL, NULL);
2247 if (!NT_STATUS_IS_OK(status)) {
2248 printf("smb2cli_create '%s' (write DIR access) returned %s\n",
2249 path,
2250 nt_errstr(status));
2251 return false;
2254 status = smb2cli_query_directory(
2255 cli->conn, cli->timeout, cli->smb2.session, cli->smb2.tcon,
2256 1, 0, 0, fid_persistent, fid_volatile, "*", 0xffff,
2257 talloc_tos(), &dir_data, &dir_data_length);
2259 if (!NT_STATUS_IS_OK(status)) {
2260 printf("smb2cli_query_directory returned %s\n", nt_errstr(status));
2261 return false;
2264 status = smb2cli_flush(cli->conn, cli->timeout, cli->smb2.session,
2265 cli->smb2.tcon, fid_persistent, fid_volatile);
2266 if (!NT_STATUS_IS_OK(status)) {
2267 printf("smb2cli_flush on a directory returned %s\n",
2268 nt_errstr(status));
2269 return false;
2272 status = smb2cli_close(cli->conn, cli->timeout, cli->smb2.session,
2273 cli->smb2.tcon, 0, fid_persistent, fid_volatile);
2274 if (!NT_STATUS_IS_OK(status)) {
2275 printf("smb2cli_close returned %s\n", nt_errstr(status));
2276 return false;
2280 return true;
2283 bool run_smb2_dir_fsync(int dummy)
2285 struct cli_state *cli = NULL;
2286 NTSTATUS status;
2287 bool bret = false;
2288 const char *dname = "fsync_test_dir";
2290 printf("Starting SMB2-DIR-FSYNC\n");
2292 if (!torture_init_connection(&cli)) {
2293 return false;
2296 status = smbXcli_negprot(cli->conn, cli->timeout,
2297 PROTOCOL_SMB2_02, PROTOCOL_SMB2_02);
2298 if (!NT_STATUS_IS_OK(status)) {
2299 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
2300 return false;
2303 status = cli_session_setup_creds(cli, torture_creds);
2304 if (!NT_STATUS_IS_OK(status)) {
2305 printf("cli_session_setup returned %s\n", nt_errstr(status));
2306 return false;
2309 status = cli_tree_connect(cli, share, "?????", NULL);
2310 if (!NT_STATUS_IS_OK(status)) {
2311 printf("cli_tree_connect returned %s\n", nt_errstr(status));
2312 return false;
2315 (void)cli_rmdir(cli, dname);
2316 status = cli_mkdir(cli, dname);
2317 if (!NT_STATUS_IS_OK(status)) {
2318 printf("cli_mkdir(%s) returned %s\n",
2319 dname,
2320 nt_errstr(status));
2321 return false;
2324 /* Test on a subdirectory. */
2325 bret = test_dir_fsync(cli, dname);
2326 if (bret == false) {
2327 (void)cli_rmdir(cli, dname);
2328 return false;
2330 (void)cli_rmdir(cli, dname);
2332 /* Test on the root handle of a share. */
2333 bret = test_dir_fsync(cli, "");
2334 if (bret == false) {
2335 return false;
2337 return true;
2340 bool run_smb2_path_slash(int dummy)
2342 struct cli_state *cli = NULL;
2343 NTSTATUS status;
2344 uint64_t fid_persistent;
2345 uint64_t fid_volatile;
2346 const char *dname_noslash = "smb2_dir_slash";
2347 const char *dname_backslash = "smb2_dir_slash\\";
2348 const char *dname_slash = "smb2_dir_slash/";
2349 const char *fname_noslash = "smb2_file_slash";
2350 const char *fname_backslash = "smb2_file_slash\\";
2351 const char *fname_slash = "smb2_file_slash/";
2353 printf("Starting SMB2-PATH-SLASH\n");
2355 if (!torture_init_connection(&cli)) {
2356 return false;
2359 status = smbXcli_negprot(cli->conn, cli->timeout,
2360 PROTOCOL_SMB2_02, PROTOCOL_SMB2_02);
2361 if (!NT_STATUS_IS_OK(status)) {
2362 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
2363 return false;
2366 status = cli_session_setup_creds(cli, torture_creds);
2367 if (!NT_STATUS_IS_OK(status)) {
2368 printf("cli_session_setup returned %s\n", nt_errstr(status));
2369 return false;
2372 status = cli_tree_connect(cli, share, "?????", NULL);
2373 if (!NT_STATUS_IS_OK(status)) {
2374 printf("cli_tree_connect returned %s\n", nt_errstr(status));
2375 return false;
2378 (void)cli_unlink(cli, dname_noslash, 0);
2379 (void)cli_rmdir(cli, dname_noslash);
2380 (void)cli_unlink(cli, fname_noslash, 0);
2381 (void)cli_rmdir(cli, fname_noslash);
2383 /* Try to create a directory with the backslash name. */
2384 status = smb2cli_create(cli->conn,
2385 cli->timeout,
2386 cli->smb2.session,
2387 cli->smb2.tcon,
2388 dname_backslash,
2389 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2390 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2391 FILE_READ_DATA|FILE_READ_ATTRIBUTES, /* desired_access, */
2392 0, /* file_attributes, */
2393 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2394 FILE_CREATE, /* create_disposition, */
2395 FILE_DIRECTORY_FILE, /* create_options, */
2396 NULL, /* smb2_create_blobs *blobs */
2397 &fid_persistent,
2398 &fid_volatile,
2399 NULL, NULL, NULL);
2401 /* directory ending in '\\' should be success. */
2403 if (!NT_STATUS_IS_OK(status)) {
2404 printf("smb2cli_create '%s' returned %s - "
2405 "should be NT_STATUS_OK\n",
2406 dname_backslash,
2407 nt_errstr(status));
2408 return false;
2410 status = smb2cli_close(cli->conn,
2411 cli->timeout,
2412 cli->smb2.session,
2413 cli->smb2.tcon,
2415 fid_persistent,
2416 fid_volatile);
2417 if (!NT_STATUS_IS_OK(status)) {
2418 printf("smb2cli_close returned %s\n", nt_errstr(status));
2419 return false;
2422 (void)cli_rmdir(cli, dname_noslash);
2424 /* Try to create a directory with the slash name. */
2425 status = smb2cli_create(cli->conn,
2426 cli->timeout,
2427 cli->smb2.session,
2428 cli->smb2.tcon,
2429 dname_slash,
2430 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2431 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2432 FILE_READ_DATA|FILE_READ_ATTRIBUTES, /* desired_access, */
2433 0, /* file_attributes, */
2434 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2435 FILE_CREATE, /* create_disposition, */
2436 FILE_DIRECTORY_FILE, /* create_options, */
2437 NULL, /* smb2_create_blobs *blobs */
2438 &fid_persistent,
2439 &fid_volatile,
2440 NULL, NULL, NULL);
2442 /* directory ending in '/' is an error. */
2443 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_INVALID)) {
2444 printf("smb2cli_create '%s' returned %s - "
2445 "should be NT_STATUS_OBJECT_NAME_INVALID\n",
2446 dname_slash,
2447 nt_errstr(status));
2448 if (NT_STATUS_IS_OK(status)) {
2449 (void)smb2cli_close(cli->conn,
2450 cli->timeout,
2451 cli->smb2.session,
2452 cli->smb2.tcon,
2454 fid_persistent,
2455 fid_volatile);
2457 (void)cli_rmdir(cli, dname_noslash);
2458 return false;
2461 (void)cli_rmdir(cli, dname_noslash);
2463 /* Try to create a file with the backslash name. */
2464 status = smb2cli_create(cli->conn,
2465 cli->timeout,
2466 cli->smb2.session,
2467 cli->smb2.tcon,
2468 fname_backslash,
2469 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2470 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2471 FILE_READ_DATA|FILE_READ_ATTRIBUTES, /* desired_access, */
2472 0, /* file_attributes, */
2473 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2474 FILE_CREATE, /* create_disposition, */
2475 FILE_NON_DIRECTORY_FILE, /* create_options, */
2476 NULL, /* smb2_create_blobs *blobs */
2477 &fid_persistent,
2478 &fid_volatile,
2479 NULL, NULL, NULL);
2481 /* file ending in '\\' should be error. */
2483 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_INVALID)) {
2484 printf("smb2cli_create '%s' returned %s - "
2485 "should be NT_STATUS_OBJECT_NAME_INVALID\n",
2486 fname_backslash,
2487 nt_errstr(status));
2488 if (NT_STATUS_IS_OK(status)) {
2489 (void)smb2cli_close(cli->conn,
2490 cli->timeout,
2491 cli->smb2.session,
2492 cli->smb2.tcon,
2494 fid_persistent,
2495 fid_volatile);
2497 (void)cli_unlink(cli, fname_noslash, 0);
2498 return false;
2501 (void)cli_unlink(cli, fname_noslash, 0);
2503 /* Try to create a file with the slash name. */
2504 status = smb2cli_create(cli->conn,
2505 cli->timeout,
2506 cli->smb2.session,
2507 cli->smb2.tcon,
2508 fname_slash,
2509 SMB2_OPLOCK_LEVEL_NONE, /* oplock_level, */
2510 SMB2_IMPERSONATION_IMPERSONATION, /* impersonation_level, */
2511 FILE_READ_DATA|FILE_READ_ATTRIBUTES, /* desired_access, */
2512 0, /* file_attributes, */
2513 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE, /* share_access, */
2514 FILE_CREATE, /* create_disposition, */
2515 FILE_NON_DIRECTORY_FILE, /* create_options, */
2516 NULL, /* smb2_create_blobs *blobs */
2517 &fid_persistent,
2518 &fid_volatile,
2519 NULL, NULL, NULL);
2521 /* file ending in '/' should be error. */
2523 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_INVALID)) {
2524 printf("smb2cli_create '%s' returned %s - "
2525 "should be NT_STATUS_OBJECT_NAME_INVALID\n",
2526 fname_slash,
2527 nt_errstr(status));
2528 if (NT_STATUS_IS_OK(status)) {
2529 (void)smb2cli_close(cli->conn,
2530 cli->timeout,
2531 cli->smb2.session,
2532 cli->smb2.tcon,
2534 fid_persistent,
2535 fid_volatile);
2537 (void)cli_unlink(cli, fname_noslash, 0);
2538 return false;
2541 (void)cli_unlink(cli, fname_noslash, 0);
2542 return true;
2546 * NB. This can only work against a server where
2547 * the connecting user has been granted SeSecurityPrivilege.
2549 * 1). Create a test file.
2550 * 2). Open with SEC_FLAG_SYSTEM_SECURITY *only*. ACCESS_DENIED -
2551 * NB. SMB2-only behavior.
2552 * 3). Open with SEC_FLAG_SYSTEM_SECURITY|FILE_WRITE_ATTRIBUTES.
2553 * 4). Write SACL. Should fail with ACCESS_DENIED (seems to need WRITE_DAC).
2554 * 5). Close (3).
2555 * 6). Open with SEC_FLAG_SYSTEM_SECURITY|SEC_STD_WRITE_DAC.
2556 * 7). Write SACL. Success.
2557 * 8). Close (4).
2558 * 9). Open with SEC_FLAG_SYSTEM_SECURITY|READ_ATTRIBUTES.
2559 * 10). Read SACL. Success.
2560 * 11). Read DACL. Should fail with ACCESS_DENIED (no READ_CONTROL).
2561 * 12). Close (9).
2564 bool run_smb2_sacl(int dummy)
2566 struct cli_state *cli = NULL;
2567 NTSTATUS status;
2568 struct security_descriptor *sd_dacl = NULL;
2569 struct security_descriptor *sd_sacl = NULL;
2570 const char *fname = "sacl_test_file";
2571 uint16_t fnum = (uint16_t)-1;
2573 printf("Starting SMB2-SACL\n");
2575 if (!torture_init_connection(&cli)) {
2576 return false;
2579 status = smbXcli_negprot(cli->conn,
2580 cli->timeout,
2581 PROTOCOL_SMB2_02,
2582 PROTOCOL_SMB3_11);
2583 if (!NT_STATUS_IS_OK(status)) {
2584 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
2585 return false;
2588 status = cli_session_setup_creds(cli, torture_creds);
2589 if (!NT_STATUS_IS_OK(status)) {
2590 printf("cli_session_setup returned %s\n", nt_errstr(status));
2591 return false;
2594 status = cli_tree_connect(cli, share, "?????", NULL);
2595 if (!NT_STATUS_IS_OK(status)) {
2596 printf("cli_tree_connect returned %s\n", nt_errstr(status));
2597 return false;
2600 (void)cli_unlink(cli, fname, 0);
2602 /* First create a file. */
2603 status = cli_ntcreate(cli,
2604 fname,
2606 GENERIC_ALL_ACCESS,
2607 FILE_ATTRIBUTE_NORMAL,
2608 FILE_SHARE_NONE,
2609 FILE_CREATE,
2612 &fnum,
2613 NULL);
2615 if (!NT_STATUS_IS_OK(status)) {
2616 printf("Create of %s failed (%s)\n",
2617 fname,
2618 nt_errstr(status));
2619 goto fail;
2622 cli_close(cli, fnum);
2623 fnum = (uint16_t)-1;
2626 * Now try to open with *only* SEC_FLAG_SYSTEM_SECURITY.
2627 * This should fail with NT_STATUS_ACCESS_DENIED - but
2628 * only against an SMB2 server. SMB1 allows this as tested
2629 * in SMB1-SYSTEM-SECURITY.
2632 status = cli_smb2_create_fnum(cli,
2633 fname,
2634 SMB2_OPLOCK_LEVEL_NONE,
2635 SMB2_IMPERSONATION_IMPERSONATION,
2636 SEC_FLAG_SYSTEM_SECURITY, /* desired access */
2637 0, /* file_attributes, */
2638 FILE_SHARE_READ|
2639 FILE_SHARE_WRITE|
2640 FILE_SHARE_DELETE, /* share_access, */
2641 FILE_OPEN, /* create_disposition, */
2642 FILE_NON_DIRECTORY_FILE, /* create_options, */
2643 NULL, /* in_cblobs. */
2644 &fnum, /* fnum */
2645 NULL, /* smb_create_returns */
2646 talloc_tos(), /* mem_ctx */
2647 NULL); /* out_cblobs */
2649 if (NT_STATUS_EQUAL(status, NT_STATUS_PRIVILEGE_NOT_HELD)) {
2650 printf("SMB2-SACL-TEST can only work with a user "
2651 "who has been granted SeSecurityPrivilege.\n"
2652 "This is the "
2653 "\"Manage auditing and security log\""
2654 "privilege setting on Windows\n");
2655 goto fail;
2658 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2659 printf("open file %s with SEC_FLAG_SYSTEM_SECURITY only: "
2660 "got %s - should fail with ACCESS_DENIED\n",
2661 fname,
2662 nt_errstr(status));
2663 goto fail;
2667 * Open with SEC_FLAG_SYSTEM_SECURITY|FILE_WRITE_ATTRIBUTES.
2670 status = cli_smb2_create_fnum(cli,
2671 fname,
2672 SMB2_OPLOCK_LEVEL_NONE,
2673 SMB2_IMPERSONATION_IMPERSONATION,
2674 SEC_FLAG_SYSTEM_SECURITY|
2675 FILE_WRITE_ATTRIBUTES, /* desired access */
2676 0, /* file_attributes, */
2677 FILE_SHARE_READ|
2678 FILE_SHARE_WRITE|
2679 FILE_SHARE_DELETE, /* share_access, */
2680 FILE_OPEN, /* create_disposition, */
2681 FILE_NON_DIRECTORY_FILE, /* create_options, */
2682 NULL, /* in_cblobs. */
2683 &fnum, /* fnum */
2684 NULL, /* smb_create_returns */
2685 talloc_tos(), /* mem_ctx */
2686 NULL); /* out_cblobs */
2688 if (!NT_STATUS_IS_OK(status)) {
2689 printf("Open of %s with (SEC_FLAG_SYSTEM_SECURITY|"
2690 "FILE_WRITE_ATTRIBUTES) failed (%s)\n",
2691 fname,
2692 nt_errstr(status));
2693 goto fail;
2696 /* Create an SD with a SACL. */
2697 sd_sacl = security_descriptor_sacl_create(talloc_tos(),
2699 NULL, /* owner. */
2700 NULL, /* group. */
2701 /* first ACE. */
2702 SID_WORLD,
2703 SEC_ACE_TYPE_SYSTEM_AUDIT,
2704 SEC_GENERIC_ALL,
2705 SEC_ACE_FLAG_FAILED_ACCESS,
2706 NULL);
2708 if (sd_sacl == NULL) {
2709 printf("Out of memory creating SACL\n");
2710 goto fail;
2714 * Write the SACL SD. This should fail
2715 * even though we have SEC_FLAG_SYSTEM_SECURITY,
2716 * as it seems to also need WRITE_DAC access.
2718 status = cli_set_security_descriptor(cli,
2719 fnum,
2720 SECINFO_DACL|SECINFO_SACL,
2721 sd_sacl);
2723 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2724 printf("Writing SACL on file %s got (%s) "
2725 "should have failed with ACCESS_DENIED.\n",
2726 fname,
2727 nt_errstr(status));
2728 goto fail;
2731 /* And close. */
2732 cli_smb2_close_fnum(cli, fnum);
2733 fnum = (uint16_t)-1;
2736 * Open with SEC_FLAG_SYSTEM_SECURITY|SEC_STD_WRITE_DAC.
2739 status = cli_smb2_create_fnum(cli,
2740 fname,
2741 SMB2_OPLOCK_LEVEL_NONE,
2742 SMB2_IMPERSONATION_IMPERSONATION,
2743 SEC_FLAG_SYSTEM_SECURITY|
2744 SEC_STD_WRITE_DAC, /* desired access */
2745 0, /* file_attributes, */
2746 FILE_SHARE_READ|
2747 FILE_SHARE_WRITE|
2748 FILE_SHARE_DELETE, /* share_access, */
2749 FILE_OPEN, /* create_disposition, */
2750 FILE_NON_DIRECTORY_FILE, /* create_options, */
2751 NULL, /* in_cblobs. */
2752 &fnum, /* fnum */
2753 NULL, /* smb_create_returns */
2754 talloc_tos(), /* mem_ctx */
2755 NULL); /* out_cblobs */
2757 if (!NT_STATUS_IS_OK(status)) {
2758 printf("Open of %s with (SEC_FLAG_SYSTEM_SECURITY|"
2759 "FILE_WRITE_ATTRIBUTES) failed (%s)\n",
2760 fname,
2761 nt_errstr(status));
2762 goto fail;
2766 * Write the SACL SD. This should now succeed
2767 * as we have both SEC_FLAG_SYSTEM_SECURITY
2768 * and WRITE_DAC access.
2770 status = cli_set_security_descriptor(cli,
2771 fnum,
2772 SECINFO_DACL|SECINFO_SACL,
2773 sd_sacl);
2775 if (!NT_STATUS_IS_OK(status)) {
2776 printf("cli_set_security_descriptor SACL "
2777 "on file %s failed (%s)\n",
2778 fname,
2779 nt_errstr(status));
2780 goto fail;
2783 /* And close. */
2784 cli_smb2_close_fnum(cli, fnum);
2785 fnum = (uint16_t)-1;
2787 /* We're done with the sacl we made. */
2788 TALLOC_FREE(sd_sacl);
2791 * Now try to open with SEC_FLAG_SYSTEM_SECURITY|READ_ATTRIBUTES.
2792 * This gives us access to the SACL.
2795 status = cli_smb2_create_fnum(cli,
2796 fname,
2797 SMB2_OPLOCK_LEVEL_NONE,
2798 SMB2_IMPERSONATION_IMPERSONATION,
2799 SEC_FLAG_SYSTEM_SECURITY|
2800 FILE_READ_ATTRIBUTES, /* desired access */
2801 0, /* file_attributes, */
2802 FILE_SHARE_READ|
2803 FILE_SHARE_WRITE|
2804 FILE_SHARE_DELETE, /* share_access, */
2805 FILE_OPEN, /* create_disposition, */
2806 FILE_NON_DIRECTORY_FILE, /* create_options, */
2807 NULL, /* in_cblobs. */
2808 &fnum, /* fnum */
2809 NULL, /* smb_create_returns */
2810 talloc_tos(), /* mem_ctx */
2811 NULL); /* out_cblobs */
2813 if (!NT_STATUS_IS_OK(status)) {
2814 printf("Open of %s with (SEC_FLAG_SYSTEM_SECURITY|"
2815 "FILE_READ_ATTRIBUTES) failed (%s)\n",
2816 fname,
2817 nt_errstr(status));
2818 goto fail;
2821 /* Try and read the SACL - should succeed. */
2822 status = cli_query_security_descriptor(
2823 cli, fnum, SECINFO_SACL, talloc_tos(), &sd_sacl);
2825 if (!NT_STATUS_IS_OK(status)) {
2826 printf("Read SACL from file %s failed (%s)\n",
2827 fname,
2828 nt_errstr(status));
2829 goto fail;
2832 TALLOC_FREE(sd_sacl);
2835 * Try and read the DACL - should fail as we have
2836 * no READ_DAC access.
2838 status = cli_query_security_descriptor(
2839 cli, fnum, SECINFO_DACL, talloc_tos(), &sd_sacl);
2841 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
2842 printf("Reading DACL on file %s got (%s) "
2843 "should have failed with ACCESS_DENIED.\n",
2844 fname,
2845 nt_errstr(status));
2846 goto fail;
2849 if (fnum != (uint16_t)-1) {
2850 cli_smb2_close_fnum(cli, fnum);
2851 fnum = (uint16_t)-1;
2854 TALLOC_FREE(sd_dacl);
2855 TALLOC_FREE(sd_sacl);
2857 (void)cli_unlink(cli, fname, 0);
2858 return true;
2860 fail:
2862 TALLOC_FREE(sd_dacl);
2863 TALLOC_FREE(sd_sacl);
2865 if (fnum != (uint16_t)-1) {
2866 cli_smb2_close_fnum(cli, fnum);
2867 fnum = (uint16_t)-1;
2870 (void)cli_unlink(cli, fname, 0);
2871 return false;
2874 bool run_smb2_quota1(int dummy)
2876 struct cli_state *cli = NULL;
2877 NTSTATUS status;
2878 uint16_t fnum = (uint16_t)-1;
2879 SMB_NTQUOTA_STRUCT qt = {0};
2881 printf("Starting SMB2-QUOTA1\n");
2883 if (!torture_init_connection(&cli)) {
2884 return false;
2887 status = smbXcli_negprot(cli->conn,
2888 cli->timeout,
2889 PROTOCOL_SMB2_02,
2890 PROTOCOL_SMB3_11);
2891 if (!NT_STATUS_IS_OK(status)) {
2892 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
2893 return false;
2896 status = cli_session_setup_creds(cli, torture_creds);
2897 if (!NT_STATUS_IS_OK(status)) {
2898 printf("cli_session_setup returned %s\n", nt_errstr(status));
2899 return false;
2902 status = cli_tree_connect(cli, share, "?????", NULL);
2903 if (!NT_STATUS_IS_OK(status)) {
2904 printf("cli_tree_connect returned %s\n", nt_errstr(status));
2905 return false;
2908 status = cli_smb2_create_fnum(
2909 cli,
2910 "\\",
2911 SMB2_OPLOCK_LEVEL_NONE,
2912 SMB2_IMPERSONATION_IMPERSONATION,
2913 SEC_GENERIC_READ, /* desired access */
2914 0, /* file_attributes, */
2915 FILE_SHARE_READ|
2916 FILE_SHARE_WRITE|
2917 FILE_SHARE_DELETE, /* share_access, */
2918 FILE_OPEN, /* create_disposition, */
2919 FILE_DIRECTORY_FILE, /* create_options, */
2920 NULL, /* in_cblobs. */
2921 &fnum, /* fnum */
2922 NULL, /* smb_create_returns */
2923 NULL, /* mem_ctx */
2924 NULL); /* out_cblobs */
2925 if (!NT_STATUS_IS_OK(status)) {
2926 printf("cli_smb2_create_fnum failed: %s\n", nt_errstr(status));
2927 return false;
2930 status = cli_smb2_get_user_quota(cli, fnum, &qt);
2931 if (!NT_STATUS_EQUAL(status, NT_STATUS_INVALID_HANDLE)) {
2932 printf("cli_smb2_get_user_quota returned %s, expected "
2933 "NT_STATUS_INVALID_HANDLE\n",
2934 nt_errstr(status));
2935 return false;
2938 return true;
2941 bool run_smb2_stream_acl(int dummy)
2943 struct cli_state *cli = NULL;
2944 NTSTATUS status;
2945 uint16_t fnum = (uint16_t)-1;
2946 const char *fname = "stream_acl_test_file";
2947 const char *sname = "stream_acl_test_file:streamname";
2948 struct security_descriptor *sd_dacl = NULL;
2949 bool ret = false;
2951 printf("SMB2 stream acl\n");
2953 if (!torture_init_connection(&cli)) {
2954 return false;
2957 status = smbXcli_negprot(cli->conn,
2958 cli->timeout,
2959 PROTOCOL_SMB2_02,
2960 PROTOCOL_SMB3_11);
2961 if (!NT_STATUS_IS_OK(status)) {
2962 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
2963 return false;
2966 status = cli_session_setup_creds(cli, torture_creds);
2967 if (!NT_STATUS_IS_OK(status)) {
2968 printf("cli_session_setup returned %s\n", nt_errstr(status));
2969 return false;
2972 status = cli_tree_connect(cli, share, "?????", NULL);
2973 if (!NT_STATUS_IS_OK(status)) {
2974 printf("cli_tree_connect returned %s\n", nt_errstr(status));
2975 return false;
2978 /* Ensure file doesn't exist. */
2979 (void)cli_unlink(cli, fname, 0);
2981 /* Create the file. */
2982 status = cli_ntcreate(cli,
2983 fname,
2985 GENERIC_ALL_ACCESS,
2986 FILE_ATTRIBUTE_NORMAL,
2987 FILE_SHARE_NONE,
2988 FILE_CREATE,
2991 &fnum,
2992 NULL);
2994 if (!NT_STATUS_IS_OK(status)) {
2995 printf("Create of %s failed (%s)\n",
2996 fname,
2997 nt_errstr(status));
2998 goto fail;
3001 /* Close the handle. */
3002 cli_smb2_close_fnum(cli, fnum);
3003 fnum = (uint16_t)-1;
3005 /* Create the stream. */
3006 status = cli_ntcreate(cli,
3007 sname,
3009 FILE_READ_DATA|
3010 SEC_STD_READ_CONTROL|
3011 SEC_STD_WRITE_DAC,
3012 FILE_ATTRIBUTE_NORMAL,
3013 FILE_SHARE_NONE,
3014 FILE_CREATE,
3017 &fnum,
3018 NULL);
3020 if (!NT_STATUS_IS_OK(status)) {
3021 printf("Create of %s failed (%s)\n",
3022 sname,
3023 nt_errstr(status));
3024 goto fail;
3027 /* Close the handle. */
3028 cli_smb2_close_fnum(cli, fnum);
3029 fnum = (uint16_t)-1;
3032 * Open the stream - for Samba this ensures
3033 * we prove we have a pathref fsp.
3035 status = cli_ntcreate(cli,
3036 sname,
3038 FILE_READ_DATA|
3039 SEC_STD_READ_CONTROL|
3040 SEC_STD_WRITE_DAC,
3041 FILE_ATTRIBUTE_NORMAL,
3042 FILE_SHARE_NONE,
3043 FILE_OPEN,
3046 &fnum,
3047 NULL);
3049 if (!NT_STATUS_IS_OK(status)) {
3050 printf("Open of %s failed (%s)\n",
3051 sname,
3052 nt_errstr(status));
3053 goto fail;
3056 /* Read the security descriptor off the stream handle. */
3057 status = cli_query_security_descriptor(cli,
3058 fnum,
3059 SECINFO_DACL,
3060 talloc_tos(),
3061 &sd_dacl);
3063 if (!NT_STATUS_IS_OK(status)) {
3064 printf("Reading DACL on stream %s got (%s)\n",
3065 sname,
3066 nt_errstr(status));
3067 goto fail;
3070 if (sd_dacl == NULL || sd_dacl->dacl == NULL ||
3071 sd_dacl->dacl->num_aces < 1) {
3072 printf("Invalid DACL returned on stream %s "
3073 "(this should not happen)\n",
3074 sname);
3075 goto fail;
3079 * Ensure it allows FILE_READ_DATA in the first ace.
3080 * It always should.
3082 if ((sd_dacl->dacl->aces[0].access_mask & FILE_READ_DATA) == 0) {
3083 printf("DACL->ace[0] returned on stream %s "
3084 "doesn't have read access (should not happen)\n",
3085 sname);
3086 goto fail;
3089 /* Remove FILE_READ_DATA from the first ace and set. */
3090 sd_dacl->dacl->aces[0].access_mask &= ~FILE_READ_DATA;
3092 status = cli_set_security_descriptor(cli,
3093 fnum,
3094 SECINFO_DACL,
3095 sd_dacl);
3097 if (!NT_STATUS_IS_OK(status)) {
3098 printf("Setting DACL on stream %s got (%s)\n",
3099 sname,
3100 nt_errstr(status));
3101 goto fail;
3104 TALLOC_FREE(sd_dacl);
3106 /* Read again and check it changed. */
3107 status = cli_query_security_descriptor(cli,
3108 fnum,
3109 SECINFO_DACL,
3110 talloc_tos(),
3111 &sd_dacl);
3113 if (!NT_STATUS_IS_OK(status)) {
3114 printf("Reading DACL on stream %s got (%s)\n",
3115 sname,
3116 nt_errstr(status));
3117 goto fail;
3120 if (sd_dacl == NULL || sd_dacl->dacl == NULL ||
3121 sd_dacl->dacl->num_aces < 1) {
3122 printf("Invalid DACL (1) returned on stream %s "
3123 "(this should not happen)\n",
3124 sname);
3125 goto fail;
3128 /* FILE_READ_DATA should be gone from the first ace. */
3129 if ((sd_dacl->dacl->aces[0].access_mask & FILE_READ_DATA) != 0) {
3130 printf("DACL on stream %s did not change\n",
3131 sname);
3132 goto fail;
3135 ret = true;
3137 fail:
3139 if (fnum != (uint16_t)-1) {
3140 cli_smb2_close_fnum(cli, fnum);
3141 fnum = (uint16_t)-1;
3144 (void)cli_unlink(cli, fname, 0);
3145 return ret;
3148 static NTSTATUS list_fn(struct file_info *finfo,
3149 const char *name,
3150 void *state)
3152 bool *matched = (bool *)state;
3153 if (finfo->attr & FILE_ATTRIBUTE_DIRECTORY) {
3154 *matched = true;
3156 return NT_STATUS_OK;
3160 * Must be run against a share with "smbd async dosmode = yes".
3161 * Checks we can return DOS attriutes other than "N".
3162 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=14758
3165 bool run_list_dir_async_test(int dummy)
3167 struct cli_state *cli = NULL;
3168 NTSTATUS status;
3169 const char *dname = "ASYNC_DIR";
3170 bool ret = false;
3171 bool matched = false;
3173 printf("SMB2 list dir async\n");
3175 if (!torture_init_connection(&cli)) {
3176 return false;
3179 status = smbXcli_negprot(cli->conn,
3180 cli->timeout,
3181 PROTOCOL_SMB2_02,
3182 PROTOCOL_SMB3_11);
3183 if (!NT_STATUS_IS_OK(status)) {
3184 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
3185 return false;
3188 status = cli_session_setup_creds(cli, torture_creds);
3189 if (!NT_STATUS_IS_OK(status)) {
3190 printf("cli_session_setup returned %s\n", nt_errstr(status));
3191 return false;
3194 status = cli_tree_connect(cli, share, "?????", NULL);
3195 if (!NT_STATUS_IS_OK(status)) {
3196 printf("cli_tree_connect returned %s\n", nt_errstr(status));
3197 return false;
3200 /* Ensure directory doesn't exist. */
3201 (void)cli_rmdir(cli, dname);
3203 status = cli_mkdir(cli, dname);
3204 if (!NT_STATUS_IS_OK(status)) {
3205 printf("cli_mkdir %s returned %s\n", dname, nt_errstr(status));
3206 return false;
3209 status = cli_list(cli,
3210 dname,
3211 FILE_ATTRIBUTE_NORMAL|FILE_ATTRIBUTE_DIRECTORY,
3212 list_fn,
3213 &matched);
3214 if (!NT_STATUS_IS_OK(status)) {
3215 printf("cli_list %s returned %s\n", dname, nt_errstr(status));
3216 goto fail;
3219 if (!matched) {
3220 printf("Failed to find %s\n", dname);
3221 goto fail;
3224 ret = true;
3226 fail:
3228 (void)cli_rmdir(cli, dname);
3229 return ret;
3233 * Test delete a directory fails if a file is created
3234 * in a directory after the delete on close is set.
3235 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=14892
3238 bool run_delete_on_close_non_empty(int dummy)
3240 struct cli_state *cli = NULL;
3241 NTSTATUS status;
3242 const char *dname = "DEL_ON_CLOSE_DIR";
3243 const char *fname = "DEL_ON_CLOSE_DIR\\testfile";
3244 uint16_t fnum = (uint16_t)-1;
3245 uint16_t fnum1 = (uint16_t)-1;
3246 bool ret = false;
3248 printf("SMB2 delete on close nonempty\n");
3250 if (!torture_init_connection(&cli)) {
3251 return false;
3254 status = smbXcli_negprot(cli->conn,
3255 cli->timeout,
3256 PROTOCOL_SMB2_02,
3257 PROTOCOL_SMB3_11);
3258 if (!NT_STATUS_IS_OK(status)) {
3259 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
3260 return false;
3263 status = cli_session_setup_creds(cli, torture_creds);
3264 if (!NT_STATUS_IS_OK(status)) {
3265 printf("cli_session_setup returned %s\n", nt_errstr(status));
3266 return false;
3269 status = cli_tree_connect(cli, share, "?????", NULL);
3270 if (!NT_STATUS_IS_OK(status)) {
3271 printf("cli_tree_connect returned %s\n", nt_errstr(status));
3272 return false;
3275 /* Ensure directory doesn't exist. */
3276 (void)cli_unlink(cli,
3277 fname,
3278 FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3279 (void)cli_rmdir(cli, dname);
3281 /* Create target directory. */
3282 status = cli_ntcreate(cli,
3283 dname,
3285 DELETE_ACCESS|FILE_READ_DATA,
3286 FILE_ATTRIBUTE_DIRECTORY,
3287 FILE_SHARE_READ|
3288 FILE_SHARE_WRITE|
3289 FILE_SHARE_DELETE,
3290 FILE_CREATE,
3291 FILE_DIRECTORY_FILE,
3293 &fnum,
3294 NULL);
3295 if (!NT_STATUS_IS_OK(status)) {
3296 printf("cli_ntcreate for directory %s returned %s\n",
3297 dname,
3298 nt_errstr(status));
3299 goto out;
3302 /* Now set the delete on close bit. */
3303 status = cli_nt_delete_on_close(cli, fnum, 1);
3304 if (!NT_STATUS_IS_OK(status)) {
3305 printf("cli_cli_nt_delete_on_close set for directory "
3306 "%s returned %s\n",
3307 dname,
3308 nt_errstr(status));
3309 goto out;
3312 /* Create file inside target directory. */
3314 * NB. On Windows this will return NT_STATUS_DELETE_PENDING. Only on
3315 * Samba will this succeed by default (the option "check parent
3316 * directory delete on close" configures behaviour), but we're using
3317 * this to test a race condition.
3319 status = cli_ntcreate(cli,
3320 fname,
3322 FILE_READ_DATA,
3323 FILE_ATTRIBUTE_NORMAL,
3324 FILE_SHARE_READ|
3325 FILE_SHARE_WRITE|
3326 FILE_SHARE_DELETE,
3327 FILE_CREATE,
3330 &fnum1,
3331 NULL);
3332 if (!NT_STATUS_IS_OK(status)) {
3333 printf("cli_ntcreate for file %s returned %s\n",
3334 fname,
3335 nt_errstr(status));
3336 goto out;
3338 cli_close(cli, fnum1);
3339 fnum1 = (uint16_t)-1;
3341 /* Now the close should fail. */
3342 status = cli_close(cli, fnum);
3343 if (!NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
3344 printf("cli_close for directory %s returned %s\n",
3345 dname,
3346 nt_errstr(status));
3347 goto out;
3350 ret = true;
3352 out:
3354 if (fnum1 != (uint16_t)-1) {
3355 cli_close(cli, fnum1);
3357 if (fnum != (uint16_t)-1) {
3358 cli_nt_delete_on_close(cli, fnum, 0);
3359 cli_close(cli, fnum);
3361 (void)cli_unlink(cli,
3362 fname,
3363 FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3364 (void)cli_rmdir(cli, dname);
3365 return ret;
3368 static NTSTATUS check_empty_fn(struct file_info *finfo,
3369 const char *mask,
3370 void *private_data)
3372 unsigned int *pcount = (unsigned int *)private_data;
3374 if (ISDOT(finfo->name) || ISDOTDOT(finfo->name)) {
3375 (*pcount)++;
3376 return NT_STATUS_OK;
3378 return NT_STATUS_DIRECTORY_NOT_EMPTY;
3382 * Test setting the delete on close bit on a directory
3383 * containing an unwritable file fails or succeeds
3384 * an a share set with "hide unwritable = yes"
3385 * depending on the setting of "delete veto files".
3386 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=15023
3388 * First version. With "delete veto files = yes"
3389 * setting the delete on close should succeed.
3392 bool run_delete_on_close_nonwrite_delete_yes_test(int dummy)
3394 struct cli_state *cli = NULL;
3395 NTSTATUS status;
3396 const char *dname = "delete_veto_yes";
3397 const char *list_dname = "delete_veto_yes\\*";
3398 uint16_t fnum = (uint16_t)-1;
3399 bool ret = false;
3400 unsigned int list_count = 0;
3402 printf("SMB2 delete on close nonwrite - delete veto yes\n");
3404 if (!torture_init_connection(&cli)) {
3405 return false;
3408 status = smbXcli_negprot(cli->conn,
3409 cli->timeout,
3410 PROTOCOL_SMB2_02,
3411 PROTOCOL_SMB3_11);
3412 if (!NT_STATUS_IS_OK(status)) {
3413 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
3414 return false;
3417 status = cli_session_setup_creds(cli, torture_creds);
3418 if (!NT_STATUS_IS_OK(status)) {
3419 printf("cli_session_setup returned %s\n", nt_errstr(status));
3420 return false;
3423 status = cli_tree_connect(cli, share, "?????", NULL);
3424 if (!NT_STATUS_IS_OK(status)) {
3425 printf("cli_tree_connect returned %s\n", nt_errstr(status));
3426 return false;
3429 /* Ensure target directory is seen as empty. */
3430 status = cli_list(cli,
3431 list_dname,
3432 FILE_ATTRIBUTE_DIRECTORY |
3433 FILE_ATTRIBUTE_HIDDEN |
3434 FILE_ATTRIBUTE_SYSTEM,
3435 check_empty_fn,
3436 &list_count);
3437 if (!NT_STATUS_IS_OK(status)) {
3438 printf("cli_list of %s returned %s\n",
3439 dname,
3440 nt_errstr(status));
3441 return false;
3443 if (list_count != 2) {
3444 printf("cli_list of %s returned a count of %u\n",
3445 dname,
3446 list_count);
3447 return false;
3450 /* Open target directory. */
3451 status = cli_ntcreate(cli,
3452 dname,
3454 DELETE_ACCESS|FILE_READ_DATA,
3455 FILE_ATTRIBUTE_DIRECTORY,
3456 FILE_SHARE_READ|
3457 FILE_SHARE_WRITE|
3458 FILE_SHARE_DELETE,
3459 FILE_OPEN,
3460 FILE_DIRECTORY_FILE,
3462 &fnum,
3463 NULL);
3464 if (!NT_STATUS_IS_OK(status)) {
3465 printf("cli_ntcreate for directory %s returned %s\n",
3466 dname,
3467 nt_errstr(status));
3468 goto out;
3471 /* Now set the delete on close bit. */
3472 status = cli_nt_delete_on_close(cli, fnum, 1);
3473 if (!NT_STATUS_IS_OK(status)) {
3474 printf("cli_cli_nt_delete_on_close set for directory "
3475 "%s returned %s (should have succeeded)\n",
3476 dname,
3477 nt_errstr(status));
3478 goto out;
3481 ret = true;
3483 out:
3485 if (fnum != (uint16_t)-1) {
3486 (void)cli_nt_delete_on_close(cli, fnum, 0);
3487 (void)cli_close(cli, fnum);
3489 return ret;
3493 * Test setting the delete on close bit on a directory
3494 * containing an unwritable file fails or succeeds
3495 * an a share set with "hide unwritable = yes"
3496 * depending on the setting of "delete veto files".
3497 * BUG: https://bugzilla.samba.org/show_bug.cgi?id=15023
3499 * Second version. With "delete veto files = no"
3500 * setting the delete on close should fail.
3503 bool run_delete_on_close_nonwrite_delete_no_test(int dummy)
3505 struct cli_state *cli = NULL;
3506 NTSTATUS status;
3507 const char *dname = "delete_veto_no";
3508 const char *list_dname = "delete_veto_no\\*";
3509 uint16_t fnum = (uint16_t)-1;
3510 bool ret = false;
3511 unsigned int list_count = 0;
3513 printf("SMB2 delete on close nonwrite - delete veto yes\n");
3515 if (!torture_init_connection(&cli)) {
3516 return false;
3519 status = smbXcli_negprot(cli->conn,
3520 cli->timeout,
3521 PROTOCOL_SMB2_02,
3522 PROTOCOL_SMB3_11);
3523 if (!NT_STATUS_IS_OK(status)) {
3524 printf("smbXcli_negprot returned %s\n", nt_errstr(status));
3525 return false;
3528 status = cli_session_setup_creds(cli, torture_creds);
3529 if (!NT_STATUS_IS_OK(status)) {
3530 printf("cli_session_setup returned %s\n", nt_errstr(status));
3531 return false;
3534 status = cli_tree_connect(cli, share, "?????", NULL);
3535 if (!NT_STATUS_IS_OK(status)) {
3536 printf("cli_tree_connect returned %s\n", nt_errstr(status));
3537 return false;
3540 /* Ensure target directory is seen as empty. */
3541 status = cli_list(cli,
3542 list_dname,
3543 FILE_ATTRIBUTE_DIRECTORY |
3544 FILE_ATTRIBUTE_HIDDEN |
3545 FILE_ATTRIBUTE_SYSTEM,
3546 check_empty_fn,
3547 &list_count);
3548 if (!NT_STATUS_IS_OK(status)) {
3549 printf("cli_list of %s returned %s\n",
3550 dname,
3551 nt_errstr(status));
3552 return false;
3554 if (list_count != 2) {
3555 printf("cli_list of %s returned a count of %u\n",
3556 dname,
3557 list_count);
3558 return false;
3561 /* Open target directory. */
3562 status = cli_ntcreate(cli,
3563 dname,
3565 DELETE_ACCESS|FILE_READ_DATA,
3566 FILE_ATTRIBUTE_DIRECTORY,
3567 FILE_SHARE_READ|
3568 FILE_SHARE_WRITE|
3569 FILE_SHARE_DELETE,
3570 FILE_OPEN,
3571 FILE_DIRECTORY_FILE,
3573 &fnum,
3574 NULL);
3575 if (!NT_STATUS_IS_OK(status)) {
3576 printf("cli_ntcreate for directory %s returned %s\n",
3577 dname,
3578 nt_errstr(status));
3579 goto out;
3582 /* Now set the delete on close bit. */
3583 status = cli_nt_delete_on_close(cli, fnum, 1);
3584 if (NT_STATUS_IS_OK(status)) {
3585 printf("cli_cli_nt_delete_on_close set for directory "
3586 "%s returned NT_STATUS_OK "
3587 "(should have failed)\n",
3588 dname);
3589 goto out;
3591 if (!NT_STATUS_EQUAL(status, NT_STATUS_DIRECTORY_NOT_EMPTY)) {
3592 printf("cli_cli_nt_delete_on_close set for directory "
3593 "%s returned %s "
3594 "(should have returned "
3595 "NT_STATUS_DIRECTORY_NOT_EMPTY)\n",
3596 dname,
3597 nt_errstr(status));
3598 goto out;
3601 ret = true;
3603 out:
3605 if (fnum != (uint16_t)-1) {
3606 (void)cli_nt_delete_on_close(cli, fnum, 0);
3607 (void)cli_close(cli, fnum);
3609 return ret;