2 Unix SMB/CIFS implementation.
4 delete on close testing
6 Copyright (C) Andrew Tridgell 2003
8 This program is free software; you can redistribute it and/or modify
9 it under the terms of the GNU General Public License as published by
10 the Free Software Foundation; either version 2 of the License, or
11 (at your option) any later version.
13 This program is distributed in the hope that it will be useful,
14 but WITHOUT ANY WARRANTY; without even the implied warranty of
15 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
16 GNU General Public License for more details.
18 You should have received a copy of the GNU General Public License
19 along with this program; if not, write to the Free Software
20 Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
24 #include "libcli/libcli.h"
25 #include "torture/torture.h"
26 #include "torture/util.h"
27 #include "system/filesys.h"
28 #include "libcli/raw/libcliraw.h"
30 #include "torture/raw/proto.h"
32 static BOOL
check_delete_on_close(struct smbcli_state
*cli
, int fnum
,
33 const char *fname
, BOOL expect_it
,
36 TALLOC_CTX
*mem_ctx
= talloc_init("single_search");
37 union smb_search_data data
;
40 time_t c_time
, a_time
, m_time
;
46 status
= torture_single_search(cli
, mem_ctx
,
49 RAW_SEARCH_DATA_FULL_DIRECTORY_INFO
,
50 FILE_ATTRIBUTE_DIRECTORY
,
52 if (!NT_STATUS_IS_OK(status
)) {
53 printf("(%s) single_search failed (%s)\n",
54 where
, nt_errstr(status
));
60 union smb_fileinfo io
;
61 int nlink
= expect_it
? 0 : 1;
63 io
.all_info
.level
= RAW_FILEINFO_ALL_INFO
;
64 io
.all_info
.in
.file
.fnum
= fnum
;
66 status
= smb_raw_fileinfo(cli
->tree
, mem_ctx
, &io
);
67 if (!NT_STATUS_IS_OK(status
)) {
68 printf("(%s) qfileinfo failed (%s)\n", where
,
74 if (expect_it
!= io
.all_info
.out
.delete_pending
) {
75 printf("%s - Expected del_on_close flag %d, qfileinfo/all_info gave %d\n",
76 where
, expect_it
, io
.all_info
.out
.delete_pending
);
81 if (nlink
!= io
.all_info
.out
.nlink
) {
82 printf("%s - Expected nlink %d, qfileinfo/all_info gave %d\n",
83 where
, nlink
, io
.all_info
.out
.nlink
);
88 io
.standard_info
.level
= RAW_FILEINFO_STANDARD_INFO
;
89 io
.standard_info
.in
.file
.fnum
= fnum
;
91 status
= smb_raw_fileinfo(cli
->tree
, mem_ctx
, &io
);
92 if (!NT_STATUS_IS_OK(status
)) {
93 printf("(%s) qpathinfo failed (%s)\n", where
,
99 if (expect_it
!= io
.standard_info
.out
.delete_pending
) {
100 printf("%s - Expected del_on_close flag %d, qfileinfo/standard_info gave %d\n",
101 where
, expect_it
, io
.standard_info
.out
.delete_pending
);
106 if (nlink
!= io
.standard_info
.out
.nlink
) {
107 printf("%s - Expected nlink %d, qfileinfo/standard_info gave %d\n",
108 where
, nlink
, io
.all_info
.out
.nlink
);
115 status
= smbcli_qpathinfo(cli
->tree
, fname
,
116 &c_time
, &a_time
, &m_time
,
120 if (!NT_STATUS_EQUAL(status
, NT_STATUS_DELETE_PENDING
)) {
121 printf("(%s) qpathinfo did not give correct error "
122 "code (%s) -- NT_STATUS_DELETE_PENDING "
129 if (!NT_STATUS_IS_OK(status
)) {
130 printf("(%s) qpathinfo failed (%s)\n", where
,
138 talloc_free(mem_ctx
);
142 #define CHECK_STATUS(_cli, _expected) do { \
143 if (!NT_STATUS_EQUAL(_cli->tree->session->transport->error.e.nt_status, _expected)) { \
144 printf("(%d) Incorrect status %s - should be %s\n", \
145 __LINE__, nt_errstr(_cli->tree->session->transport->error.e.nt_status), nt_errstr(_expected)); \
150 static const char *fname
= "\\delete.file";
151 static const char *fname_new
= "\\delete.new";
152 static const char *dname
= "\\delete.dir";
154 static void del_clean_area(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
156 smbcli_deltree(cli1
->tree
, dname
);
157 smbcli_setatr(cli1
->tree
, fname
, 0, 0);
158 smbcli_unlink(cli1
->tree
, fname
);
159 smbcli_setatr(cli1
->tree
, fname_new
, 0, 0);
160 smbcli_unlink(cli1
->tree
, fname_new
);
162 smb_raw_exit(cli1
->session
);
163 smb_raw_exit(cli2
->session
);
166 /* Test 1 - this should delete the file on close. */
168 static BOOL
deltest1(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
172 del_clean_area(cli1
, cli2
);
174 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
176 FILE_ATTRIBUTE_NORMAL
,
177 NTCREATEX_SHARE_ACCESS_DELETE
, NTCREATEX_DISP_OVERWRITE_IF
,
178 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
181 printf("(%s) open of %s failed (%s)\n",
182 __location__
, fname
, smbcli_errstr(cli1
->tree
));
186 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
187 printf("(%s) close failed (%s)\n",
188 __location__
, smbcli_errstr(cli1
->tree
));
192 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDWR
, DENY_NONE
);
194 printf("(%s) open of %s succeeded (should fail)\n",
195 __location__
, fname
);
199 printf("first delete on close test succeeded.\n");
203 /* Test 2 - this should delete the file on close. */
204 static BOOL
deltest2(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
208 del_clean_area(cli1
, cli2
);
210 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
212 FILE_ATTRIBUTE_NORMAL
, NTCREATEX_SHARE_ACCESS_NONE
,
213 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
216 printf("(%s) open of %s failed (%s)\n",
217 __location__
, fname
, smbcli_errstr(cli1
->tree
));
221 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
222 printf("(%s) setting delete_on_close failed (%s)\n",
223 __location__
, smbcli_errstr(cli1
->tree
));
227 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
228 printf("(%s) close failed (%s)\n",
229 __location__
, smbcli_errstr(cli1
->tree
));
233 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
235 printf("(%s) open of %s succeeded should have been deleted on close !\n",
236 __location__
, fname
);
237 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
238 printf("(%s) close failed (%s)\n",
239 __location__
, smbcli_errstr(cli1
->tree
));
242 smbcli_unlink(cli1
->tree
, fname
);
244 printf("second delete on close test succeeded.\n");
250 static BOOL
deltest3(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
255 del_clean_area(cli1
, cli2
);
257 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
259 FILE_ATTRIBUTE_NORMAL
,
260 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
,
261 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
264 printf("(%s) open - 1 of %s failed (%s)\n",
265 __location__
, fname
, smbcli_errstr(cli1
->tree
));
269 /* This should fail with a sharing violation - open for delete is only compatible
270 with SHARE_DELETE. */
272 fnum2
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
273 SEC_RIGHTS_FILE_READ
,
274 FILE_ATTRIBUTE_NORMAL
,
275 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
,
276 NTCREATEX_DISP_OPEN
, 0, 0);
279 printf("(%s) open - 2 of %s succeeded - should have failed.\n",
280 __location__
, fname
);
284 /* This should succeed. */
286 fnum2
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
287 SEC_RIGHTS_FILE_READ
,
288 FILE_ATTRIBUTE_NORMAL
,
289 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
|NTCREATEX_SHARE_ACCESS_DELETE
,
290 NTCREATEX_DISP_OPEN
, 0, 0);
293 printf("(%s) open - 2 of %s failed (%s)\n",
294 __location__
, fname
, smbcli_errstr(cli1
->tree
));
298 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
299 printf("(%s) setting delete_on_close failed (%s)\n",
300 __location__
, smbcli_errstr(cli1
->tree
));
304 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
305 printf("(%s) close 1 failed (%s)\n",
306 __location__
, smbcli_errstr(cli1
->tree
));
310 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum2
))) {
311 printf("(%s) close 2 failed (%s)\n",
312 __location__
, smbcli_errstr(cli1
->tree
));
316 /* This should fail - file should no longer be there. */
318 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
320 printf("(%s) open of %s succeeded should have been deleted on close !\n",
321 __location__
, fname
);
322 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
323 printf("(%s) close failed (%s)\n",
324 __location__
, smbcli_errstr(cli1
->tree
));
326 smbcli_unlink(cli1
->tree
, fname
);
329 printf("third delete on close test succeeded.\n");
335 static BOOL
deltest4(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
341 del_clean_area(cli1
, cli2
);
343 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
345 SEC_FILE_WRITE_DATA
|
347 FILE_ATTRIBUTE_NORMAL
,
348 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
,
349 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
352 printf("(%s) open of %s failed (%s)\n",
353 __location__
, fname
, smbcli_errstr(cli1
->tree
));
357 /* This should succeed. */
358 fnum2
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
359 SEC_RIGHTS_FILE_READ
,
360 FILE_ATTRIBUTE_NORMAL
,
361 NTCREATEX_SHARE_ACCESS_READ
|
362 NTCREATEX_SHARE_ACCESS_WRITE
|
363 NTCREATEX_SHARE_ACCESS_DELETE
,
364 NTCREATEX_DISP_OPEN
, 0, 0);
366 printf("(%s) open - 2 of %s failed (%s)\n",
367 __location__
, fname
, smbcli_errstr(cli1
->tree
));
371 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum2
))) {
372 printf("(%s) close - 1 failed (%s)\n",
373 __location__
, smbcli_errstr(cli1
->tree
));
377 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
378 printf("(%s) setting delete_on_close failed (%s)\n",
379 __location__
, smbcli_errstr(cli1
->tree
));
383 /* This should fail - no more opens once delete on close set. */
384 fnum2
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
385 SEC_RIGHTS_FILE_READ
,
386 FILE_ATTRIBUTE_NORMAL
,
387 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
|NTCREATEX_SHARE_ACCESS_DELETE
,
388 NTCREATEX_DISP_OPEN
, 0, 0);
390 printf("(%s) open - 3 of %s succeeded ! Should have failed.\n",
391 __location__
, fname
);
394 CHECK_STATUS(cli1
, NT_STATUS_DELETE_PENDING
);
396 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
397 printf("(%s) close - 2 failed (%s)\n",
398 __location__
, smbcli_errstr(cli1
->tree
));
402 printf("fourth delete on close test succeeded.\n");
410 static BOOL
deltest5(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
414 del_clean_area(cli1
, cli2
);
416 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDWR
|O_CREAT
, DENY_NONE
);
418 printf("(%s) open of %s failed (%s)\n",
419 __location__
, fname
, smbcli_errstr(cli1
->tree
));
423 /* This should fail - only allowed on NT opens with DELETE access. */
425 if (NT_STATUS_IS_OK(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
426 printf("(%s) setting delete_on_close on OpenX file succeeded - should fail !\n",
431 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
432 printf("(%s) close - 2 failed (%s)\n",
433 __location__
, smbcli_errstr(cli1
->tree
));
437 printf("fifth delete on close test succeeded.\n");
442 static BOOL
deltest6(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
446 del_clean_area(cli1
, cli2
);
448 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
449 SEC_FILE_READ_DATA
| SEC_FILE_WRITE_DATA
,
450 FILE_ATTRIBUTE_NORMAL
,
451 NTCREATEX_SHARE_ACCESS_READ
|
452 NTCREATEX_SHARE_ACCESS_WRITE
|
453 NTCREATEX_SHARE_ACCESS_DELETE
,
454 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
457 printf("(%s) open of %s failed (%s)\n",
458 __location__
, fname
, smbcli_errstr(cli1
->tree
));
462 /* This should fail - only allowed on NT opens with DELETE access. */
464 if (NT_STATUS_IS_OK(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
465 printf("(%s) setting delete_on_close on file with no delete access succeeded - should fail !\n",
470 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
471 printf("(%s) close - 2 failed (%s)\n",
472 __location__
, smbcli_errstr(cli1
->tree
));
476 printf("sixth delete on close test succeeded.\n");
481 static BOOL
deltest7(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
486 del_clean_area(cli1
, cli2
);
488 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
490 SEC_FILE_WRITE_DATA
|
492 FILE_ATTRIBUTE_NORMAL
, 0,
493 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
496 printf("(%s) open of %s failed (%s)\n",
497 __location__
, fname
, smbcli_errstr(cli1
->tree
));
502 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
503 printf("(%s) setting delete_on_close on file failed !\n",
509 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, True
, __location__
);
511 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, False
))) {
512 printf("(%s) unsetting delete_on_close on file failed !\n",
518 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
520 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
521 printf("(%s) close - 2 failed (%s)\n",
522 __location__
, smbcli_errstr(cli1
->tree
));
527 /* This next open should succeed - we reset the flag. */
529 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
531 printf("(%s) open of %s failed (%s)\n",
532 __location__
, fname
, smbcli_errstr(cli1
->tree
));
537 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
538 printf("(%s) close - 2 failed (%s)\n",
539 __location__
, smbcli_errstr(cli1
->tree
));
544 printf("seventh delete on close test succeeded.\n");
552 static BOOL
deltest8(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
558 del_clean_area(cli1
, cli2
);
560 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
564 FILE_ATTRIBUTE_NORMAL
,
565 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
|NTCREATEX_SHARE_ACCESS_DELETE
,
566 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
569 printf("(%s) open of %s failed (%s)\n",
570 __location__
, fname
, smbcli_errstr(cli1
->tree
));
575 fnum2
= smbcli_nt_create_full(cli2
->tree
, fname
, 0,
579 FILE_ATTRIBUTE_NORMAL
,
580 NTCREATEX_SHARE_ACCESS_READ
|NTCREATEX_SHARE_ACCESS_WRITE
|NTCREATEX_SHARE_ACCESS_DELETE
,
581 NTCREATEX_DISP_OPEN
, 0, 0);
584 printf("(%s) open of %s failed (%s)\n",
585 __location__
, fname
, smbcli_errstr(cli1
->tree
));
590 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
591 printf("(%s) setting delete_on_close on file failed !\n",
597 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, True
, __location__
);
598 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, True
, __location__
);
600 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
601 printf("(%s) close - 1 failed (%s)\n",
602 __location__
, smbcli_errstr(cli1
->tree
));
607 correct
&= check_delete_on_close(cli1
, -1, fname
, True
, __location__
);
608 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, True
, __location__
);
610 if (NT_STATUS_IS_ERR(smbcli_close(cli2
->tree
, fnum2
))) {
611 printf("(%s) close - 2 failed (%s)\n",
612 __location__
, smbcli_errstr(cli2
->tree
));
617 /* This should fail.. */
618 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
620 printf("(%s) open of %s succeeded should have been deleted on close !\n",
621 __location__
, fname
);
624 printf("eighth delete on close test succeeded.\n");
633 static BOOL
deltest9(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
637 del_clean_area(cli1
, cli2
);
639 /* This should fail - we need to set DELETE_ACCESS. */
640 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
641 SEC_FILE_READ_DATA
|SEC_FILE_WRITE_DATA
,
642 FILE_ATTRIBUTE_NORMAL
,
643 NTCREATEX_SHARE_ACCESS_NONE
,
644 NTCREATEX_DISP_OVERWRITE_IF
,
645 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
648 printf("(%s) open of %s succeeded should have failed!\n",
649 __location__
, fname
);
653 printf("ninth delete on close test succeeded.\n");
658 static BOOL
deltest10(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
663 del_clean_area(cli1
, cli2
);
665 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
669 FILE_ATTRIBUTE_NORMAL
,
670 NTCREATEX_SHARE_ACCESS_NONE
,
671 NTCREATEX_DISP_OVERWRITE_IF
,
672 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
674 printf("(%s) open of %s failed (%s)\n",
675 __location__
, fname
, smbcli_errstr(cli1
->tree
));
680 /* This should delete the file. */
681 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
682 printf("(%s) close failed (%s)\n",
683 __location__
, smbcli_errstr(cli1
->tree
));
688 /* This should fail.. */
689 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
691 printf("(%s) open of %s succeeded should have been deleted on close !\n",
692 __location__
, fname
);
696 printf("tenth delete on close test succeeded.\n");
705 static BOOL
deltest11(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
710 del_clean_area(cli1
, cli2
);
712 /* test 11 - does having read only attribute still allow delete on close. */
714 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
716 FILE_ATTRIBUTE_READONLY
,
717 NTCREATEX_SHARE_ACCESS_NONE
,
718 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
721 printf("(%s) open of %s failed (%s)\n",
722 __location__
, fname
, smbcli_errstr(cli1
->tree
));
726 status
= smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
);
728 if (!NT_STATUS_EQUAL(status
, NT_STATUS_CANNOT_DELETE
)) {
729 printf("(%s) setting delete_on_close should fail with NT_STATUS_CANNOT_DELETE. Got %s instead)\n",
730 __location__
, smbcli_errstr(cli1
->tree
));
734 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
735 printf("(%s) close failed (%s)\n",
736 __location__
, smbcli_errstr(cli1
->tree
));
740 printf("eleventh delete on close test succeeded.\n");
745 static BOOL
deltest12(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
750 del_clean_area(cli1
, cli2
);
752 /* test 12 - does having read only attribute still allow delete on
753 * close at time of open. */
755 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
757 FILE_ATTRIBUTE_READONLY
,
758 NTCREATEX_SHARE_ACCESS_DELETE
,
759 NTCREATEX_DISP_OVERWRITE_IF
,
760 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
763 printf("(%s) open of %s succeeded. Should fail with "
764 "NT_STATUS_CANNOT_DELETE.\n", __location__
, fname
);
765 smbcli_close(cli1
->tree
, fnum1
);
768 status
= smbcli_nt_error(cli1
->tree
);
769 if (!NT_STATUS_EQUAL(status
, NT_STATUS_CANNOT_DELETE
)) {
770 printf("(%s) setting delete_on_close on open should "
771 "fail with NT_STATUS_CANNOT_DELETE. Got %s "
773 __location__
, smbcli_errstr(cli1
->tree
));
778 printf("twelvth delete on close test succeeded.\n");
783 static BOOL
deltest13(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
789 del_clean_area(cli1
, cli2
);
791 /* Test 13: Does resetting the delete on close flag affect a second
794 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
798 FILE_ATTRIBUTE_NORMAL
,
799 NTCREATEX_SHARE_ACCESS_READ
|
800 NTCREATEX_SHARE_ACCESS_WRITE
|
801 NTCREATEX_SHARE_ACCESS_DELETE
,
802 NTCREATEX_DISP_OVERWRITE_IF
,
806 printf("(%s) open of %s failed (%s)\n",
807 __location__
, fname
, smbcli_errstr(cli1
->tree
));
812 fnum2
= smbcli_nt_create_full(cli2
->tree
, fname
, 0,
816 FILE_ATTRIBUTE_NORMAL
,
817 NTCREATEX_SHARE_ACCESS_READ
|
818 NTCREATEX_SHARE_ACCESS_WRITE
|
819 NTCREATEX_SHARE_ACCESS_DELETE
,
820 NTCREATEX_DISP_OPEN
, 0, 0);
823 printf("(%s) open of %s failed (%s)\n",
824 __location__
, fname
, smbcli_errstr(cli2
->tree
));
829 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
,
831 printf("(%s) setting delete_on_close on file failed !\n",
837 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, True
, __location__
);
838 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, True
, __location__
);
840 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli2
->tree
, fnum2
,
842 printf("(%s) setting delete_on_close on file failed !\n",
848 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
849 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, False
, __location__
);
851 if (NT_STATUS_IS_ERR(smbcli_close(cli1
->tree
, fnum1
))) {
852 printf("(%s) close - 1 failed (%s)\n",
853 __location__
, smbcli_errstr(cli1
->tree
));
858 if (NT_STATUS_IS_ERR(smbcli_close(cli2
->tree
, fnum2
))) {
859 printf("(%s) close - 2 failed (%s)\n",
860 __location__
, smbcli_errstr(cli2
->tree
));
865 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDONLY
, DENY_NONE
);
868 printf("(%s) open of %s failed!\n",
869 __location__
, fname
);
874 printf("thirteenth delete on close test succeeded.\n");
882 static BOOL
deltest14(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
887 del_clean_area(cli1
, cli2
);
889 /* Test 14 -- directory */
891 dnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
895 FILE_ATTRIBUTE_DIRECTORY
,
896 NTCREATEX_SHARE_ACCESS_READ
|
897 NTCREATEX_SHARE_ACCESS_WRITE
|
898 NTCREATEX_SHARE_ACCESS_DELETE
,
899 NTCREATEX_DISP_CREATE
, 0, 0);
901 printf("(%s) open of %s failed: %s!\n",
902 __location__
, dname
, smbcli_errstr(cli1
->tree
));
907 correct
&= check_delete_on_close(cli1
, dnum1
, dname
, False
, __location__
);
908 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, dnum1
, True
))) {
909 printf("(%s) setting delete_on_close on file failed !\n",
914 correct
&= check_delete_on_close(cli1
, dnum1
, dname
, True
, __location__
);
915 smbcli_close(cli1
->tree
, dnum1
);
917 /* Now it should be gone... */
919 dnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
923 FILE_ATTRIBUTE_DIRECTORY
,
924 NTCREATEX_SHARE_ACCESS_READ
|
925 NTCREATEX_SHARE_ACCESS_WRITE
|
926 NTCREATEX_SHARE_ACCESS_DELETE
,
927 NTCREATEX_DISP_OPEN
, 0, 0);
929 printf("(%s) setting delete_on_close on file succeeded !\n",
935 printf("fourteenth delete on close test succeeded.\n");
943 static BOOL
deltest15(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
950 del_clean_area(cli1
, cli2
);
952 /* Test 15: delete on close under rename */
954 smbcli_setatr(cli1
->tree
, fname
, 0, 0);
955 smbcli_unlink(cli1
->tree
, fname
);
956 smbcli_unlink(cli1
->tree
, fname_new
);
958 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
960 FILE_ATTRIBUTE_NORMAL
,
961 NTCREATEX_SHARE_ACCESS_READ
|
962 NTCREATEX_SHARE_ACCESS_WRITE
|
963 NTCREATEX_SHARE_ACCESS_DELETE
,
964 NTCREATEX_DISP_OVERWRITE_IF
,
968 printf("(%s) open - 1 of %s failed (%s)\n",
969 __location__
, fname
, smbcli_errstr(cli1
->tree
));
974 status
= smbcli_rename(cli2
->tree
, fname
, fname_new
);
976 if (!NT_STATUS_IS_OK(status
)) {
977 printf("(%s) renaming failed: %s !\n",
978 __location__
, nt_errstr(status
));
983 fnum2
= smbcli_nt_create_full(cli2
->tree
, fname_new
, 0,
985 FILE_ATTRIBUTE_NORMAL
,
986 NTCREATEX_SHARE_ACCESS_READ
|
987 NTCREATEX_SHARE_ACCESS_WRITE
|
988 NTCREATEX_SHARE_ACCESS_DELETE
,
989 NTCREATEX_DISP_OVERWRITE_IF
,
993 printf("(%s) open - 1 of %s failed (%s)\n",
994 __location__
, fname_new
, smbcli_errstr(cli1
->tree
));
999 status
= smbcli_nt_delete_on_close(cli2
->tree
, fnum2
, True
);
1001 if (!NT_STATUS_IS_OK(status
)) {
1002 printf("(%s) setting delete_on_close on file failed !\n",
1008 smbcli_close(cli2
->tree
, fnum2
);
1010 /* The file should be around under the new name, there's a second
1013 correct
&= check_delete_on_close(cli1
, fnum1
, fname_new
, True
, __location__
);
1015 fnum2
= smbcli_nt_create_full(cli2
->tree
, fname
, 0,
1017 FILE_ATTRIBUTE_NORMAL
,
1018 NTCREATEX_SHARE_ACCESS_READ
|
1019 NTCREATEX_SHARE_ACCESS_WRITE
|
1020 NTCREATEX_SHARE_ACCESS_DELETE
,
1021 NTCREATEX_DISP_OVERWRITE_IF
,
1025 printf("(%s) open - 1 of %s failed (%s)\n",
1026 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1031 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, False
, __location__
);
1033 smbcli_close(cli2
->tree
, fnum2
);
1034 smbcli_close(cli1
->tree
, fnum1
);
1036 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1038 FILE_ATTRIBUTE_NORMAL
,
1039 NTCREATEX_SHARE_ACCESS_READ
|
1040 NTCREATEX_SHARE_ACCESS_WRITE
|
1041 NTCREATEX_SHARE_ACCESS_DELETE
,
1042 NTCREATEX_DISP_OPEN
,
1046 printf("(%s) open - 1 of %s failed (%s)\n",
1047 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1052 smbcli_close(cli1
->tree
, fnum1
);
1054 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname_new
, 0,
1056 FILE_ATTRIBUTE_NORMAL
,
1057 NTCREATEX_SHARE_ACCESS_READ
|
1058 NTCREATEX_SHARE_ACCESS_WRITE
|
1059 NTCREATEX_SHARE_ACCESS_DELETE
,
1060 NTCREATEX_DISP_OPEN
,
1064 printf("(%s) smbcli_open succeeded, should have "
1065 "failed\n", __location__
);
1066 smbcli_close(cli1
->tree
, fnum1
);
1071 printf("fifteenth delete on close test succeeded.\n");
1079 static BOOL
deltest16(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
1083 BOOL correct
= True
;
1085 del_clean_area(cli1
, cli2
);
1089 /* Ensure the file doesn't already exist. */
1090 smbcli_close(cli1
->tree
, fnum1
);
1091 smbcli_close(cli1
->tree
, fnum2
);
1092 smbcli_setatr(cli1
->tree
, fname
, 0, 0);
1093 smbcli_unlink(cli1
->tree
, fname
);
1095 /* Firstly create with all access, but delete on close. */
1096 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1097 SEC_RIGHTS_FILE_ALL
,
1098 FILE_ATTRIBUTE_NORMAL
,
1099 NTCREATEX_SHARE_ACCESS_READ
|
1100 NTCREATEX_SHARE_ACCESS_WRITE
|
1101 NTCREATEX_SHARE_ACCESS_DELETE
,
1102 NTCREATEX_DISP_CREATE
,
1103 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
1106 printf("(%s) open - 1 of %s failed (%s)\n",
1107 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1112 /* The delete on close bit is *not* reported as being set. */
1113 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
1115 /* The delete on close bit is *not* reported as being set. */
1116 correct
&= check_delete_on_close(cli1
, -1, fname
, False
, __location__
);
1117 correct
&= check_delete_on_close(cli2
, -1, fname
, False
, __location__
);
1119 /* Now try opening again for read-only. */
1120 fnum2
= smbcli_nt_create_full(cli2
->tree
, fname
, 0,
1121 SEC_RIGHTS_FILE_READ
,
1122 FILE_ATTRIBUTE_NORMAL
,
1123 NTCREATEX_SHARE_ACCESS_READ
|
1124 NTCREATEX_SHARE_ACCESS_WRITE
|
1125 NTCREATEX_SHARE_ACCESS_DELETE
,
1126 NTCREATEX_DISP_OPEN
,
1132 printf("(%s) open - 1 of %s failed (%s)\n",
1133 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1138 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
1139 correct
&= check_delete_on_close(cli1
, -1, fname
, False
, __location__
);
1140 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, False
, __location__
);
1141 correct
&= check_delete_on_close(cli2
, -1, fname
, False
, __location__
);
1143 smbcli_close(cli1
->tree
, fnum1
);
1145 correct
&= check_delete_on_close(cli2
, fnum2
, fname
, True
, __location__
);
1146 correct
&= check_delete_on_close(cli2
, -1, fname
, True
, __location__
);
1148 smbcli_close(cli2
->tree
, fnum2
);
1150 /* And the file should be deleted ! */
1151 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDWR
, DENY_NONE
);
1153 printf("(%s) open of %s succeeded (should fail)\n",
1154 __location__
, fname
);
1159 printf("sixteenth delete on close test succeeded.\n");
1167 static BOOL
deltest17(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
1171 BOOL correct
= True
;
1173 del_clean_area(cli1
, cli2
);
1177 /* Ensure the file doesn't already exist. */
1178 smbcli_close(cli1
->tree
, fnum1
);
1179 smbcli_close(cli1
->tree
, fnum2
);
1180 smbcli_setatr(cli1
->tree
, fname
, 0, 0);
1181 smbcli_unlink(cli1
->tree
, fname
);
1183 /* Firstly open and create with all access */
1184 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1185 SEC_RIGHTS_FILE_ALL
,
1186 FILE_ATTRIBUTE_NORMAL
,
1187 NTCREATEX_SHARE_ACCESS_READ
|
1188 NTCREATEX_SHARE_ACCESS_WRITE
|
1189 NTCREATEX_SHARE_ACCESS_DELETE
,
1190 NTCREATEX_DISP_CREATE
,
1193 printf("(%s) open - 1 of %s failed (%s)\n",
1194 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1199 /* And close - just to create the file. */
1200 smbcli_close(cli1
->tree
, fnum1
);
1202 /* Next open with all access, but add delete on close. */
1203 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1204 SEC_RIGHTS_FILE_ALL
,
1205 FILE_ATTRIBUTE_NORMAL
,
1206 NTCREATEX_SHARE_ACCESS_READ
|
1207 NTCREATEX_SHARE_ACCESS_WRITE
|
1208 NTCREATEX_SHARE_ACCESS_DELETE
,
1209 NTCREATEX_DISP_OPEN
,
1210 NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
1213 printf("(%s) open - 1 of %s failed (%s)\n",
1214 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1219 /* The delete on close bit is *not* reported as being set. */
1220 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
1222 /* Now try opening again for read-only. */
1223 fnum2
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1224 SEC_RIGHTS_FILE_READ
|
1226 FILE_ATTRIBUTE_NORMAL
,
1227 NTCREATEX_SHARE_ACCESS_READ
|
1228 NTCREATEX_SHARE_ACCESS_WRITE
|
1229 NTCREATEX_SHARE_ACCESS_DELETE
,
1230 NTCREATEX_DISP_OPEN
,
1235 printf("(%s) open - 1 of %s failed (%s)\n",
1236 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1241 /* still not reported as being set on either */
1242 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, False
, __location__
);
1243 correct
&= check_delete_on_close(cli1
, fnum2
, fname
, False
, __location__
);
1245 smbcli_close(cli1
->tree
, fnum1
);
1247 correct
&= check_delete_on_close(cli1
, fnum2
, fname
, False
, __location__
);
1249 smbcli_close(cli1
->tree
, fnum2
);
1251 /* See if the file is deleted - shouldn't be.... */
1252 fnum1
= smbcli_open(cli1
->tree
, fname
, O_RDWR
, DENY_NONE
);
1254 printf("(%s) open of %s failed (should succeed) - %s\n",
1255 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1260 printf("seventeenth delete on close test succeeded.\n");
1268 static BOOL
deltest18(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
1272 BOOL correct
= True
;
1274 del_clean_area(cli1
, cli2
);
1276 /* Test 18. With directories. */
1278 /* Ensure the file doesn't already exist. */
1279 smbcli_close(cli1
->tree
, fnum1
);
1280 smbcli_close(cli1
->tree
, fnum2
);
1282 smbcli_deltree(cli1
->tree
, dname
);
1284 /* Firstly create with all access, but delete on close. */
1285 fnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1287 SEC_FILE_WRITE_DATA
|
1289 FILE_ATTRIBUTE_DIRECTORY
,
1290 NTCREATEX_SHARE_ACCESS_READ
|
1291 NTCREATEX_SHARE_ACCESS_WRITE
|
1292 NTCREATEX_SHARE_ACCESS_DELETE
,
1293 NTCREATEX_DISP_CREATE
,
1294 NTCREATEX_OPTIONS_DIRECTORY
|NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
1297 printf("(%s) open - 1 of %s failed (%s)\n",
1298 __location__
, dname
, smbcli_errstr(cli1
->tree
));
1303 /* The delete on close bit is *not* reported as being set. */
1304 correct
&= check_delete_on_close(cli1
, fnum1
, dname
, False
, __location__
);
1306 /* Now try opening again for read-only. */
1307 fnum2
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1308 SEC_RIGHTS_FILE_READ
,
1309 FILE_ATTRIBUTE_DIRECTORY
,
1310 NTCREATEX_SHARE_ACCESS_READ
|
1311 NTCREATEX_SHARE_ACCESS_WRITE
|
1312 NTCREATEX_SHARE_ACCESS_DELETE
,
1313 NTCREATEX_DISP_OPEN
,
1314 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1319 printf("(%s) open - 1 of %s failed (%s)\n",
1320 __location__
, dname
, smbcli_errstr(cli1
->tree
));
1325 correct
&= check_delete_on_close(cli1
, fnum1
, dname
, False
, __location__
);
1326 correct
&= check_delete_on_close(cli1
, fnum2
, dname
, False
, __location__
);
1328 smbcli_close(cli1
->tree
, fnum1
);
1330 correct
&= check_delete_on_close(cli1
, fnum2
, dname
, True
, __location__
);
1332 smbcli_close(cli1
->tree
, fnum2
);
1334 /* And the directory should be deleted ! */
1335 fnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1336 SEC_RIGHTS_FILE_READ
,
1337 FILE_ATTRIBUTE_DIRECTORY
,
1338 NTCREATEX_SHARE_ACCESS_READ
|
1339 NTCREATEX_SHARE_ACCESS_WRITE
|
1340 NTCREATEX_SHARE_ACCESS_DELETE
,
1341 NTCREATEX_DISP_OPEN
,
1342 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1344 printf("(%s) open of %s succeeded (should fail)\n",
1345 __location__
, dname
);
1350 printf("eighteenth delete on close test succeeded.\n");
1358 static BOOL
deltest19(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
1362 BOOL correct
= True
;
1364 del_clean_area(cli1
, cli2
);
1368 smbcli_deltree(cli1
->tree
, dname
);
1370 /* Firstly open and create with all access */
1371 fnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1373 SEC_FILE_WRITE_DATA
|
1375 FILE_ATTRIBUTE_DIRECTORY
,
1376 NTCREATEX_SHARE_ACCESS_READ
|
1377 NTCREATEX_SHARE_ACCESS_WRITE
|
1378 NTCREATEX_SHARE_ACCESS_DELETE
,
1379 NTCREATEX_DISP_CREATE
,
1380 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1383 printf("(%s) open - 1 of %s failed (%s)\n",
1384 __location__
, dname
, smbcli_errstr(cli1
->tree
));
1389 /* And close - just to create the directory. */
1390 smbcli_close(cli1
->tree
, fnum1
);
1392 /* Next open with all access, but add delete on close. */
1393 fnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1395 SEC_FILE_WRITE_DATA
|
1397 FILE_ATTRIBUTE_DIRECTORY
,
1398 NTCREATEX_SHARE_ACCESS_READ
|
1399 NTCREATEX_SHARE_ACCESS_WRITE
|
1400 NTCREATEX_SHARE_ACCESS_DELETE
,
1401 NTCREATEX_DISP_OPEN
,
1402 NTCREATEX_OPTIONS_DIRECTORY
|NTCREATEX_OPTIONS_DELETE_ON_CLOSE
, 0);
1405 printf("(%s) open - 1 of %s failed (%s)\n",
1406 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1411 /* The delete on close bit is *not* reported as being set. */
1412 correct
&= check_delete_on_close(cli1
, fnum1
, dname
, False
, __location__
);
1414 /* Now try opening again for read-only. */
1415 fnum2
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1416 SEC_RIGHTS_FILE_READ
,
1417 FILE_ATTRIBUTE_DIRECTORY
,
1418 NTCREATEX_SHARE_ACCESS_READ
|
1419 NTCREATEX_SHARE_ACCESS_WRITE
|
1420 NTCREATEX_SHARE_ACCESS_DELETE
,
1421 NTCREATEX_DISP_OPEN
,
1422 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1426 printf("(%s) open - 1 of %s failed (%s)\n",
1427 __location__
, dname
, smbcli_errstr(cli1
->tree
));
1432 smbcli_close(cli1
->tree
, fnum1
);
1434 correct
&= check_delete_on_close(cli1
, fnum2
, dname
, True
, __location__
);
1436 smbcli_close(cli1
->tree
, fnum2
);
1438 /* See if the file is deleted - for a directory this seems to be true ! */
1439 fnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1440 SEC_RIGHTS_FILE_READ
,
1441 FILE_ATTRIBUTE_DIRECTORY
,
1442 NTCREATEX_SHARE_ACCESS_READ
|
1443 NTCREATEX_SHARE_ACCESS_WRITE
|
1444 NTCREATEX_SHARE_ACCESS_DELETE
,
1445 NTCREATEX_DISP_OPEN
,
1446 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1448 CHECK_STATUS(cli1
, NT_STATUS_OBJECT_NAME_NOT_FOUND
);
1451 printf("(%s) open of %s succeeded (should fail)\n",
1452 __location__
, dname
);
1457 printf("nineteenth delete on close test succeeded.\n");
1465 static BOOL
deltest20(struct smbcli_state
*cli1
, struct smbcli_state
*cli2
)
1469 BOOL correct
= True
;
1472 del_clean_area(cli1
, cli2
);
1474 /* Test 20 -- non-empty directory hardest to get right... */
1476 smbcli_deltree(cli1
->tree
, dname
);
1478 dnum1
= smbcli_nt_create_full(cli1
->tree
, dname
, 0,
1480 SEC_FILE_WRITE_DATA
|
1482 FILE_ATTRIBUTE_DIRECTORY
,
1483 NTCREATEX_SHARE_ACCESS_READ
|
1484 NTCREATEX_SHARE_ACCESS_WRITE
|
1485 NTCREATEX_SHARE_ACCESS_DELETE
,
1486 NTCREATEX_DISP_CREATE
,
1487 NTCREATEX_OPTIONS_DIRECTORY
, 0);
1489 printf("(%s) open of %s failed: %s!\n",
1490 __location__
, dname
, smbcli_errstr(cli1
->tree
));
1495 correct
&= check_delete_on_close(cli1
, dnum1
, dname
, False
, __location__
);
1496 status
= smbcli_nt_delete_on_close(cli1
->tree
, dnum1
, True
);
1500 asprintf(&fullname
, "\\%s%s", dname
, fname
);
1501 fnum1
= smbcli_open(cli1
->tree
, fullname
, O_CREAT
|O_RDWR
,
1504 printf("(%s) smbcli_open succeeded, should have "
1505 "failed with NT_STATUS_DELETE_PENDING\n",
1511 if (!NT_STATUS_EQUAL(smbcli_nt_error(cli1
->tree
),
1512 NT_STATUS_DELETE_PENDING
)) {
1513 printf("(%s) smbcli_open returned %s, expected "
1514 "NT_STATUS_DELETE_PENDING\n",
1515 __location__
, smbcli_errstr(cli1
->tree
));
1521 status
= smbcli_nt_delete_on_close(cli1
->tree
, dnum1
, False
);
1522 if (!NT_STATUS_IS_OK(status
)) {
1523 printf("(%s) setting delete_on_close on file failed !\n",
1531 asprintf(&fullname
, "\\%s%s", dname
, fname
);
1532 fnum1
= smbcli_open(cli1
->tree
, fullname
, O_CREAT
|O_RDWR
,
1535 printf("(%s) smbcli_open failed: %s\n",
1536 __location__
, smbcli_errstr(cli1
->tree
));
1540 smbcli_close(cli1
->tree
, fnum1
);
1543 status
= smbcli_nt_delete_on_close(cli1
->tree
, dnum1
, True
);
1545 if (!NT_STATUS_EQUAL(status
, NT_STATUS_DIRECTORY_NOT_EMPTY
)) {
1546 printf("(%s) setting delete_on_close returned %s, expected "
1547 "NT_STATUS_DIRECTORY_NOT_EMPTY\n", __location__
,
1548 smbcli_errstr(cli1
->tree
));
1553 smbcli_close(cli1
->tree
, dnum1
);
1555 printf("twentieth delete on close test succeeded.\n");
1563 static BOOL
deltest21(struct smbcli_state
**ppcli1
, struct smbcli_state
**ppcli2
)
1566 struct smbcli_state
*cli1
= *ppcli1
;
1567 struct smbcli_state
*cli2
= *ppcli2
;
1568 BOOL correct
= True
;
1570 del_clean_area(cli1
, cli2
);
1572 /* Test 21 -- Test removal of file after socket close. */
1574 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1575 SEC_RIGHTS_FILE_ALL
,
1576 FILE_ATTRIBUTE_NORMAL
, NTCREATEX_SHARE_ACCESS_NONE
,
1577 NTCREATEX_DISP_OVERWRITE_IF
, 0, 0);
1580 printf("(%s) open of %s failed (%s)\n",
1581 __location__
, fname
, smbcli_errstr(cli1
->tree
));
1585 if (NT_STATUS_IS_ERR(smbcli_nt_delete_on_close(cli1
->tree
, fnum1
, True
))) {
1586 printf("(%s) setting delete_on_close failed (%s)\n",
1587 __location__
, smbcli_errstr(cli1
->tree
));
1591 /* Ensure delete on close is set. */
1592 correct
&= check_delete_on_close(cli1
, fnum1
, fname
, True
, __location__
);
1594 /* Now yank the rug from under cli1. */
1595 smbcli_transport_dead(cli1
->transport
, NT_STATUS_LOCAL_DISCONNECT
);
1599 if (!torture_open_connection(ppcli1
, 0)) {
1605 /* On slow build farm machines it might happen that they are not fast
1606 * enogh to delete the file for this test */
1609 /* File should not be there. */
1610 fnum1
= smbcli_nt_create_full(cli1
->tree
, fname
, 0,
1611 SEC_RIGHTS_FILE_READ
,
1612 FILE_ATTRIBUTE_NORMAL
,
1613 NTCREATEX_SHARE_ACCESS_READ
|
1614 NTCREATEX_SHARE_ACCESS_WRITE
|
1615 NTCREATEX_SHARE_ACCESS_DELETE
,
1616 NTCREATEX_DISP_OPEN
,
1619 CHECK_STATUS(cli1
, NT_STATUS_OBJECT_NAME_NOT_FOUND
);
1621 printf("twenty-first delete on close test succeeded.\n");
1629 Test delete on close semantics.
1631 BOOL
torture_test_delete(struct torture_context
*torture
)
1633 struct smbcli_state
*cli1
= NULL
;
1634 struct smbcli_state
*cli2
= NULL
;
1635 BOOL correct
= True
;
1637 printf("starting delete test\n");
1639 if (!torture_open_connection(&cli1
, 0)) {
1643 if (!torture_open_connection(&cli2
, 1)) {
1644 printf("(%s) failed to open second connection.\n",
1650 correct
&= deltest1(cli1
, cli2
);
1651 correct
&= deltest2(cli1
, cli2
);
1652 correct
&= deltest3(cli1
, cli2
);
1653 correct
&= deltest4(cli1
, cli2
);
1654 correct
&= deltest5(cli1
, cli2
);
1655 correct
&= deltest6(cli1
, cli2
);
1656 correct
&= deltest7(cli1
, cli2
);
1657 correct
&= deltest8(cli1
, cli2
);
1658 correct
&= deltest9(cli1
, cli2
);
1659 correct
&= deltest10(cli1
, cli2
);
1660 correct
&= deltest11(cli1
, cli2
);
1661 correct
&= deltest12(cli1
, cli2
);
1662 correct
&= deltest13(cli1
, cli2
);
1663 correct
&= deltest14(cli1
, cli2
);
1664 correct
&= deltest15(cli1
, cli2
);
1665 if (!lp_parm_bool(-1, "target", "samba3", False
)) {
1666 correct
&= deltest16(cli1
, cli2
);
1667 correct
&= deltest17(cli1
, cli2
);
1668 correct
&= deltest18(cli1
, cli2
);
1669 correct
&= deltest19(cli1
, cli2
);
1670 correct
&= deltest20(cli1
, cli2
);
1672 correct
&= deltest21(&cli1
, &cli2
);
1675 printf("Failed delete test\n");
1677 printf("delete test ok !\n");
1681 del_clean_area(cli1
, cli2
);
1683 if (!torture_close_connection(cli1
)) {
1686 if (!torture_close_connection(cli2
)) {