2 Unix SMB/CIFS implementation.
4 Copyright (C) Andrew Tridgell 1997-1998
5 Copyright (C) Jeremy Allison 2009
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this program. If not, see <http://www.gnu.org/licenses/>.
22 #include "system/shmem.h"
23 #include "wbc_async.h"
24 #include "torture/proto.h"
25 #include "libcli/security/security.h"
27 #include "tldap_util.h"
28 #include "../librpc/gen_ndr/svcctl.h"
30 #include "nsswitch/winbind_client.h"
32 #include "talloc_dict.h"
33 #include "async_smb.h"
34 #include "libsmb/libsmb.h"
35 #include "libsmb/clirap.h"
37 #include "libsmb/nmblib.h"
38 #include "../lib/util/tevent_ntstatus.h"
40 #include "libsmb/read_smb.h"
45 fstring host, workgroup, share, password, username, myname;
46 static int max_protocol = PROTOCOL_NT1;
47 static const char *sockops="TCP_NODELAY";
49 static int port_to_use=0;
50 int torture_numops=100;
51 int torture_blocksize=1024*1024;
52 static int procnum; /* records process count number when forking */
53 static struct cli_state *current_cli;
54 static fstring randomfname;
55 static bool use_oplocks;
56 static bool use_level_II_oplocks;
57 static const char *client_txt = "client_oplocks.txt";
58 static bool use_kerberos;
59 static fstring multishare_conn_fname;
60 static bool use_multishare_conn = False;
61 static bool do_encrypt;
62 static const char *local_path = NULL;
63 static int signing_state = Undefined;
66 bool torture_showall = False;
68 static double create_procs(bool (*fn)(int), bool *result);
71 /* return a pointer to a anonymous shared memory segment of size "size"
72 which will persist across fork() but will disappear when all processes
75 The memory is not zeroed
77 This function uses system5 shared memory. It takes advantage of a property
78 that the memory is not destroyed if it is attached when the id is removed
80 void *shm_setup(int size)
86 shmid = shm_open("private", O_RDWR | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR);
88 printf("can't get shared memory\n");
91 shm_unlink("private");
92 if (ftruncate(shmid, size) == -1) {
93 printf("can't set shared memory size\n");
96 ret = mmap(0, size, PROT_READ | PROT_WRITE, MAP_SHARED, shmid, 0);
97 if (ret == MAP_FAILED) {
98 printf("can't map shared memory\n");
102 shmid = shmget(IPC_PRIVATE, size, S_IRUSR | S_IWUSR);
104 printf("can't get shared memory\n");
107 ret = (void *)shmat(shmid, 0, 0);
108 if (!ret || ret == (void *)-1) {
109 printf("can't attach to shared memory\n");
112 /* the following releases the ipc, but note that this process
113 and all its children will still have access to the memory, its
114 just that the shmid is no longer valid for other shm calls. This
115 means we don't leave behind lots of shm segments after we exit
117 See Stevens "advanced programming in unix env" for details
119 shmctl(shmid, IPC_RMID, 0);
125 /********************************************************************
126 Ensure a connection is encrypted.
127 ********************************************************************/
129 static bool force_cli_encryption(struct cli_state *c,
130 const char *sharename)
133 uint32 caplow, caphigh;
136 if (!SERVER_HAS_UNIX_CIFS(c)) {
137 d_printf("Encryption required and "
138 "server that doesn't support "
139 "UNIX extensions - failing connect\n");
143 status = cli_unix_extensions_version(c, &major, &minor, &caplow,
145 if (!NT_STATUS_IS_OK(status)) {
146 d_printf("Encryption required and "
147 "can't get UNIX CIFS extensions "
148 "version from server: %s\n", nt_errstr(status));
152 if (!(caplow & CIFS_UNIX_TRANSPORT_ENCRYPTION_CAP)) {
153 d_printf("Encryption required and "
154 "share %s doesn't support "
155 "encryption.\n", sharename);
159 if (c->use_kerberos) {
160 status = cli_gss_smb_encryption_start(c);
162 status = cli_raw_ntlm_smb_encryption_start(c,
168 if (!NT_STATUS_IS_OK(status)) {
169 d_printf("Encryption required and "
170 "setup failed with error %s.\n",
179 static struct cli_state *open_nbt_connection(void)
184 status = cli_connect_nb(host, NULL, port_to_use, 0x20, myname,
186 if (!NT_STATUS_IS_OK(status)) {
187 printf("Failed to connect with %s. Error %s\n", host, nt_errstr(status) );
191 c->use_kerberos = use_kerberos;
193 c->timeout = 120000; /* set a really long timeout (2 minutes) */
194 if (use_oplocks) c->use_oplocks = True;
195 if (use_level_II_oplocks) c->use_level_II_oplocks = True;
200 /****************************************************************************
201 Send a corrupt session request. See rfc1002.txt 4.3 and 4.3.2.
202 ****************************************************************************/
204 static bool cli_bad_session_request(int fd,
205 struct nmb_name *calling, struct nmb_name *called)
214 uint8_t message_type;
217 frame = talloc_stackframe();
219 iov[0].iov_base = len_buf;
220 iov[0].iov_len = sizeof(len_buf);
222 /* put in the destination name */
224 iov[1].iov_base = name_mangle(talloc_tos(), called->name,
226 if (iov[1].iov_base == NULL) {
229 iov[1].iov_len = name_len((unsigned char *)iov[1].iov_base,
230 talloc_get_size(iov[1].iov_base));
234 iov[2].iov_base = name_mangle(talloc_tos(), calling->name,
236 if (iov[2].iov_base == NULL) {
239 iov[2].iov_len = name_len((unsigned char *)iov[2].iov_base,
240 talloc_get_size(iov[2].iov_base));
242 /* Deliberately corrupt the name len (first byte) */
243 *((uint8_t *)iov[2].iov_base) = 100;
245 /* send a session request (RFC 1002) */
246 /* setup the packet length
247 * Remove four bytes from the length count, since the length
248 * field in the NBT Session Service header counts the number
249 * of bytes which follow. The cli_send_smb() function knows
250 * about this and accounts for those four bytes.
254 _smb_setlen(len_buf, iov[1].iov_len + iov[2].iov_len);
255 SCVAL(len_buf,0,0x81);
257 len = write_data_iov(fd, iov, 3);
261 len = read_smb(fd, talloc_tos(), &inbuf, &err);
267 message_type = CVAL(inbuf, 0);
268 if (message_type != 0x83) {
269 d_fprintf(stderr, "Expected msg type 0x83, got 0x%2.2x\n",
274 if (smb_len(inbuf) != 1) {
275 d_fprintf(stderr, "Expected smb_len 1, got %d\n",
276 (int)smb_len(inbuf));
280 error = CVAL(inbuf, 4);
282 d_fprintf(stderr, "Expected error 0x82, got %d\n",
293 /* Insert a NULL at the first separator of the given path and return a pointer
294 * to the remainder of the string.
297 terminate_path_at_separator(char * path)
305 if ((p = strchr_m(path, '/'))) {
310 if ((p = strchr_m(path, '\\'))) {
320 parse a //server/share type UNC name
322 bool smbcli_parse_unc(const char *unc_name, TALLOC_CTX *mem_ctx,
323 char **hostname, char **sharename)
327 *hostname = *sharename = NULL;
329 if (strncmp(unc_name, "\\\\", 2) &&
330 strncmp(unc_name, "//", 2)) {
334 *hostname = talloc_strdup(mem_ctx, &unc_name[2]);
335 p = terminate_path_at_separator(*hostname);
338 *sharename = talloc_strdup(mem_ctx, p);
339 terminate_path_at_separator(*sharename);
342 if (*hostname && *sharename) {
346 TALLOC_FREE(*hostname);
347 TALLOC_FREE(*sharename);
351 static bool torture_open_connection_share(struct cli_state **c,
352 const char *hostname,
353 const char *sharename)
359 flags |= CLI_FULL_CONNECTION_USE_KERBEROS;
361 flags |= CLI_FULL_CONNECTION_OPLOCKS;
362 if (use_level_II_oplocks)
363 flags |= CLI_FULL_CONNECTION_LEVEL_II_OPLOCKS;
365 status = cli_full_connection(c, myname,
366 hostname, NULL, port_to_use,
369 password, flags, signing_state);
370 if (!NT_STATUS_IS_OK(status)) {
371 printf("failed to open share connection: //%s/%s port:%d - %s\n",
372 hostname, sharename, port_to_use, nt_errstr(status));
376 (*c)->timeout = 120000; /* set a really long timeout (2 minutes) */
379 return force_cli_encryption(*c,
385 bool torture_open_connection(struct cli_state **c, int conn_index)
387 char **unc_list = NULL;
388 int num_unc_names = 0;
391 if (use_multishare_conn==True) {
393 unc_list = file_lines_load(multishare_conn_fname, &num_unc_names, 0, NULL);
394 if (!unc_list || num_unc_names <= 0) {
395 printf("Failed to load unc names list from '%s'\n", multishare_conn_fname);
399 if (!smbcli_parse_unc(unc_list[conn_index % num_unc_names],
401 printf("Failed to parse UNC name %s\n",
402 unc_list[conn_index % num_unc_names]);
403 TALLOC_FREE(unc_list);
407 result = torture_open_connection_share(c, h, s);
409 /* h, s were copied earlier */
410 TALLOC_FREE(unc_list);
414 return torture_open_connection_share(c, host, share);
417 bool torture_init_connection(struct cli_state **pcli)
419 struct cli_state *cli;
421 cli = open_nbt_connection();
430 bool torture_cli_session_setup2(struct cli_state *cli, uint16 *new_vuid)
432 uint16 old_vuid = cli->vuid;
433 fstring old_user_name;
434 size_t passlen = strlen(password);
438 fstrcpy(old_user_name, cli->user_name);
440 ret = NT_STATUS_IS_OK(cli_session_setup(cli, username,
444 *new_vuid = cli->vuid;
445 cli->vuid = old_vuid;
446 status = cli_set_username(cli, old_user_name);
447 if (!NT_STATUS_IS_OK(status)) {
454 bool torture_close_connection(struct cli_state *c)
459 status = cli_tdis(c);
460 if (!NT_STATUS_IS_OK(status)) {
461 printf("tdis failed (%s)\n", nt_errstr(status));
471 /* check if the server produced the expected dos or nt error code */
472 static bool check_both_error(int line, NTSTATUS status,
473 uint8 eclass, uint32 ecode, NTSTATUS nterr)
475 if (NT_STATUS_IS_DOS(status)) {
479 /* Check DOS error */
480 cclass = NT_STATUS_DOS_CLASS(status);
481 num = NT_STATUS_DOS_CODE(status);
483 if (eclass != cclass || ecode != num) {
484 printf("unexpected error code class=%d code=%d\n",
485 (int)cclass, (int)num);
486 printf(" expected %d/%d %s (line=%d)\n",
487 (int)eclass, (int)ecode, nt_errstr(nterr), line);
492 if (!NT_STATUS_EQUAL(nterr, status)) {
493 printf("unexpected error code %s\n",
495 printf(" expected %s (line=%d)\n",
496 nt_errstr(nterr), line);
505 /* check if the server produced the expected error code */
506 static bool check_error(int line, struct cli_state *c,
507 uint8 eclass, uint32 ecode, NTSTATUS nterr)
509 if (cli_is_dos_error(c)) {
513 /* Check DOS error */
515 cli_dos_error(c, &cclass, &num);
517 if (eclass != cclass || ecode != num) {
518 printf("unexpected error code class=%d code=%d\n",
519 (int)cclass, (int)num);
520 printf(" expected %d/%d %s (line=%d)\n",
521 (int)eclass, (int)ecode, nt_errstr(nterr), line);
530 status = cli_nt_error(c);
532 if (NT_STATUS_V(nterr) != NT_STATUS_V(status)) {
533 printf("unexpected error code %s\n", nt_errstr(status));
534 printf(" expected %s (line=%d)\n", nt_errstr(nterr), line);
543 static bool wait_lock(struct cli_state *c, int fnum, uint32 offset, uint32 len)
547 status = cli_lock32(c, fnum, offset, len, -1, WRITE_LOCK);
549 while (!NT_STATUS_IS_OK(status)) {
550 if (!check_both_error(__LINE__, status, ERRDOS,
551 ERRlock, NT_STATUS_LOCK_NOT_GRANTED)) {
555 status = cli_lock32(c, fnum, offset, len, -1, WRITE_LOCK);
562 static bool rw_torture(struct cli_state *c)
564 const char *lockfname = "\\torture.lck";
568 pid_t pid2, pid = getpid();
575 memset(buf, '\0', sizeof(buf));
577 status = cli_open(c, lockfname, O_RDWR | O_CREAT | O_EXCL,
579 if (!NT_STATUS_IS_OK(status)) {
580 status = cli_open(c, lockfname, O_RDWR, DENY_NONE, &fnum2);
582 if (!NT_STATUS_IS_OK(status)) {
583 printf("open of %s failed (%s)\n",
584 lockfname, nt_errstr(status));
588 for (i=0;i<torture_numops;i++) {
589 unsigned n = (unsigned)sys_random()%10;
592 printf("%d\r", i); fflush(stdout);
594 slprintf(fname, sizeof(fstring) - 1, "\\torture.%u", n);
596 if (!wait_lock(c, fnum2, n*sizeof(int), sizeof(int))) {
600 status = cli_open(c, fname, O_RDWR | O_CREAT | O_TRUNC,
602 if (!NT_STATUS_IS_OK(status)) {
603 printf("open failed (%s)\n", nt_errstr(status));
608 status = cli_writeall(c, fnum, 0, (uint8_t *)&pid, 0,
610 if (!NT_STATUS_IS_OK(status)) {
611 printf("write failed (%s)\n", nt_errstr(status));
616 status = cli_writeall(c, fnum, 0, (uint8_t *)buf,
617 sizeof(pid)+(j*sizeof(buf)),
619 if (!NT_STATUS_IS_OK(status)) {
620 printf("write failed (%s)\n",
628 status = cli_read(c, fnum, (char *)&pid2, 0, sizeof(pid),
630 if (!NT_STATUS_IS_OK(status)) {
631 printf("read failed (%s)\n", nt_errstr(status));
633 } else if (nread != sizeof(pid)) {
634 printf("read/write compare failed: "
635 "recv %ld req %ld\n", (unsigned long)nread,
636 (unsigned long)sizeof(pid));
641 printf("data corruption!\n");
645 status = cli_close(c, fnum);
646 if (!NT_STATUS_IS_OK(status)) {
647 printf("close failed (%s)\n", nt_errstr(status));
651 status = cli_unlink(c, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
652 if (!NT_STATUS_IS_OK(status)) {
653 printf("unlink failed (%s)\n", nt_errstr(status));
657 status = cli_unlock(c, fnum2, n*sizeof(int), sizeof(int));
658 if (!NT_STATUS_IS_OK(status)) {
659 printf("unlock failed (%s)\n", nt_errstr(status));
665 cli_unlink(c, lockfname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
672 static bool run_torture(int dummy)
674 struct cli_state *cli;
679 cli_sockopt(cli, sockops);
681 ret = rw_torture(cli);
683 if (!torture_close_connection(cli)) {
690 static bool rw_torture3(struct cli_state *c, char *lockfname)
692 uint16_t fnum = (uint16_t)-1;
697 unsigned countprev = 0;
700 NTSTATUS status = NT_STATUS_OK;
703 for (i = 0; i < sizeof(buf); i += sizeof(uint32))
705 SIVAL(buf, i, sys_random());
712 FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
713 if (!NT_STATUS_IS_OK(status)) {
714 printf("unlink failed (%s) (normal, this file should "
715 "not exist)\n", nt_errstr(status));
718 status = cli_open(c, lockfname, O_RDWR | O_CREAT | O_EXCL,
720 if (!NT_STATUS_IS_OK(status)) {
721 printf("first open read/write of %s failed (%s)\n",
722 lockfname, nt_errstr(status));
728 for (i = 0; i < 500 && fnum == (uint16_t)-1; i++)
730 status = cli_open(c, lockfname, O_RDONLY,
732 if (!NT_STATUS_IS_OK(status)) {
737 if (!NT_STATUS_IS_OK(status)) {
738 printf("second open read-only of %s failed (%s)\n",
739 lockfname, nt_errstr(status));
745 for (count = 0; count < sizeof(buf); count += sent)
747 if (count >= countprev) {
748 printf("%d %8d\r", i, count);
751 countprev += (sizeof(buf) / 20);
756 sent = ((unsigned)sys_random()%(20))+ 1;
757 if (sent > sizeof(buf) - count)
759 sent = sizeof(buf) - count;
762 status = cli_writeall(c, fnum, 0, (uint8_t *)buf+count,
764 if (!NT_STATUS_IS_OK(status)) {
765 printf("write failed (%s)\n",
772 status = cli_read(c, fnum, buf_rd+count, count,
773 sizeof(buf)-count, &sent);
774 if(!NT_STATUS_IS_OK(status)) {
775 printf("read failed offset:%d size:%ld (%s)\n",
776 count, (unsigned long)sizeof(buf)-count,
780 } else if (sent > 0) {
781 if (memcmp(buf_rd+count, buf+count, sent) != 0)
783 printf("read/write compare failed\n");
784 printf("offset: %d req %ld recvd %ld\n", count, (unsigned long)sizeof(buf)-count, (unsigned long)sent);
793 status = cli_close(c, fnum);
794 if (!NT_STATUS_IS_OK(status)) {
795 printf("close failed (%s)\n", nt_errstr(status));
802 static bool rw_torture2(struct cli_state *c1, struct cli_state *c2)
804 const char *lockfname = "\\torture2.lck";
814 status = cli_unlink(c1, lockfname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
815 if (!NT_STATUS_IS_OK(status)) {
816 printf("unlink failed (%s) (normal, this file should not exist)\n", nt_errstr(status));
819 status = cli_open(c1, lockfname, O_RDWR | O_CREAT | O_EXCL,
821 if (!NT_STATUS_IS_OK(status)) {
822 printf("first open read/write of %s failed (%s)\n",
823 lockfname, nt_errstr(status));
827 status = cli_open(c2, lockfname, O_RDONLY, DENY_NONE, &fnum2);
828 if (!NT_STATUS_IS_OK(status)) {
829 printf("second open read-only of %s failed (%s)\n",
830 lockfname, nt_errstr(status));
831 cli_close(c1, fnum1);
835 for (i = 0; i < torture_numops; i++)
837 size_t buf_size = ((unsigned)sys_random()%(sizeof(buf)-1))+ 1;
839 printf("%d\r", i); fflush(stdout);
842 generate_random_buffer((unsigned char *)buf, buf_size);
844 status = cli_writeall(c1, fnum1, 0, (uint8_t *)buf, 0,
846 if (!NT_STATUS_IS_OK(status)) {
847 printf("write failed (%s)\n", nt_errstr(status));
852 if ((bytes_read = cli_read_old(c2, fnum2, buf_rd, 0, buf_size)) != buf_size) {
853 printf("read failed (%s)\n", cli_errstr(c2));
854 printf("read %d, expected %ld\n", (int)bytes_read,
855 (unsigned long)buf_size);
860 if (memcmp(buf_rd, buf, buf_size) != 0)
862 printf("read/write compare failed\n");
868 status = cli_close(c2, fnum2);
869 if (!NT_STATUS_IS_OK(status)) {
870 printf("close failed (%s)\n", nt_errstr(status));
874 status = cli_close(c1, fnum1);
875 if (!NT_STATUS_IS_OK(status)) {
876 printf("close failed (%s)\n", nt_errstr(status));
880 status = cli_unlink(c1, lockfname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
881 if (!NT_STATUS_IS_OK(status)) {
882 printf("unlink failed (%s)\n", nt_errstr(status));
889 static bool run_readwritetest(int dummy)
891 struct cli_state *cli1, *cli2;
892 bool test1, test2 = False;
894 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
897 cli_sockopt(cli1, sockops);
898 cli_sockopt(cli2, sockops);
900 printf("starting readwritetest\n");
902 test1 = rw_torture2(cli1, cli2);
903 printf("Passed readwritetest v1: %s\n", BOOLSTR(test1));
906 test2 = rw_torture2(cli1, cli1);
907 printf("Passed readwritetest v2: %s\n", BOOLSTR(test2));
910 if (!torture_close_connection(cli1)) {
914 if (!torture_close_connection(cli2)) {
918 return (test1 && test2);
921 static bool run_readwritemulti(int dummy)
923 struct cli_state *cli;
928 cli_sockopt(cli, sockops);
930 printf("run_readwritemulti: fname %s\n", randomfname);
931 test = rw_torture3(cli, randomfname);
933 if (!torture_close_connection(cli)) {
940 static bool run_readwritelarge_internal(int max_xmit_k)
942 static struct cli_state *cli1;
944 const char *lockfname = "\\large.dat";
950 if (!torture_open_connection(&cli1, 0)) {
953 cli_sockopt(cli1, sockops);
954 memset(buf,'\0',sizeof(buf));
956 cli1->max_xmit = max_xmit_k*1024;
958 if (signing_state == Required) {
959 /* Horrible cheat to force
960 multiple signed outstanding
961 packets against a Samba server.
963 cli1->is_samba = false;
966 printf("starting readwritelarge_internal\n");
968 cli_unlink(cli1, lockfname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
970 status = cli_open(cli1, lockfname, O_RDWR | O_CREAT | O_EXCL,
972 if (!NT_STATUS_IS_OK(status)) {
973 printf("open read/write of %s failed (%s)\n", lockfname, nt_errstr(status));
977 cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 0, sizeof(buf), NULL);
979 status = cli_qfileinfo_basic(cli1, fnum1, NULL, &fsize, NULL, NULL,
981 if (!NT_STATUS_IS_OK(status)) {
982 printf("qfileinfo failed (%s)\n", nt_errstr(status));
986 if (fsize == sizeof(buf))
987 printf("readwritelarge_internal test 1 succeeded (size = %lx)\n",
988 (unsigned long)fsize);
990 printf("readwritelarge_internal test 1 failed (size = %lx)\n",
991 (unsigned long)fsize);
995 status = cli_close(cli1, fnum1);
996 if (!NT_STATUS_IS_OK(status)) {
997 printf("close failed (%s)\n", nt_errstr(status));
1001 status = cli_unlink(cli1, lockfname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1002 if (!NT_STATUS_IS_OK(status)) {
1003 printf("unlink failed (%s)\n", nt_errstr(status));
1007 status = cli_open(cli1, lockfname, O_RDWR | O_CREAT | O_EXCL,
1009 if (!NT_STATUS_IS_OK(status)) {
1010 printf("open read/write of %s failed (%s)\n", lockfname, nt_errstr(status));
1014 cli1->max_xmit = 4*1024;
1016 cli_smbwrite(cli1, fnum1, buf, 0, sizeof(buf), NULL);
1018 status = cli_qfileinfo_basic(cli1, fnum1, NULL, &fsize, NULL, NULL,
1020 if (!NT_STATUS_IS_OK(status)) {
1021 printf("qfileinfo failed (%s)\n", nt_errstr(status));
1025 if (fsize == sizeof(buf))
1026 printf("readwritelarge_internal test 2 succeeded (size = %lx)\n",
1027 (unsigned long)fsize);
1029 printf("readwritelarge_internal test 2 failed (size = %lx)\n",
1030 (unsigned long)fsize);
1035 /* ToDo - set allocation. JRA */
1036 if(!cli_set_allocation_size(cli1, fnum1, 0)) {
1037 printf("set allocation size to zero failed (%s)\n", cli_errstr(&cli1));
1040 if (!cli_qfileinfo_basic(cli1, fnum1, NULL, &fsize, NULL, NULL, NULL,
1042 printf("qfileinfo failed (%s)\n", cli_errstr(cli1));
1046 printf("readwritelarge test 3 (truncate test) succeeded (size = %x)\n", fsize);
1049 status = cli_close(cli1, fnum1);
1050 if (!NT_STATUS_IS_OK(status)) {
1051 printf("close failed (%s)\n", nt_errstr(status));
1055 if (!torture_close_connection(cli1)) {
1061 static bool run_readwritelarge(int dummy)
1063 return run_readwritelarge_internal(128);
1066 static bool run_readwritelarge_signtest(int dummy)
1069 signing_state = Required;
1070 ret = run_readwritelarge_internal(2);
1071 signing_state = Undefined;
1078 #define ival(s) strtol(s, NULL, 0)
1080 /* run a test that simulates an approximate netbench client load */
1081 static bool run_netbench(int client)
1083 struct cli_state *cli;
1088 const char *params[20];
1089 bool correct = True;
1095 cli_sockopt(cli, sockops);
1099 slprintf(cname,sizeof(cname)-1, "client%d", client);
1101 f = fopen(client_txt, "r");
1108 while (fgets(line, sizeof(line)-1, f)) {
1112 line[strlen(line)-1] = 0;
1114 /* printf("[%d] %s\n", line_count, line); */
1116 all_string_sub(line,"client1", cname, sizeof(line));
1118 /* parse the command parameters */
1119 params[0] = strtok_r(line, " ", &saveptr);
1121 while (params[i]) params[++i] = strtok_r(NULL, " ", &saveptr);
1125 if (i < 2) continue;
1127 if (!strncmp(params[0],"SMB", 3)) {
1128 printf("ERROR: You are using a dbench 1 load file\n");
1132 if (!strcmp(params[0],"NTCreateX")) {
1133 nb_createx(params[1], ival(params[2]), ival(params[3]),
1135 } else if (!strcmp(params[0],"Close")) {
1136 nb_close(ival(params[1]));
1137 } else if (!strcmp(params[0],"Rename")) {
1138 nb_rename(params[1], params[2]);
1139 } else if (!strcmp(params[0],"Unlink")) {
1140 nb_unlink(params[1]);
1141 } else if (!strcmp(params[0],"Deltree")) {
1142 nb_deltree(params[1]);
1143 } else if (!strcmp(params[0],"Rmdir")) {
1144 nb_rmdir(params[1]);
1145 } else if (!strcmp(params[0],"QUERY_PATH_INFORMATION")) {
1146 nb_qpathinfo(params[1]);
1147 } else if (!strcmp(params[0],"QUERY_FILE_INFORMATION")) {
1148 nb_qfileinfo(ival(params[1]));
1149 } else if (!strcmp(params[0],"QUERY_FS_INFORMATION")) {
1150 nb_qfsinfo(ival(params[1]));
1151 } else if (!strcmp(params[0],"FIND_FIRST")) {
1152 nb_findfirst(params[1]);
1153 } else if (!strcmp(params[0],"WriteX")) {
1154 nb_writex(ival(params[1]),
1155 ival(params[2]), ival(params[3]), ival(params[4]));
1156 } else if (!strcmp(params[0],"ReadX")) {
1157 nb_readx(ival(params[1]),
1158 ival(params[2]), ival(params[3]), ival(params[4]));
1159 } else if (!strcmp(params[0],"Flush")) {
1160 nb_flush(ival(params[1]));
1162 printf("Unknown operation %s\n", params[0]);
1170 if (!torture_close_connection(cli)) {
1178 /* run a test that simulates an approximate netbench client load */
1179 static bool run_nbench(int dummy)
1182 bool correct = True;
1188 signal(SIGALRM, nb_alarm);
1190 t = create_procs(run_netbench, &correct);
1193 printf("\nThroughput %g MB/sec\n",
1194 1.0e-6 * nbio_total() / t);
1200 This test checks for two things:
1202 1) correct support for retaining locks over a close (ie. the server
1203 must not use posix semantics)
1204 2) support for lock timeouts
1206 static bool run_locktest1(int dummy)
1208 struct cli_state *cli1, *cli2;
1209 const char *fname = "\\lockt1.lck";
1210 uint16_t fnum1, fnum2, fnum3;
1212 unsigned lock_timeout;
1215 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
1218 cli_sockopt(cli1, sockops);
1219 cli_sockopt(cli2, sockops);
1221 printf("starting locktest1\n");
1223 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1225 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
1227 if (!NT_STATUS_IS_OK(status)) {
1228 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
1232 status = cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum2);
1233 if (!NT_STATUS_IS_OK(status)) {
1234 printf("open2 of %s failed (%s)\n", fname, nt_errstr(status));
1238 status = cli_open(cli2, fname, O_RDWR, DENY_NONE, &fnum3);
1239 if (!NT_STATUS_IS_OK(status)) {
1240 printf("open3 of %s failed (%s)\n", fname, nt_errstr(status));
1244 status = cli_lock32(cli1, fnum1, 0, 4, 0, WRITE_LOCK);
1245 if (!NT_STATUS_IS_OK(status)) {
1246 printf("lock1 failed (%s)\n", nt_errstr(status));
1250 status = cli_lock32(cli2, fnum3, 0, 4, 0, WRITE_LOCK);
1251 if (NT_STATUS_IS_OK(status)) {
1252 printf("lock2 succeeded! This is a locking bug\n");
1255 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1256 NT_STATUS_LOCK_NOT_GRANTED)) {
1261 lock_timeout = (1 + (random() % 20));
1262 printf("Testing lock timeout with timeout=%u\n", lock_timeout);
1264 status = cli_lock32(cli2, fnum3, 0, 4, lock_timeout * 1000, WRITE_LOCK);
1265 if (NT_STATUS_IS_OK(status)) {
1266 printf("lock3 succeeded! This is a locking bug\n");
1269 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1270 NT_STATUS_FILE_LOCK_CONFLICT)) {
1276 if (ABS(t2 - t1) < lock_timeout-1) {
1277 printf("error: This server appears not to support timed lock requests\n");
1280 printf("server slept for %u seconds for a %u second timeout\n",
1281 (unsigned int)(t2-t1), lock_timeout);
1283 status = cli_close(cli1, fnum2);
1284 if (!NT_STATUS_IS_OK(status)) {
1285 printf("close1 failed (%s)\n", nt_errstr(status));
1289 status = cli_lock32(cli2, fnum3, 0, 4, 0, WRITE_LOCK);
1290 if (NT_STATUS_IS_OK(status)) {
1291 printf("lock4 succeeded! This is a locking bug\n");
1294 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1295 NT_STATUS_FILE_LOCK_CONFLICT)) {
1300 status = cli_close(cli1, fnum1);
1301 if (!NT_STATUS_IS_OK(status)) {
1302 printf("close2 failed (%s)\n", nt_errstr(status));
1306 status = cli_close(cli2, fnum3);
1307 if (!NT_STATUS_IS_OK(status)) {
1308 printf("close3 failed (%s)\n", nt_errstr(status));
1312 status = cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1313 if (!NT_STATUS_IS_OK(status)) {
1314 printf("unlink failed (%s)\n", nt_errstr(status));
1319 if (!torture_close_connection(cli1)) {
1323 if (!torture_close_connection(cli2)) {
1327 printf("Passed locktest1\n");
1332 this checks to see if a secondary tconx can use open files from an
1335 static bool run_tcon_test(int dummy)
1337 static struct cli_state *cli;
1338 const char *fname = "\\tcontest.tmp";
1340 uint16 cnum1, cnum2, cnum3;
1341 uint16 vuid1, vuid2;
1346 memset(buf, '\0', sizeof(buf));
1348 if (!torture_open_connection(&cli, 0)) {
1351 cli_sockopt(cli, sockops);
1353 printf("starting tcontest\n");
1355 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1357 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
1358 if (!NT_STATUS_IS_OK(status)) {
1359 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
1363 cnum1 = cli_state_get_tid(cli);
1366 status = cli_writeall(cli, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
1367 if (!NT_STATUS_IS_OK(status)) {
1368 printf("initial write failed (%s)", nt_errstr(status));
1372 status = cli_tcon_andx(cli, share, "?????",
1373 password, strlen(password)+1);
1374 if (!NT_STATUS_IS_OK(status)) {
1375 printf("%s refused 2nd tree connect (%s)\n", host,
1381 cnum2 = cli_state_get_tid(cli);
1382 cnum3 = MAX(cnum1, cnum2) + 1; /* any invalid number */
1383 vuid2 = cli->vuid + 1;
1385 /* try a write with the wrong tid */
1386 cli_state_set_tid(cli, cnum2);
1388 status = cli_writeall(cli, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
1389 if (NT_STATUS_IS_OK(status)) {
1390 printf("* server allows write with wrong TID\n");
1393 printf("server fails write with wrong TID : %s\n",
1398 /* try a write with an invalid tid */
1399 cli_state_set_tid(cli, cnum3);
1401 status = cli_writeall(cli, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
1402 if (NT_STATUS_IS_OK(status)) {
1403 printf("* server allows write with invalid TID\n");
1406 printf("server fails write with invalid TID : %s\n",
1410 /* try a write with an invalid vuid */
1412 cli_state_set_tid(cli, cnum1);
1414 status = cli_writeall(cli, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
1415 if (NT_STATUS_IS_OK(status)) {
1416 printf("* server allows write with invalid VUID\n");
1419 printf("server fails write with invalid VUID : %s\n",
1423 cli_state_set_tid(cli, cnum1);
1426 status = cli_close(cli, fnum1);
1427 if (!NT_STATUS_IS_OK(status)) {
1428 printf("close failed (%s)\n", nt_errstr(status));
1432 cli_state_set_tid(cli, cnum2);
1434 status = cli_tdis(cli);
1435 if (!NT_STATUS_IS_OK(status)) {
1436 printf("secondary tdis failed (%s)\n", nt_errstr(status));
1440 cli_state_set_tid(cli, cnum1);
1442 if (!torture_close_connection(cli)) {
1451 checks for old style tcon support
1453 static bool run_tcon2_test(int dummy)
1455 static struct cli_state *cli;
1456 uint16 cnum, max_xmit;
1460 if (!torture_open_connection(&cli, 0)) {
1463 cli_sockopt(cli, sockops);
1465 printf("starting tcon2 test\n");
1467 if (asprintf(&service, "\\\\%s\\%s", host, share) == -1) {
1471 status = cli_raw_tcon(cli, service, password, "?????", &max_xmit, &cnum);
1475 if (!NT_STATUS_IS_OK(status)) {
1476 printf("tcon2 failed : %s\n", nt_errstr(status));
1478 printf("tcon OK : max_xmit=%d cnum=%d\n",
1479 (int)max_xmit, (int)cnum);
1482 if (!torture_close_connection(cli)) {
1486 printf("Passed tcon2 test\n");
1490 static bool tcon_devtest(struct cli_state *cli,
1491 const char *myshare, const char *devtype,
1492 const char *return_devtype,
1493 NTSTATUS expected_error)
1498 status = cli_tcon_andx(cli, myshare, devtype,
1499 password, strlen(password)+1);
1501 if (NT_STATUS_IS_OK(expected_error)) {
1502 if (NT_STATUS_IS_OK(status)) {
1503 if (strcmp(cli->dev, return_devtype) == 0) {
1506 printf("tconX to share %s with type %s "
1507 "succeeded but returned the wrong "
1508 "device type (got [%s] but should have got [%s])\n",
1509 myshare, devtype, cli->dev, return_devtype);
1513 printf("tconX to share %s with type %s "
1514 "should have succeeded but failed\n",
1520 if (NT_STATUS_IS_OK(status)) {
1521 printf("tconx to share %s with type %s "
1522 "should have failed but succeeded\n",
1526 if (NT_STATUS_EQUAL(cli_nt_error(cli),
1530 printf("Returned unexpected error\n");
1539 checks for correct tconX support
1541 static bool run_tcon_devtype_test(int dummy)
1543 static struct cli_state *cli1 = NULL;
1548 status = cli_full_connection(&cli1, myname,
1549 host, NULL, port_to_use,
1551 username, workgroup,
1552 password, flags, signing_state);
1554 if (!NT_STATUS_IS_OK(status)) {
1555 printf("could not open connection\n");
1559 if (!tcon_devtest(cli1, "IPC$", "A:", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1562 if (!tcon_devtest(cli1, "IPC$", "?????", "IPC", NT_STATUS_OK))
1565 if (!tcon_devtest(cli1, "IPC$", "LPT:", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1568 if (!tcon_devtest(cli1, "IPC$", "IPC", "IPC", NT_STATUS_OK))
1571 if (!tcon_devtest(cli1, "IPC$", "FOOBA", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1574 if (!tcon_devtest(cli1, share, "A:", "A:", NT_STATUS_OK))
1577 if (!tcon_devtest(cli1, share, "?????", "A:", NT_STATUS_OK))
1580 if (!tcon_devtest(cli1, share, "LPT:", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1583 if (!tcon_devtest(cli1, share, "IPC", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1586 if (!tcon_devtest(cli1, share, "FOOBA", NULL, NT_STATUS_BAD_DEVICE_TYPE))
1592 printf("Passed tcondevtest\n");
1599 This test checks that
1601 1) the server supports multiple locking contexts on the one SMB
1602 connection, distinguished by PID.
1604 2) the server correctly fails overlapping locks made by the same PID (this
1605 goes against POSIX behaviour, which is why it is tricky to implement)
1607 3) the server denies unlock requests by an incorrect client PID
1609 static bool run_locktest2(int dummy)
1611 static struct cli_state *cli;
1612 const char *fname = "\\lockt2.lck";
1613 uint16_t fnum1, fnum2, fnum3;
1614 bool correct = True;
1617 if (!torture_open_connection(&cli, 0)) {
1621 cli_sockopt(cli, sockops);
1623 printf("starting locktest2\n");
1625 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1629 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
1630 if (!NT_STATUS_IS_OK(status)) {
1631 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
1635 status = cli_open(cli, fname, O_RDWR, DENY_NONE, &fnum2);
1636 if (!NT_STATUS_IS_OK(status)) {
1637 printf("open2 of %s failed (%s)\n", fname, nt_errstr(status));
1643 status = cli_open(cli, fname, O_RDWR, DENY_NONE, &fnum3);
1644 if (!NT_STATUS_IS_OK(status)) {
1645 printf("open3 of %s failed (%s)\n", fname, nt_errstr(status));
1651 status = cli_lock32(cli, fnum1, 0, 4, 0, WRITE_LOCK);
1652 if (!NT_STATUS_IS_OK(status)) {
1653 printf("lock1 failed (%s)\n", nt_errstr(status));
1657 status = cli_lock32(cli, fnum1, 0, 4, 0, WRITE_LOCK);
1658 if (NT_STATUS_IS_OK(status)) {
1659 printf("WRITE lock1 succeeded! This is a locking bug\n");
1662 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1663 NT_STATUS_LOCK_NOT_GRANTED)) {
1668 status = cli_lock32(cli, fnum2, 0, 4, 0, WRITE_LOCK);
1669 if (NT_STATUS_IS_OK(status)) {
1670 printf("WRITE lock2 succeeded! This is a locking bug\n");
1673 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1674 NT_STATUS_LOCK_NOT_GRANTED)) {
1679 status = cli_lock32(cli, fnum2, 0, 4, 0, READ_LOCK);
1680 if (NT_STATUS_IS_OK(status)) {
1681 printf("READ lock2 succeeded! This is a locking bug\n");
1684 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1685 NT_STATUS_FILE_LOCK_CONFLICT)) {
1690 status = cli_lock32(cli, fnum1, 100, 4, 0, WRITE_LOCK);
1691 if (!NT_STATUS_IS_OK(status)) {
1692 printf("lock at 100 failed (%s)\n", nt_errstr(status));
1695 if (NT_STATUS_IS_OK(cli_unlock(cli, fnum1, 100, 4))) {
1696 printf("unlock at 100 succeeded! This is a locking bug\n");
1700 status = cli_unlock(cli, fnum1, 0, 4);
1701 if (NT_STATUS_IS_OK(status)) {
1702 printf("unlock1 succeeded! This is a locking bug\n");
1705 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1706 NT_STATUS_RANGE_NOT_LOCKED)) {
1711 status = cli_unlock(cli, fnum1, 0, 8);
1712 if (NT_STATUS_IS_OK(status)) {
1713 printf("unlock2 succeeded! This is a locking bug\n");
1716 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1717 NT_STATUS_RANGE_NOT_LOCKED)) {
1722 status = cli_lock32(cli, fnum3, 0, 4, 0, WRITE_LOCK);
1723 if (NT_STATUS_IS_OK(status)) {
1724 printf("lock3 succeeded! This is a locking bug\n");
1727 if (!check_both_error(__LINE__, status, ERRDOS, ERRlock,
1728 NT_STATUS_LOCK_NOT_GRANTED)) {
1735 status = cli_close(cli, fnum1);
1736 if (!NT_STATUS_IS_OK(status)) {
1737 printf("close1 failed (%s)\n", nt_errstr(status));
1741 status = cli_close(cli, fnum2);
1742 if (!NT_STATUS_IS_OK(status)) {
1743 printf("close2 failed (%s)\n", nt_errstr(status));
1747 status = cli_close(cli, fnum3);
1748 if (!NT_STATUS_IS_OK(status)) {
1749 printf("close3 failed (%s)\n", nt_errstr(status));
1753 if (!torture_close_connection(cli)) {
1757 printf("locktest2 finished\n");
1764 This test checks that
1766 1) the server supports the full offset range in lock requests
1768 static bool run_locktest3(int dummy)
1770 static struct cli_state *cli1, *cli2;
1771 const char *fname = "\\lockt3.lck";
1772 uint16_t fnum1, fnum2;
1775 bool correct = True;
1778 #define NEXT_OFFSET offset += (~(uint32)0) / torture_numops
1780 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
1783 cli_sockopt(cli1, sockops);
1784 cli_sockopt(cli2, sockops);
1786 printf("starting locktest3\n");
1788 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1790 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
1792 if (!NT_STATUS_IS_OK(status)) {
1793 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
1797 status = cli_open(cli2, fname, O_RDWR, DENY_NONE, &fnum2);
1798 if (!NT_STATUS_IS_OK(status)) {
1799 printf("open2 of %s failed (%s)\n", fname, nt_errstr(status));
1803 for (offset=i=0;i<torture_numops;i++) {
1806 status = cli_lock32(cli1, fnum1, offset-1, 1, 0, WRITE_LOCK);
1807 if (!NT_STATUS_IS_OK(status)) {
1808 printf("lock1 %d failed (%s)\n",
1814 status = cli_lock32(cli2, fnum2, offset-2, 1, 0, WRITE_LOCK);
1815 if (!NT_STATUS_IS_OK(status)) {
1816 printf("lock2 %d failed (%s)\n",
1823 for (offset=i=0;i<torture_numops;i++) {
1826 status = cli_lock32(cli1, fnum1, offset-2, 1, 0, WRITE_LOCK);
1827 if (NT_STATUS_IS_OK(status)) {
1828 printf("error: lock1 %d succeeded!\n", i);
1832 status = cli_lock32(cli2, fnum2, offset-1, 1, 0, WRITE_LOCK);
1833 if (NT_STATUS_IS_OK(status)) {
1834 printf("error: lock2 %d succeeded!\n", i);
1838 status = cli_lock32(cli1, fnum1, offset-1, 1, 0, WRITE_LOCK);
1839 if (NT_STATUS_IS_OK(status)) {
1840 printf("error: lock3 %d succeeded!\n", i);
1844 status = cli_lock32(cli2, fnum2, offset-2, 1, 0, WRITE_LOCK);
1845 if (NT_STATUS_IS_OK(status)) {
1846 printf("error: lock4 %d succeeded!\n", i);
1851 for (offset=i=0;i<torture_numops;i++) {
1854 status = cli_unlock(cli1, fnum1, offset-1, 1);
1855 if (!NT_STATUS_IS_OK(status)) {
1856 printf("unlock1 %d failed (%s)\n",
1862 status = cli_unlock(cli2, fnum2, offset-2, 1);
1863 if (!NT_STATUS_IS_OK(status)) {
1864 printf("unlock2 %d failed (%s)\n",
1871 status = cli_close(cli1, fnum1);
1872 if (!NT_STATUS_IS_OK(status)) {
1873 printf("close1 failed (%s)\n", nt_errstr(status));
1877 status = cli_close(cli2, fnum2);
1878 if (!NT_STATUS_IS_OK(status)) {
1879 printf("close2 failed (%s)\n", nt_errstr(status));
1883 status = cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1884 if (!NT_STATUS_IS_OK(status)) {
1885 printf("unlink failed (%s)\n", nt_errstr(status));
1889 if (!torture_close_connection(cli1)) {
1893 if (!torture_close_connection(cli2)) {
1897 printf("finished locktest3\n");
1902 #define EXPECTED(ret, v) if ((ret) != (v)) { \
1903 printf("** "); correct = False; \
1907 looks at overlapping locks
1909 static bool run_locktest4(int dummy)
1911 static struct cli_state *cli1, *cli2;
1912 const char *fname = "\\lockt4.lck";
1913 uint16_t fnum1, fnum2, f;
1916 bool correct = True;
1919 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
1923 cli_sockopt(cli1, sockops);
1924 cli_sockopt(cli2, sockops);
1926 printf("starting locktest4\n");
1928 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
1930 cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
1931 cli_open(cli2, fname, O_RDWR, DENY_NONE, &fnum2);
1933 memset(buf, 0, sizeof(buf));
1935 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 0, sizeof(buf),
1937 if (!NT_STATUS_IS_OK(status)) {
1938 printf("Failed to create file: %s\n", nt_errstr(status));
1943 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 4, 0, WRITE_LOCK)) &&
1944 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 2, 4, 0, WRITE_LOCK));
1945 EXPECTED(ret, False);
1946 printf("the same process %s set overlapping write locks\n", ret?"can":"cannot");
1948 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 10, 4, 0, READ_LOCK)) &&
1949 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 12, 4, 0, READ_LOCK));
1950 EXPECTED(ret, True);
1951 printf("the same process %s set overlapping read locks\n", ret?"can":"cannot");
1953 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 20, 4, 0, WRITE_LOCK)) &&
1954 NT_STATUS_IS_OK(cli_lock32(cli2, fnum2, 22, 4, 0, WRITE_LOCK));
1955 EXPECTED(ret, False);
1956 printf("a different connection %s set overlapping write locks\n", ret?"can":"cannot");
1958 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 30, 4, 0, READ_LOCK)) &&
1959 NT_STATUS_IS_OK(cli_lock32(cli2, fnum2, 32, 4, 0, READ_LOCK));
1960 EXPECTED(ret, True);
1961 printf("a different connection %s set overlapping read locks\n", ret?"can":"cannot");
1963 ret = (cli_setpid(cli1, 1),
1964 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 40, 4, 0, WRITE_LOCK))) &&
1965 (cli_setpid(cli1, 2),
1966 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 42, 4, 0, WRITE_LOCK)));
1967 EXPECTED(ret, False);
1968 printf("a different pid %s set overlapping write locks\n", ret?"can":"cannot");
1970 ret = (cli_setpid(cli1, 1),
1971 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 50, 4, 0, READ_LOCK))) &&
1972 (cli_setpid(cli1, 2),
1973 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 52, 4, 0, READ_LOCK)));
1974 EXPECTED(ret, True);
1975 printf("a different pid %s set overlapping read locks\n", ret?"can":"cannot");
1977 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 60, 4, 0, READ_LOCK)) &&
1978 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 60, 4, 0, READ_LOCK));
1979 EXPECTED(ret, True);
1980 printf("the same process %s set the same read lock twice\n", ret?"can":"cannot");
1982 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 70, 4, 0, WRITE_LOCK)) &&
1983 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 70, 4, 0, WRITE_LOCK));
1984 EXPECTED(ret, False);
1985 printf("the same process %s set the same write lock twice\n", ret?"can":"cannot");
1987 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 80, 4, 0, READ_LOCK)) &&
1988 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 80, 4, 0, WRITE_LOCK));
1989 EXPECTED(ret, False);
1990 printf("the same process %s overlay a read lock with a write lock\n", ret?"can":"cannot");
1992 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 90, 4, 0, WRITE_LOCK)) &&
1993 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 90, 4, 0, READ_LOCK));
1994 EXPECTED(ret, True);
1995 printf("the same process %s overlay a write lock with a read lock\n", ret?"can":"cannot");
1997 ret = (cli_setpid(cli1, 1),
1998 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 100, 4, 0, WRITE_LOCK))) &&
1999 (cli_setpid(cli1, 2),
2000 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 100, 4, 0, READ_LOCK)));
2001 EXPECTED(ret, False);
2002 printf("a different pid %s overlay a write lock with a read lock\n", ret?"can":"cannot");
2004 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 110, 4, 0, READ_LOCK)) &&
2005 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 112, 4, 0, READ_LOCK)) &&
2006 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 110, 6));
2007 EXPECTED(ret, False);
2008 printf("the same process %s coalesce read locks\n", ret?"can":"cannot");
2011 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 120, 4, 0, WRITE_LOCK)) &&
2012 (cli_read_old(cli2, fnum2, buf, 120, 4) == 4);
2013 EXPECTED(ret, False);
2014 printf("this server %s strict write locking\n", ret?"doesn't do":"does");
2016 status = cli_lock32(cli1, fnum1, 130, 4, 0, READ_LOCK);
2017 ret = NT_STATUS_IS_OK(status);
2019 status = cli_writeall(cli2, fnum2, 0, (uint8_t *)buf, 130, 4,
2021 ret = NT_STATUS_IS_OK(status);
2023 EXPECTED(ret, False);
2024 printf("this server %s strict read locking\n", ret?"doesn't do":"does");
2027 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 140, 4, 0, READ_LOCK)) &&
2028 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 140, 4, 0, READ_LOCK)) &&
2029 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 140, 4)) &&
2030 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 140, 4));
2031 EXPECTED(ret, True);
2032 printf("this server %s do recursive read locking\n", ret?"does":"doesn't");
2035 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 150, 4, 0, WRITE_LOCK)) &&
2036 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 150, 4, 0, READ_LOCK)) &&
2037 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 150, 4)) &&
2038 (cli_read_old(cli2, fnum2, buf, 150, 4) == 4) &&
2039 !(NT_STATUS_IS_OK(cli_writeall(cli2, fnum2, 0, (uint8_t *)buf,
2041 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 150, 4));
2042 EXPECTED(ret, True);
2043 printf("this server %s do recursive lock overlays\n", ret?"does":"doesn't");
2045 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 160, 4, 0, READ_LOCK)) &&
2046 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 160, 4)) &&
2047 NT_STATUS_IS_OK(cli_writeall(cli2, fnum2, 0, (uint8_t *)buf,
2049 (cli_read_old(cli2, fnum2, buf, 160, 4) == 4);
2050 EXPECTED(ret, True);
2051 printf("the same process %s remove a read lock using write locking\n", ret?"can":"cannot");
2053 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 170, 4, 0, WRITE_LOCK)) &&
2054 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 170, 4)) &&
2055 NT_STATUS_IS_OK(cli_writeall(cli2, fnum2, 0, (uint8_t *)buf,
2057 (cli_read_old(cli2, fnum2, buf, 170, 4) == 4);
2058 EXPECTED(ret, True);
2059 printf("the same process %s remove a write lock using read locking\n", ret?"can":"cannot");
2061 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 190, 4, 0, WRITE_LOCK)) &&
2062 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 190, 4, 0, READ_LOCK)) &&
2063 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 190, 4)) &&
2064 !NT_STATUS_IS_OK(cli_writeall(cli2, fnum2, 0, (uint8_t *)buf,
2066 (cli_read_old(cli2, fnum2, buf, 190, 4) == 4);
2067 EXPECTED(ret, True);
2068 printf("the same process %s remove the first lock first\n", ret?"does":"doesn't");
2070 cli_close(cli1, fnum1);
2071 cli_close(cli2, fnum2);
2072 cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1);
2073 cli_open(cli1, fname, O_RDWR, DENY_NONE, &f);
2074 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 8, 0, READ_LOCK)) &&
2075 NT_STATUS_IS_OK(cli_lock32(cli1, f, 0, 1, 0, READ_LOCK)) &&
2076 NT_STATUS_IS_OK(cli_close(cli1, fnum1)) &&
2077 NT_STATUS_IS_OK(cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1)) &&
2078 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 7, 1, 0, WRITE_LOCK));
2080 cli_close(cli1, fnum1);
2081 EXPECTED(ret, True);
2082 printf("the server %s have the NT byte range lock bug\n", !ret?"does":"doesn't");
2085 cli_close(cli1, fnum1);
2086 cli_close(cli2, fnum2);
2087 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2088 torture_close_connection(cli1);
2089 torture_close_connection(cli2);
2091 printf("finished locktest4\n");
2096 looks at lock upgrade/downgrade.
2098 static bool run_locktest5(int dummy)
2100 static struct cli_state *cli1, *cli2;
2101 const char *fname = "\\lockt5.lck";
2102 uint16_t fnum1, fnum2, fnum3;
2105 bool correct = True;
2108 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
2112 cli_sockopt(cli1, sockops);
2113 cli_sockopt(cli2, sockops);
2115 printf("starting locktest5\n");
2117 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2119 cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
2120 cli_open(cli2, fname, O_RDWR, DENY_NONE, &fnum2);
2121 cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum3);
2123 memset(buf, 0, sizeof(buf));
2125 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 0, sizeof(buf),
2127 if (!NT_STATUS_IS_OK(status)) {
2128 printf("Failed to create file: %s\n", nt_errstr(status));
2133 /* Check for NT bug... */
2134 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 8, 0, READ_LOCK)) &&
2135 NT_STATUS_IS_OK(cli_lock32(cli1, fnum3, 0, 1, 0, READ_LOCK));
2136 cli_close(cli1, fnum1);
2137 cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1);
2138 status = cli_lock32(cli1, fnum1, 7, 1, 0, WRITE_LOCK);
2139 ret = NT_STATUS_IS_OK(status);
2140 EXPECTED(ret, True);
2141 printf("this server %s the NT locking bug\n", ret ? "doesn't have" : "has");
2142 cli_close(cli1, fnum1);
2143 cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1);
2144 cli_unlock(cli1, fnum3, 0, 1);
2146 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 4, 0, WRITE_LOCK)) &&
2147 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 1, 1, 0, READ_LOCK));
2148 EXPECTED(ret, True);
2149 printf("the same process %s overlay a write with a read lock\n", ret?"can":"cannot");
2151 status = cli_lock32(cli2, fnum2, 0, 4, 0, READ_LOCK);
2152 ret = NT_STATUS_IS_OK(status);
2153 EXPECTED(ret, False);
2155 printf("a different processs %s get a read lock on the first process lock stack\n", ret?"can":"cannot");
2157 /* Unlock the process 2 lock. */
2158 cli_unlock(cli2, fnum2, 0, 4);
2160 status = cli_lock32(cli1, fnum3, 0, 4, 0, READ_LOCK);
2161 ret = NT_STATUS_IS_OK(status);
2162 EXPECTED(ret, False);
2164 printf("the same processs on a different fnum %s get a read lock\n", ret?"can":"cannot");
2166 /* Unlock the process 1 fnum3 lock. */
2167 cli_unlock(cli1, fnum3, 0, 4);
2169 /* Stack 2 more locks here. */
2170 ret = NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 4, 0, READ_LOCK)) &&
2171 NT_STATUS_IS_OK(cli_lock32(cli1, fnum1, 0, 4, 0, READ_LOCK));
2173 EXPECTED(ret, True);
2174 printf("the same process %s stack read locks\n", ret?"can":"cannot");
2176 /* Unlock the first process lock, then check this was the WRITE lock that was
2179 ret = NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 0, 4)) &&
2180 NT_STATUS_IS_OK(cli_lock32(cli2, fnum2, 0, 4, 0, READ_LOCK));
2182 EXPECTED(ret, True);
2183 printf("the first unlock removes the %s lock\n", ret?"WRITE":"READ");
2185 /* Unlock the process 2 lock. */
2186 cli_unlock(cli2, fnum2, 0, 4);
2188 /* We should have 3 stacked locks here. Ensure we need to do 3 unlocks. */
2190 ret = NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 1, 1)) &&
2191 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 0, 4)) &&
2192 NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 0, 4));
2194 EXPECTED(ret, True);
2195 printf("the same process %s unlock the stack of 4 locks\n", ret?"can":"cannot");
2197 /* Ensure the next unlock fails. */
2198 ret = NT_STATUS_IS_OK(cli_unlock(cli1, fnum1, 0, 4));
2199 EXPECTED(ret, False);
2200 printf("the same process %s count the lock stack\n", !ret?"can":"cannot");
2202 /* Ensure connection 2 can get a write lock. */
2203 status = cli_lock32(cli2, fnum2, 0, 4, 0, WRITE_LOCK);
2204 ret = NT_STATUS_IS_OK(status);
2205 EXPECTED(ret, True);
2207 printf("a different processs %s get a write lock on the unlocked stack\n", ret?"can":"cannot");
2211 cli_close(cli1, fnum1);
2212 cli_close(cli2, fnum2);
2213 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2214 if (!torture_close_connection(cli1)) {
2217 if (!torture_close_connection(cli2)) {
2221 printf("finished locktest5\n");
2227 tries the unusual lockingX locktype bits
2229 static bool run_locktest6(int dummy)
2231 static struct cli_state *cli;
2232 const char *fname[1] = { "\\lock6.txt" };
2237 if (!torture_open_connection(&cli, 0)) {
2241 cli_sockopt(cli, sockops);
2243 printf("starting locktest6\n");
2246 printf("Testing %s\n", fname[i]);
2248 cli_unlink(cli, fname[i], FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2250 cli_open(cli, fname[i], O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum);
2251 status = cli_locktype(cli, fnum, 0, 8, 0, LOCKING_ANDX_CHANGE_LOCKTYPE);
2252 cli_close(cli, fnum);
2253 printf("CHANGE_LOCKTYPE gave %s\n", nt_errstr(status));
2255 cli_open(cli, fname[i], O_RDWR, DENY_NONE, &fnum);
2256 status = cli_locktype(cli, fnum, 0, 8, 0, LOCKING_ANDX_CANCEL_LOCK);
2257 cli_close(cli, fnum);
2258 printf("CANCEL_LOCK gave %s\n", nt_errstr(status));
2260 cli_unlink(cli, fname[i], FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2263 torture_close_connection(cli);
2265 printf("finished locktest6\n");
2269 static bool run_locktest7(int dummy)
2271 struct cli_state *cli1;
2272 const char *fname = "\\lockt7.lck";
2275 bool correct = False;
2278 if (!torture_open_connection(&cli1, 0)) {
2282 cli_sockopt(cli1, sockops);
2284 printf("starting locktest7\n");
2286 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2288 cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
2290 memset(buf, 0, sizeof(buf));
2292 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 0, sizeof(buf),
2294 if (!NT_STATUS_IS_OK(status)) {
2295 printf("Failed to create file: %s\n", nt_errstr(status));
2299 cli_setpid(cli1, 1);
2301 status = cli_lock32(cli1, fnum1, 130, 4, 0, READ_LOCK);
2302 if (!NT_STATUS_IS_OK(status)) {
2303 printf("Unable to apply read lock on range 130:4, error was %s\n", nt_errstr(status));
2306 printf("pid1 successfully locked range 130:4 for READ\n");
2309 if (cli_read_old(cli1, fnum1, buf, 130, 4) != 4) {
2310 printf("pid1 unable to read the range 130:4, error was %s\n", cli_errstr(cli1));
2313 printf("pid1 successfully read the range 130:4\n");
2316 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
2317 if (!NT_STATUS_IS_OK(status)) {
2318 printf("pid1 unable to write to the range 130:4, error was "
2319 "%s\n", nt_errstr(status));
2320 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_LOCK_CONFLICT)) {
2321 printf("Incorrect error (should be NT_STATUS_FILE_LOCK_CONFLICT)\n");
2325 printf("pid1 successfully wrote to the range 130:4 (should be denied)\n");
2329 cli_setpid(cli1, 2);
2331 if (cli_read_old(cli1, fnum1, buf, 130, 4) != 4) {
2332 printf("pid2 unable to read the range 130:4, error was %s\n", cli_errstr(cli1));
2334 printf("pid2 successfully read the range 130:4\n");
2337 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
2338 if (!NT_STATUS_IS_OK(status)) {
2339 printf("pid2 unable to write to the range 130:4, error was "
2340 "%s\n", nt_errstr(status));
2341 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_LOCK_CONFLICT)) {
2342 printf("Incorrect error (should be NT_STATUS_FILE_LOCK_CONFLICT)\n");
2346 printf("pid2 successfully wrote to the range 130:4 (should be denied)\n");
2350 cli_setpid(cli1, 1);
2351 cli_unlock(cli1, fnum1, 130, 4);
2353 status = cli_lock32(cli1, fnum1, 130, 4, 0, WRITE_LOCK);
2354 if (!NT_STATUS_IS_OK(status)) {
2355 printf("Unable to apply write lock on range 130:4, error was %s\n", nt_errstr(status));
2358 printf("pid1 successfully locked range 130:4 for WRITE\n");
2361 if (cli_read_old(cli1, fnum1, buf, 130, 4) != 4) {
2362 printf("pid1 unable to read the range 130:4, error was %s\n", cli_errstr(cli1));
2365 printf("pid1 successfully read the range 130:4\n");
2368 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
2369 if (!NT_STATUS_IS_OK(status)) {
2370 printf("pid1 unable to write to the range 130:4, error was "
2371 "%s\n", nt_errstr(status));
2374 printf("pid1 successfully wrote to the range 130:4\n");
2377 cli_setpid(cli1, 2);
2379 if (cli_read_old(cli1, fnum1, buf, 130, 4) != 4) {
2380 printf("pid2 unable to read the range 130:4, error was %s\n", cli_errstr(cli1));
2381 if (NT_STATUS_V(cli_nt_error(cli1)) != NT_STATUS_V(NT_STATUS_FILE_LOCK_CONFLICT)) {
2382 printf("Incorrect error (should be NT_STATUS_FILE_LOCK_CONFLICT)\n");
2386 printf("pid2 successfully read the range 130:4 (should be denied)\n");
2390 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 130, 4, NULL);
2391 if (!NT_STATUS_IS_OK(status)) {
2392 printf("pid2 unable to write to the range 130:4, error was "
2393 "%s\n", nt_errstr(status));
2394 if (!NT_STATUS_EQUAL(status, NT_STATUS_FILE_LOCK_CONFLICT)) {
2395 printf("Incorrect error (should be NT_STATUS_FILE_LOCK_CONFLICT)\n");
2399 printf("pid2 successfully wrote to the range 130:4 (should be denied)\n");
2403 cli_unlock(cli1, fnum1, 130, 0);
2407 cli_close(cli1, fnum1);
2408 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2409 torture_close_connection(cli1);
2411 printf("finished locktest7\n");
2416 * This demonstrates a problem with our use of GPFS share modes: A file
2417 * descriptor sitting in the pending close queue holding a GPFS share mode
2418 * blocks opening a file another time. Happens with Word 2007 temp files.
2419 * With "posix locking = yes" and "gpfs:sharemodes = yes" enabled, the third
2420 * open is denied with NT_STATUS_SHARING_VIOLATION.
2423 static bool run_locktest8(int dummy)
2425 struct cli_state *cli1;
2426 const char *fname = "\\lockt8.lck";
2427 uint16_t fnum1, fnum2;
2429 bool correct = False;
2432 if (!torture_open_connection(&cli1, 0)) {
2436 cli_sockopt(cli1, sockops);
2438 printf("starting locktest8\n");
2440 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2442 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_WRITE,
2444 if (!NT_STATUS_IS_OK(status)) {
2445 d_fprintf(stderr, "cli_open returned %s\n", nt_errstr(status));
2449 memset(buf, 0, sizeof(buf));
2451 status = cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum2);
2452 if (!NT_STATUS_IS_OK(status)) {
2453 d_fprintf(stderr, "cli_open second time returned %s\n",
2458 status = cli_lock32(cli1, fnum2, 1, 1, 0, READ_LOCK);
2459 if (!NT_STATUS_IS_OK(status)) {
2460 printf("Unable to apply read lock on range 1:1, error was "
2461 "%s\n", nt_errstr(status));
2465 status = cli_close(cli1, fnum1);
2466 if (!NT_STATUS_IS_OK(status)) {
2467 d_fprintf(stderr, "cli_close(fnum1) %s\n", nt_errstr(status));
2471 status = cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1);
2472 if (!NT_STATUS_IS_OK(status)) {
2473 d_fprintf(stderr, "cli_open third time returned %s\n",
2481 cli_close(cli1, fnum1);
2482 cli_close(cli1, fnum2);
2483 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2484 torture_close_connection(cli1);
2486 printf("finished locktest8\n");
2491 * This test is designed to be run in conjunction with
2492 * external NFS or POSIX locks taken in the filesystem.
2493 * It checks that the smbd server will block until the
2494 * lock is released and then acquire it. JRA.
2497 static bool got_alarm;
2498 static int alarm_fd;
2500 static void alarm_handler(int dummy)
2505 static void alarm_handler_parent(int dummy)
2510 static void do_local_lock(int read_fd, int write_fd)
2515 const char *local_pathname = NULL;
2518 local_pathname = talloc_asprintf(talloc_tos(),
2519 "%s/lockt9.lck", local_path);
2520 if (!local_pathname) {
2521 printf("child: alloc fail\n");
2525 unlink(local_pathname);
2526 fd = open(local_pathname, O_RDWR|O_CREAT, 0666);
2528 printf("child: open of %s failed %s.\n",
2529 local_pathname, strerror(errno));
2533 /* Now take a fcntl lock. */
2534 lock.l_type = F_WRLCK;
2535 lock.l_whence = SEEK_SET;
2538 lock.l_pid = getpid();
2540 ret = fcntl(fd,F_SETLK,&lock);
2542 printf("child: failed to get lock 0:4 on file %s. Error %s\n",
2543 local_pathname, strerror(errno));
2546 printf("child: got lock 0:4 on file %s.\n",
2551 CatchSignal(SIGALRM, alarm_handler);
2553 /* Signal the parent. */
2554 if (write(write_fd, &c, 1) != 1) {
2555 printf("child: start signal fail %s.\n",
2562 /* Wait for the parent to be ready. */
2563 if (read(read_fd, &c, 1) != 1) {
2564 printf("child: reply signal fail %s.\n",
2572 printf("child: released lock 0:4 on file %s.\n",
2578 static bool run_locktest9(int dummy)
2580 struct cli_state *cli1;
2581 const char *fname = "\\lockt9.lck";
2583 bool correct = False;
2584 int pipe_in[2], pipe_out[2];
2588 struct timeval start;
2592 printf("starting locktest9\n");
2594 if (local_path == NULL) {
2595 d_fprintf(stderr, "locktest9 must be given a local path via -l <localpath>\n");
2599 if (pipe(pipe_in) == -1 || pipe(pipe_out) == -1) {
2604 if (child_pid == -1) {
2608 if (child_pid == 0) {
2610 do_local_lock(pipe_out[0], pipe_in[1]);
2620 ret = read(pipe_in[0], &c, 1);
2622 d_fprintf(stderr, "failed to read start signal from child. %s\n",
2627 if (!torture_open_connection(&cli1, 0)) {
2631 cli_sockopt(cli1, sockops);
2633 status = cli_open(cli1, fname, O_RDWR, DENY_NONE,
2635 if (!NT_STATUS_IS_OK(status)) {
2636 d_fprintf(stderr, "cli_open returned %s\n", nt_errstr(status));
2640 /* Ensure the child has the lock. */
2641 status = cli_lock32(cli1, fnum, 0, 4, 0, WRITE_LOCK);
2642 if (NT_STATUS_IS_OK(status)) {
2643 d_fprintf(stderr, "Got the lock on range 0:4 - this should not happen !\n");
2646 d_printf("Child has the lock.\n");
2649 /* Tell the child to wait 5 seconds then exit. */
2650 ret = write(pipe_out[1], &c, 1);
2652 d_fprintf(stderr, "failed to send exit signal to child. %s\n",
2657 /* Wait 20 seconds for the lock. */
2658 alarm_fd = cli1->fd;
2659 CatchSignal(SIGALRM, alarm_handler_parent);
2662 start = timeval_current();
2664 status = cli_lock32(cli1, fnum, 0, 4, -1, WRITE_LOCK);
2665 if (!NT_STATUS_IS_OK(status)) {
2666 d_fprintf(stderr, "Unable to apply write lock on range 0:4, error was "
2667 "%s\n", nt_errstr(status));
2672 seconds = timeval_elapsed(&start);
2674 printf("Parent got the lock after %.2f seconds.\n",
2677 status = cli_close(cli1, fnum);
2678 if (!NT_STATUS_IS_OK(status)) {
2679 d_fprintf(stderr, "cli_close(fnum1) %s\n", nt_errstr(status));
2686 cli_close(cli1, fnum);
2687 torture_close_connection(cli1);
2691 printf("finished locktest9\n");
2696 test whether fnums and tids open on one VC are available on another (a major
2699 static bool run_fdpasstest(int dummy)
2701 struct cli_state *cli1, *cli2;
2702 const char *fname = "\\fdpass.tst";
2707 if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
2710 cli_sockopt(cli1, sockops);
2711 cli_sockopt(cli2, sockops);
2713 printf("starting fdpasstest\n");
2715 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2717 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
2719 if (!NT_STATUS_IS_OK(status)) {
2720 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
2724 status = cli_writeall(cli1, fnum1, 0, (const uint8_t *)"hello world\n", 0,
2726 if (!NT_STATUS_IS_OK(status)) {
2727 printf("write failed (%s)\n", nt_errstr(status));
2731 cli2->vuid = cli1->vuid;
2732 cli_state_set_tid(cli2, cli_state_get_tid(cli1));
2733 cli_setpid(cli2, cli_getpid(cli1));
2735 if (cli_read_old(cli2, fnum1, buf, 0, 13) == 13) {
2736 printf("read succeeded! nasty security hole [%s]\n",
2741 cli_close(cli1, fnum1);
2742 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2744 torture_close_connection(cli1);
2745 torture_close_connection(cli2);
2747 printf("finished fdpasstest\n");
2751 static bool run_fdsesstest(int dummy)
2753 struct cli_state *cli;
2758 const char *fname = "\\fdsess.tst";
2759 const char *fname1 = "\\fdsess1.tst";
2766 if (!torture_open_connection(&cli, 0))
2768 cli_sockopt(cli, sockops);
2770 if (!torture_cli_session_setup2(cli, &new_vuid))
2773 saved_cnum = cli_state_get_tid(cli);
2774 if (!NT_STATUS_IS_OK(cli_tcon_andx(cli, share, "?????", "", 1)))
2776 new_cnum = cli_state_get_tid(cli);
2777 cli_state_set_tid(cli, saved_cnum);
2779 printf("starting fdsesstest\n");
2781 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2782 cli_unlink(cli, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2784 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
2785 if (!NT_STATUS_IS_OK(status)) {
2786 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
2790 status = cli_writeall(cli, fnum1, 0, (const uint8_t *)"hello world\n", 0, 13,
2792 if (!NT_STATUS_IS_OK(status)) {
2793 printf("write failed (%s)\n", nt_errstr(status));
2797 saved_vuid = cli->vuid;
2798 cli->vuid = new_vuid;
2800 if (cli_read_old(cli, fnum1, buf, 0, 13) == 13) {
2801 printf("read succeeded with different vuid! nasty security hole [%s]\n",
2805 /* Try to open a file with different vuid, samba cnum. */
2806 if (NT_STATUS_IS_OK(cli_open(cli, fname1, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum2))) {
2807 printf("create with different vuid, same cnum succeeded.\n");
2808 cli_close(cli, fnum2);
2809 cli_unlink(cli, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2811 printf("create with different vuid, same cnum failed.\n");
2812 printf("This will cause problems with service clients.\n");
2816 cli->vuid = saved_vuid;
2818 /* Try with same vuid, different cnum. */
2819 cli_state_set_tid(cli, new_cnum);
2821 if (cli_read_old(cli, fnum1, buf, 0, 13) == 13) {
2822 printf("read succeeded with different cnum![%s]\n",
2827 cli_state_set_tid(cli, saved_cnum);
2828 cli_close(cli, fnum1);
2829 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2831 torture_close_connection(cli);
2833 printf("finished fdsesstest\n");
2838 This test checks that
2840 1) the server does not allow an unlink on a file that is open
2842 static bool run_unlinktest(int dummy)
2844 struct cli_state *cli;
2845 const char *fname = "\\unlink.tst";
2847 bool correct = True;
2850 if (!torture_open_connection(&cli, 0)) {
2854 cli_sockopt(cli, sockops);
2856 printf("starting unlink test\n");
2858 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2862 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum);
2863 if (!NT_STATUS_IS_OK(status)) {
2864 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
2868 status = cli_unlink(cli, fname,
2869 FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2870 if (NT_STATUS_IS_OK(status)) {
2871 printf("error: server allowed unlink on an open file\n");
2874 correct = check_error(__LINE__, cli, ERRDOS, ERRbadshare,
2875 NT_STATUS_SHARING_VIOLATION);
2878 cli_close(cli, fnum);
2879 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2881 if (!torture_close_connection(cli)) {
2885 printf("unlink test finished\n");
2892 test how many open files this server supports on the one socket
2894 static bool run_maxfidtest(int dummy)
2896 struct cli_state *cli;
2898 uint16_t fnums[0x11000];
2901 bool correct = True;
2907 printf("failed to connect\n");
2911 cli_sockopt(cli, sockops);
2913 for (i=0; i<0x11000; i++) {
2914 slprintf(fname,sizeof(fname)-1,"\\maxfid.%d.%d", i,(int)getpid());
2915 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_TRUNC, DENY_NONE,
2917 if (!NT_STATUS_IS_OK(status)) {
2918 printf("open of %s failed (%s)\n",
2919 fname, nt_errstr(status));
2920 printf("maximum fnum is %d\n", i);
2928 printf("cleaning up\n");
2930 slprintf(fname,sizeof(fname)-1,"\\maxfid.%d.%d", i,(int)getpid());
2931 cli_close(cli, fnums[i]);
2933 status = cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
2934 if (!NT_STATUS_IS_OK(status)) {
2935 printf("unlink of %s failed (%s)\n",
2936 fname, nt_errstr(status));
2943 printf("maxfid test finished\n");
2944 if (!torture_close_connection(cli)) {
2950 /* generate a random buffer */
2951 static void rand_buf(char *buf, int len)
2954 *buf = (char)sys_random();
2959 /* send smb negprot commands, not reading the response */
2960 static bool run_negprot_nowait(int dummy)
2962 struct tevent_context *ev;
2964 struct cli_state *cli;
2965 bool correct = True;
2967 printf("starting negprot nowait test\n");
2969 ev = tevent_context_init(talloc_tos());
2974 if (!(cli = open_nbt_connection())) {
2979 for (i=0;i<50000;i++) {
2980 struct tevent_req *req;
2982 req = cli_negprot_send(ev, ev, cli);
2987 if (!tevent_req_poll(req, ev)) {
2988 d_fprintf(stderr, "tevent_req_poll failed: %s\n",
2996 if (torture_close_connection(cli)) {
3000 printf("finished negprot nowait test\n");
3005 /* send smb negprot commands, not reading the response */
3006 static bool run_bad_nbt_session(int dummy)
3008 struct nmb_name called, calling;
3009 struct sockaddr_storage ss;
3014 printf("starting bad nbt session test\n");
3016 make_nmb_name(&calling, myname, 0x0);
3017 make_nmb_name(&called , host, 0x20);
3019 if (!resolve_name(host, &ss, 0x20, true)) {
3020 d_fprintf(stderr, "Could not resolve name %s\n", host);
3024 status = open_socket_out(&ss, 139, 10000, &fd);
3025 if (!NT_STATUS_IS_OK(status)) {
3026 d_fprintf(stderr, "open_socket_out failed: %s\n",
3031 ret = cli_bad_session_request(fd, &calling, &called);
3034 d_fprintf(stderr, "open_socket_out failed: %s\n",
3039 printf("finished bad nbt session test\n");
3043 /* send random IPC commands */
3044 static bool run_randomipc(int dummy)
3046 char *rparam = NULL;
3048 unsigned int rdrcnt,rprcnt;
3050 int api, param_len, i;
3051 struct cli_state *cli;
3052 bool correct = True;
3055 printf("starting random ipc test\n");
3057 if (!torture_open_connection(&cli, 0)) {
3061 for (i=0;i<count;i++) {
3062 api = sys_random() % 500;
3063 param_len = (sys_random() % 64);
3065 rand_buf(param, param_len);
3070 param, param_len, 8,
3071 NULL, 0, BUFFER_SIZE,
3075 printf("%d/%d\r", i,count);
3078 printf("%d/%d\n", i, count);
3080 if (!torture_close_connection(cli)) {
3084 printf("finished random ipc test\n");
3091 static void browse_callback(const char *sname, uint32 stype,
3092 const char *comment, void *state)
3094 printf("\t%20.20s %08x %s\n", sname, stype, comment);
3100 This test checks the browse list code
3103 static bool run_browsetest(int dummy)
3105 static struct cli_state *cli;
3106 bool correct = True;
3108 printf("starting browse test\n");
3110 if (!torture_open_connection(&cli, 0)) {
3114 printf("domain list:\n");
3115 cli_NetServerEnum(cli, cli->server_domain,
3116 SV_TYPE_DOMAIN_ENUM,
3117 browse_callback, NULL);
3119 printf("machine list:\n");
3120 cli_NetServerEnum(cli, cli->server_domain,
3122 browse_callback, NULL);
3124 if (!torture_close_connection(cli)) {
3128 printf("browse test finished\n");
3136 This checks how the getatr calls works
3138 static bool run_attrtest(int dummy)
3140 struct cli_state *cli;
3143 const char *fname = "\\attrib123456789.tst";
3144 bool correct = True;
3147 printf("starting attrib test\n");
3149 if (!torture_open_connection(&cli, 0)) {
3153 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3154 cli_open(cli, fname,
3155 O_RDWR | O_CREAT | O_TRUNC, DENY_NONE, &fnum);
3156 cli_close(cli, fnum);
3158 status = cli_getatr(cli, fname, NULL, NULL, &t);
3159 if (!NT_STATUS_IS_OK(status)) {
3160 printf("getatr failed (%s)\n", nt_errstr(status));
3164 if (abs(t - time(NULL)) > 60*60*24*10) {
3165 printf("ERROR: SMBgetatr bug. time is %s",
3171 t2 = t-60*60*24; /* 1 day ago */
3173 status = cli_setatr(cli, fname, 0, t2);
3174 if (!NT_STATUS_IS_OK(status)) {
3175 printf("setatr failed (%s)\n", nt_errstr(status));
3179 status = cli_getatr(cli, fname, NULL, NULL, &t);
3180 if (!NT_STATUS_IS_OK(status)) {
3181 printf("getatr failed (%s)\n", nt_errstr(status));
3186 printf("ERROR: getatr/setatr bug. times are\n%s",
3188 printf("%s", ctime(&t2));
3192 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3194 if (!torture_close_connection(cli)) {
3198 printf("attrib test finished\n");
3205 This checks a couple of trans2 calls
3207 static bool run_trans2test(int dummy)
3209 struct cli_state *cli;
3212 time_t c_time, a_time, m_time;
3213 struct timespec c_time_ts, a_time_ts, m_time_ts, w_time_ts, m_time2_ts;
3214 const char *fname = "\\trans2.tst";
3215 const char *dname = "\\trans2";
3216 const char *fname2 = "\\trans2\\trans2.tst";
3218 bool correct = True;
3222 printf("starting trans2 test\n");
3224 if (!torture_open_connection(&cli, 0)) {
3228 status = cli_get_fs_attr_info(cli, &fs_attr);
3229 if (!NT_STATUS_IS_OK(status)) {
3230 printf("ERROR: cli_get_fs_attr_info returned %s\n",
3235 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3236 cli_open(cli, fname, O_RDWR | O_CREAT | O_TRUNC, DENY_NONE, &fnum);
3237 status = cli_qfileinfo_basic(cli, fnum, NULL, &size, &c_time_ts,
3238 &a_time_ts, &w_time_ts, &m_time_ts, NULL);
3239 if (!NT_STATUS_IS_OK(status)) {
3240 printf("ERROR: qfileinfo failed (%s)\n", nt_errstr(status));
3244 status = cli_qfilename(cli, fnum, talloc_tos(), &pname);
3245 if (!NT_STATUS_IS_OK(status)) {
3246 printf("ERROR: qfilename failed (%s)\n", nt_errstr(status));
3250 if (strcmp(pname, fname)) {
3251 printf("qfilename gave different name? [%s] [%s]\n",
3256 cli_close(cli, fnum);
3260 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3261 status = cli_open(cli, fname, O_RDWR | O_CREAT | O_TRUNC, DENY_NONE,
3263 if (!NT_STATUS_IS_OK(status)) {
3264 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3267 cli_close(cli, fnum);
3269 status = cli_qpathinfo1(cli, fname, &c_time, &a_time, &m_time, &size,
3271 if (!NT_STATUS_IS_OK(status)) {
3272 printf("ERROR: qpathinfo failed (%s)\n", nt_errstr(status));
3275 if (c_time != m_time) {
3276 printf("create time=%s", ctime(&c_time));
3277 printf("modify time=%s", ctime(&m_time));
3278 printf("This system appears to have sticky create times\n");
3280 if (a_time % (60*60) == 0) {
3281 printf("access time=%s", ctime(&a_time));
3282 printf("This system appears to set a midnight access time\n");
3286 if (abs(m_time - time(NULL)) > 60*60*24*7) {
3287 printf("ERROR: totally incorrect times - maybe word reversed? mtime=%s", ctime(&m_time));
3293 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3294 cli_open(cli, fname,
3295 O_RDWR | O_CREAT | O_TRUNC, DENY_NONE, &fnum);
3296 cli_close(cli, fnum);
3297 status = cli_qpathinfo2(cli, fname, &c_time_ts, &a_time_ts, &w_time_ts,
3298 &m_time_ts, &size, NULL, NULL);
3299 if (!NT_STATUS_IS_OK(status)) {
3300 printf("ERROR: qpathinfo2 failed (%s)\n", nt_errstr(status));
3303 if (w_time_ts.tv_sec < 60*60*24*2) {
3304 printf("write time=%s", ctime(&w_time_ts.tv_sec));
3305 printf("This system appears to set a initial 0 write time\n");
3310 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3313 /* check if the server updates the directory modification time
3314 when creating a new file */
3315 status = cli_mkdir(cli, dname);
3316 if (!NT_STATUS_IS_OK(status)) {
3317 printf("ERROR: mkdir failed (%s)\n", nt_errstr(status));
3321 status = cli_qpathinfo2(cli, "\\trans2\\", &c_time_ts, &a_time_ts,
3322 &w_time_ts, &m_time_ts, &size, NULL, NULL);
3323 if (!NT_STATUS_IS_OK(status)) {
3324 printf("ERROR: qpathinfo2 failed (%s)\n", nt_errstr(status));
3328 cli_open(cli, fname2,
3329 O_RDWR | O_CREAT | O_TRUNC, DENY_NONE, &fnum);
3330 cli_writeall(cli, fnum, 0, (uint8_t *)&fnum, 0, sizeof(fnum), NULL);
3331 cli_close(cli, fnum);
3332 status = cli_qpathinfo2(cli, "\\trans2\\", &c_time_ts, &a_time_ts,
3333 &w_time_ts, &m_time2_ts, &size, NULL, NULL);
3334 if (!NT_STATUS_IS_OK(status)) {
3335 printf("ERROR: qpathinfo2 failed (%s)\n", nt_errstr(status));
3338 if (memcmp(&m_time_ts, &m_time2_ts, sizeof(struct timespec))
3340 printf("This system does not update directory modification times\n");
3344 cli_unlink(cli, fname2, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3345 cli_rmdir(cli, dname);
3347 if (!torture_close_connection(cli)) {
3351 printf("trans2 test finished\n");
3357 This checks new W2K calls.
3360 static NTSTATUS new_trans(struct cli_state *pcli, int fnum, int level)
3362 uint8_t *buf = NULL;
3366 status = cli_qfileinfo(talloc_tos(), pcli, fnum, level, 0,
3367 pcli->max_xmit, NULL, &buf, &len);
3368 if (!NT_STATUS_IS_OK(status)) {
3369 printf("ERROR: qfileinfo (%d) failed (%s)\n", level,
3372 printf("qfileinfo: level %d, len = %u\n", level, len);
3373 dump_data(0, (uint8 *)buf, len);
3380 static bool run_w2ktest(int dummy)
3382 struct cli_state *cli;
3384 const char *fname = "\\w2ktest\\w2k.tst";
3386 bool correct = True;
3388 printf("starting w2k test\n");
3390 if (!torture_open_connection(&cli, 0)) {
3394 cli_open(cli, fname,
3395 O_RDWR | O_CREAT , DENY_NONE, &fnum);
3397 for (level = 1004; level < 1040; level++) {
3398 new_trans(cli, fnum, level);
3401 cli_close(cli, fnum);
3403 if (!torture_close_connection(cli)) {
3407 printf("w2k test finished\n");
3414 this is a harness for some oplock tests
3416 static bool run_oplock1(int dummy)
3418 struct cli_state *cli1;
3419 const char *fname = "\\lockt1.lck";
3421 bool correct = True;
3424 printf("starting oplock test 1\n");
3426 if (!torture_open_connection(&cli1, 0)) {
3430 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3432 cli_sockopt(cli1, sockops);
3434 cli1->use_oplocks = True;
3436 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
3438 if (!NT_STATUS_IS_OK(status)) {
3439 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3443 cli1->use_oplocks = False;
3445 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3446 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3448 status = cli_close(cli1, fnum1);
3449 if (!NT_STATUS_IS_OK(status)) {
3450 printf("close2 failed (%s)\n", nt_errstr(status));
3454 status = cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3455 if (!NT_STATUS_IS_OK(status)) {
3456 printf("unlink failed (%s)\n", nt_errstr(status));
3460 if (!torture_close_connection(cli1)) {
3464 printf("finished oplock test 1\n");
3469 static bool run_oplock2(int dummy)
3471 struct cli_state *cli1, *cli2;
3472 const char *fname = "\\lockt2.lck";
3473 uint16_t fnum1, fnum2;
3474 int saved_use_oplocks = use_oplocks;
3476 bool correct = True;
3477 volatile bool *shared_correct;
3480 shared_correct = (volatile bool *)shm_setup(sizeof(bool));
3481 *shared_correct = True;
3483 use_level_II_oplocks = True;
3486 printf("starting oplock test 2\n");
3488 if (!torture_open_connection(&cli1, 0)) {
3489 use_level_II_oplocks = False;
3490 use_oplocks = saved_use_oplocks;
3494 cli1->use_oplocks = True;
3495 cli1->use_level_II_oplocks = True;
3497 if (!torture_open_connection(&cli2, 1)) {
3498 use_level_II_oplocks = False;
3499 use_oplocks = saved_use_oplocks;
3503 cli2->use_oplocks = True;
3504 cli2->use_level_II_oplocks = True;
3506 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3508 cli_sockopt(cli1, sockops);
3509 cli_sockopt(cli2, sockops);
3511 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
3513 if (!NT_STATUS_IS_OK(status)) {
3514 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3518 /* Don't need the globals any more. */
3519 use_level_II_oplocks = False;
3520 use_oplocks = saved_use_oplocks;
3524 status = cli_open(cli2, fname, O_RDWR, DENY_NONE, &fnum2);
3525 if (!NT_STATUS_IS_OK(status)) {
3526 printf("second open of %s failed (%s)\n", fname, nt_errstr(status));
3527 *shared_correct = False;
3533 status = cli_close(cli2, fnum2);
3534 if (!NT_STATUS_IS_OK(status)) {
3535 printf("close2 failed (%s)\n", nt_errstr(status));
3536 *shared_correct = False;
3544 /* Ensure cli1 processes the break. Empty file should always return 0
3547 if (cli_read_old(cli1, fnum1, buf, 0, 4) != 0) {
3548 printf("read on fnum1 failed (%s)\n", cli_errstr(cli1));
3552 /* Should now be at level II. */
3553 /* Test if sending a write locks causes a break to none. */
3554 status = cli_lock32(cli1, fnum1, 0, 4, 0, READ_LOCK);
3555 if (!NT_STATUS_IS_OK(status)) {
3556 printf("lock failed (%s)\n", nt_errstr(status));
3560 cli_unlock(cli1, fnum1, 0, 4);
3564 status = cli_lock32(cli1, fnum1, 0, 4, 0, WRITE_LOCK);
3565 if (!NT_STATUS_IS_OK(status)) {
3566 printf("lock failed (%s)\n", nt_errstr(status));
3570 cli_unlock(cli1, fnum1, 0, 4);
3574 cli_read_old(cli1, fnum1, buf, 0, 4);
3576 status = cli_close(cli1, fnum1);
3577 if (!NT_STATUS_IS_OK(status)) {
3578 printf("close1 failed (%s)\n", nt_errstr(status));
3584 status = cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3585 if (!NT_STATUS_IS_OK(status)) {
3586 printf("unlink failed (%s)\n", nt_errstr(status));
3590 if (!torture_close_connection(cli1)) {
3594 if (!*shared_correct) {
3598 printf("finished oplock test 2\n");
3603 struct oplock4_state {
3604 struct tevent_context *ev;
3605 struct cli_state *cli;
3610 static void oplock4_got_break(struct tevent_req *req);
3611 static void oplock4_got_open(struct tevent_req *req);
3613 static bool run_oplock4(int dummy)
3615 struct tevent_context *ev;
3616 struct cli_state *cli1, *cli2;
3617 struct tevent_req *oplock_req, *open_req;
3618 const char *fname = "\\lockt4.lck";
3619 const char *fname_ln = "\\lockt4_ln.lck";
3620 uint16_t fnum1, fnum2;
3621 int saved_use_oplocks = use_oplocks;
3623 bool correct = true;
3627 struct oplock4_state *state;
3629 printf("starting oplock test 4\n");
3631 if (!torture_open_connection(&cli1, 0)) {
3632 use_level_II_oplocks = false;
3633 use_oplocks = saved_use_oplocks;
3637 if (!torture_open_connection(&cli2, 1)) {
3638 use_level_II_oplocks = false;
3639 use_oplocks = saved_use_oplocks;
3643 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3644 cli_unlink(cli1, fname_ln, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3646 cli_sockopt(cli1, sockops);
3647 cli_sockopt(cli2, sockops);
3649 /* Create the file. */
3650 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE,
3652 if (!NT_STATUS_IS_OK(status)) {
3653 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3657 status = cli_close(cli1, fnum1);
3658 if (!NT_STATUS_IS_OK(status)) {
3659 printf("close1 failed (%s)\n", nt_errstr(status));
3663 /* Now create a hardlink. */
3664 status = cli_nt_hardlink(cli1, fname, fname_ln);
3665 if (!NT_STATUS_IS_OK(status)) {
3666 printf("nt hardlink failed (%s)\n", nt_errstr(status));
3670 /* Prove that opening hardlinks cause deny modes to conflict. */
3671 status = cli_open(cli1, fname, O_RDWR, DENY_ALL, &fnum1);
3672 if (!NT_STATUS_IS_OK(status)) {
3673 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3677 status = cli_open(cli1, fname_ln, O_RDWR, DENY_NONE, &fnum2);
3678 if (NT_STATUS_IS_OK(status)) {
3679 printf("open of %s succeeded - should fail with sharing violation.\n",
3684 if (!NT_STATUS_EQUAL(status, NT_STATUS_SHARING_VIOLATION)) {
3685 printf("open of %s should fail with sharing violation. Got %s\n",
3686 fname_ln, nt_errstr(status));
3690 status = cli_close(cli1, fnum1);
3691 if (!NT_STATUS_IS_OK(status)) {
3692 printf("close1 failed (%s)\n", nt_errstr(status));
3696 cli1->use_oplocks = true;
3697 cli1->use_level_II_oplocks = true;
3699 cli2->use_oplocks = true;
3700 cli2->use_level_II_oplocks = true;
3702 status = cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1);
3703 if (!NT_STATUS_IS_OK(status)) {
3704 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
3708 ev = tevent_context_init(talloc_tos());
3710 printf("tevent_req_create failed\n");
3714 state = talloc(ev, struct oplock4_state);
3715 if (state == NULL) {
3716 printf("talloc failed\n");
3721 state->got_break = &got_break;
3722 state->fnum2 = &fnum2;
3724 oplock_req = cli_smb_oplock_break_waiter_send(
3725 talloc_tos(), ev, cli1);
3726 if (oplock_req == NULL) {
3727 printf("cli_smb_oplock_break_waiter_send failed\n");
3730 tevent_req_set_callback(oplock_req, oplock4_got_break, state);
3732 open_req = cli_open_send(
3733 talloc_tos(), ev, cli2, fname_ln, O_RDWR, DENY_NONE);
3734 if (oplock_req == NULL) {
3735 printf("cli_open_send failed\n");
3738 tevent_req_set_callback(open_req, oplock4_got_open, state);
3743 while (!got_break || fnum2 == 0xffff) {
3745 ret = tevent_loop_once(ev);
3747 printf("tevent_loop_once failed: %s\n",
3753 status = cli_close(cli2, fnum2);
3754 if (!NT_STATUS_IS_OK(status)) {
3755 printf("close2 failed (%s)\n", nt_errstr(status));
3759 status = cli_close(cli1, fnum1);
3760 if (!NT_STATUS_IS_OK(status)) {
3761 printf("close1 failed (%s)\n", nt_errstr(status));
3765 status = cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3766 if (!NT_STATUS_IS_OK(status)) {
3767 printf("unlink failed (%s)\n", nt_errstr(status));
3771 status = cli_unlink(cli1, fname_ln, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3772 if (!NT_STATUS_IS_OK(status)) {
3773 printf("unlink failed (%s)\n", nt_errstr(status));
3777 if (!torture_close_connection(cli1)) {
3785 printf("finished oplock test 4\n");
3790 static void oplock4_got_break(struct tevent_req *req)
3792 struct oplock4_state *state = tevent_req_callback_data(
3793 req, struct oplock4_state);
3798 status = cli_smb_oplock_break_waiter_recv(req, &fnum, &level);
3800 if (!NT_STATUS_IS_OK(status)) {
3801 printf("cli_smb_oplock_break_waiter_recv returned %s\n",
3805 *state->got_break = true;
3807 req = cli_oplock_ack_send(state, state->ev, state->cli, fnum,
3810 printf("cli_oplock_ack_send failed\n");
3815 static void oplock4_got_open(struct tevent_req *req)
3817 struct oplock4_state *state = tevent_req_callback_data(
3818 req, struct oplock4_state);
3821 status = cli_open_recv(req, state->fnum2);
3822 if (!NT_STATUS_IS_OK(status)) {
3823 printf("cli_open_recv returned %s\n", nt_errstr(status));
3824 *state->fnum2 = 0xffff;
3829 Test delete on close semantics.
3831 static bool run_deletetest(int dummy)
3833 struct cli_state *cli1 = NULL;
3834 struct cli_state *cli2 = NULL;
3835 const char *fname = "\\delete.file";
3836 uint16_t fnum1 = (uint16_t)-1;
3837 uint16_t fnum2 = (uint16_t)-1;
3838 bool correct = True;
3841 printf("starting delete test\n");
3843 if (!torture_open_connection(&cli1, 0)) {
3847 cli_sockopt(cli1, sockops);
3849 /* Test 1 - this should delete the file on close. */
3851 cli_setatr(cli1, fname, 0, 0);
3852 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3854 status = cli_ntcreate(cli1, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS,
3855 FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF,
3856 FILE_DELETE_ON_CLOSE, 0, &fnum1);
3857 if (!NT_STATUS_IS_OK(status)) {
3858 printf("[1] open of %s failed (%s)\n", fname, nt_errstr(status));
3863 status = cli_close(cli1, fnum1);
3864 if (!NT_STATUS_IS_OK(status)) {
3865 printf("[1] close failed (%s)\n", nt_errstr(status));
3870 if (NT_STATUS_IS_OK(cli_open(cli1, fname, O_RDWR, DENY_NONE, &fnum1))) {
3871 printf("[1] open of %s succeeded (should fail)\n", fname);
3876 printf("first delete on close test succeeded.\n");
3878 /* Test 2 - this should delete the file on close. */
3880 cli_setatr(cli1, fname, 0, 0);
3881 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3883 status = cli_ntcreate(cli1, fname, 0, GENERIC_ALL_ACCESS,
3884 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
3885 FILE_OVERWRITE_IF, 0, 0, &fnum1);
3886 if (!NT_STATUS_IS_OK(status)) {
3887 printf("[2] open of %s failed (%s)\n", fname, nt_errstr(status));
3892 status = cli_nt_delete_on_close(cli1, fnum1, true);
3893 if (!NT_STATUS_IS_OK(status)) {
3894 printf("[2] setting delete_on_close failed (%s)\n", nt_errstr(status));
3899 status = cli_close(cli1, fnum1);
3900 if (!NT_STATUS_IS_OK(status)) {
3901 printf("[2] close failed (%s)\n", nt_errstr(status));
3906 if (NT_STATUS_IS_OK(cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum1))) {
3907 printf("[2] open of %s succeeded should have been deleted on close !\n", fname);
3908 status = cli_close(cli1, fnum1);
3909 if (!NT_STATUS_IS_OK(status)) {
3910 printf("[2] close failed (%s)\n", nt_errstr(status));
3914 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3916 printf("second delete on close test succeeded.\n");
3919 cli_setatr(cli1, fname, 0, 0);
3920 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3922 status = cli_ntcreate(cli1, fname, 0, GENERIC_ALL_ACCESS,
3923 FILE_ATTRIBUTE_NORMAL,
3924 FILE_SHARE_READ|FILE_SHARE_WRITE,
3925 FILE_OVERWRITE_IF, 0, 0, &fnum1);
3926 if (!NT_STATUS_IS_OK(status)) {
3927 printf("[3] open - 1 of %s failed (%s)\n", fname, nt_errstr(status));
3932 /* This should fail with a sharing violation - open for delete is only compatible
3933 with SHARE_DELETE. */
3935 if (NT_STATUS_IS_OK(cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS, FILE_ATTRIBUTE_NORMAL,
3936 FILE_SHARE_READ|FILE_SHARE_WRITE, FILE_OPEN, 0, 0, &fnum2))) {
3937 printf("[3] open - 2 of %s succeeded - should have failed.\n", fname);
3942 /* This should succeed. */
3943 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
3944 FILE_ATTRIBUTE_NORMAL,
3945 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
3946 FILE_OPEN, 0, 0, &fnum2);
3947 if (!NT_STATUS_IS_OK(status)) {
3948 printf("[3] open - 2 of %s failed (%s)\n", fname, nt_errstr(status));
3953 status = cli_nt_delete_on_close(cli1, fnum1, true);
3954 if (!NT_STATUS_IS_OK(status)) {
3955 printf("[3] setting delete_on_close failed (%s)\n", nt_errstr(status));
3960 status = cli_close(cli1, fnum1);
3961 if (!NT_STATUS_IS_OK(status)) {
3962 printf("[3] close 1 failed (%s)\n", nt_errstr(status));
3967 status = cli_close(cli1, fnum2);
3968 if (!NT_STATUS_IS_OK(status)) {
3969 printf("[3] close 2 failed (%s)\n", nt_errstr(status));
3974 /* This should fail - file should no longer be there. */
3976 if (NT_STATUS_IS_OK(cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum1))) {
3977 printf("[3] open of %s succeeded should have been deleted on close !\n", fname);
3978 status = cli_close(cli1, fnum1);
3979 if (!NT_STATUS_IS_OK(status)) {
3980 printf("[3] close failed (%s)\n", nt_errstr(status));
3982 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3986 printf("third delete on close test succeeded.\n");
3989 cli_setatr(cli1, fname, 0, 0);
3990 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
3992 status = cli_ntcreate(cli1, fname, 0,
3993 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
3994 FILE_ATTRIBUTE_NORMAL,
3995 FILE_SHARE_READ|FILE_SHARE_WRITE,
3996 FILE_OVERWRITE_IF, 0, 0, &fnum1);
3997 if (!NT_STATUS_IS_OK(status)) {
3998 printf("[4] open of %s failed (%s)\n", fname, nt_errstr(status));
4003 /* This should succeed. */
4004 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
4005 FILE_ATTRIBUTE_NORMAL,
4006 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4007 FILE_OPEN, 0, 0, &fnum2);
4008 if (!NT_STATUS_IS_OK(status)) {
4009 printf("[4] open - 2 of %s failed (%s)\n", fname, nt_errstr(status));
4014 status = cli_close(cli1, fnum2);
4015 if (!NT_STATUS_IS_OK(status)) {
4016 printf("[4] close - 1 failed (%s)\n", nt_errstr(status));
4021 status = cli_nt_delete_on_close(cli1, fnum1, true);
4022 if (!NT_STATUS_IS_OK(status)) {
4023 printf("[4] setting delete_on_close failed (%s)\n", nt_errstr(status));
4028 /* This should fail - no more opens once delete on close set. */
4029 if (NT_STATUS_IS_OK(cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
4030 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4031 FILE_OPEN, 0, 0, &fnum2))) {
4032 printf("[4] open - 3 of %s succeeded ! Should have failed.\n", fname );
4036 printf("fourth delete on close test succeeded.\n");
4038 status = cli_close(cli1, fnum1);
4039 if (!NT_STATUS_IS_OK(status)) {
4040 printf("[4] close - 2 failed (%s)\n", nt_errstr(status));
4046 cli_setatr(cli1, fname, 0, 0);
4047 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4049 status = cli_open(cli1, fname, O_RDWR|O_CREAT, DENY_NONE, &fnum1);
4050 if (!NT_STATUS_IS_OK(status)) {
4051 printf("[5] open of %s failed (%s)\n", fname, nt_errstr(status));
4056 /* This should fail - only allowed on NT opens with DELETE access. */
4058 if (NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum1, true))) {
4059 printf("[5] setting delete_on_close on OpenX file succeeded - should fail !\n");
4064 status = cli_close(cli1, fnum1);
4065 if (!NT_STATUS_IS_OK(status)) {
4066 printf("[5] close - 2 failed (%s)\n", nt_errstr(status));
4071 printf("fifth delete on close test succeeded.\n");
4074 cli_setatr(cli1, fname, 0, 0);
4075 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4077 status = cli_ntcreate(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA,
4078 FILE_ATTRIBUTE_NORMAL,
4079 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4080 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4081 if (!NT_STATUS_IS_OK(status)) {
4082 printf("[6] open of %s failed (%s)\n", fname,
4088 /* This should fail - only allowed on NT opens with DELETE access. */
4090 if (NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum1, true))) {
4091 printf("[6] setting delete_on_close on file with no delete access succeeded - should fail !\n");
4096 status = cli_close(cli1, fnum1);
4097 if (!NT_STATUS_IS_OK(status)) {
4098 printf("[6] close - 2 failed (%s)\n", nt_errstr(status));
4103 printf("sixth delete on close test succeeded.\n");
4106 cli_setatr(cli1, fname, 0, 0);
4107 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4109 status = cli_ntcreate(cli1, fname, 0,
4110 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
4111 FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF,
4113 if (!NT_STATUS_IS_OK(status)) {
4114 printf("[7] open of %s failed (%s)\n", fname, nt_errstr(status));
4119 if (!NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum1, true))) {
4120 printf("[7] setting delete_on_close on file failed !\n");
4125 if (!NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum1, false))) {
4126 printf("[7] unsetting delete_on_close on file failed !\n");
4131 status = cli_close(cli1, fnum1);
4132 if (!NT_STATUS_IS_OK(status)) {
4133 printf("[7] close - 2 failed (%s)\n", nt_errstr(status));
4138 /* This next open should succeed - we reset the flag. */
4139 status = cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum1);
4140 if (!NT_STATUS_IS_OK(status)) {
4141 printf("[5] open of %s failed (%s)\n", fname, nt_errstr(status));
4146 status = cli_close(cli1, fnum1);
4147 if (!NT_STATUS_IS_OK(status)) {
4148 printf("[7] close - 2 failed (%s)\n", nt_errstr(status));
4153 printf("seventh delete on close test succeeded.\n");
4156 cli_setatr(cli1, fname, 0, 0);
4157 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4159 if (!torture_open_connection(&cli2, 1)) {
4160 printf("[8] failed to open second connection.\n");
4165 cli_sockopt(cli1, sockops);
4167 status = cli_ntcreate(cli1, fname, 0,
4168 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
4169 FILE_ATTRIBUTE_NORMAL,
4170 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4171 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4172 if (!NT_STATUS_IS_OK(status)) {
4173 printf("[8] open 1 of %s failed (%s)\n", fname, nt_errstr(status));
4178 status = cli_ntcreate(cli2, fname, 0,
4179 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
4180 FILE_ATTRIBUTE_NORMAL,
4181 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4182 FILE_OPEN, 0, 0, &fnum2);
4183 if (!NT_STATUS_IS_OK(status)) {
4184 printf("[8] open 2 of %s failed (%s)\n", fname, nt_errstr(status));
4189 if (!NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum1, true))) {
4190 printf("[8] setting delete_on_close on file failed !\n");
4195 status = cli_close(cli1, fnum1);
4196 if (!NT_STATUS_IS_OK(status)) {
4197 printf("[8] close - 1 failed (%s)\n", nt_errstr(status));
4202 status = cli_close(cli2, fnum2);
4203 if (!NT_STATUS_IS_OK(status)) {
4204 printf("[8] close - 2 failed (%s)\n", nt_errstr(status));
4209 /* This should fail.. */
4210 status = cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum1);
4211 if (NT_STATUS_IS_OK(status)) {
4212 printf("[8] open of %s succeeded should have been deleted on close !\n", fname);
4216 printf("eighth delete on close test succeeded.\n");
4218 /* This should fail - we need to set DELETE_ACCESS. */
4219 if (NT_STATUS_IS_OK(cli_ntcreate(cli1, fname, 0,FILE_READ_DATA|FILE_WRITE_DATA,
4220 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE, FILE_OVERWRITE_IF, FILE_DELETE_ON_CLOSE, 0, &fnum1))) {
4221 printf("[9] open of %s succeeded should have failed!\n", fname);
4226 printf("ninth delete on close test succeeded.\n");
4228 status = cli_ntcreate(cli1, fname, 0,
4229 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
4230 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4231 FILE_OVERWRITE_IF, FILE_DELETE_ON_CLOSE,
4233 if (!NT_STATUS_IS_OK(status)) {
4234 printf("[10] open of %s failed (%s)\n", fname, nt_errstr(status));
4239 /* This should delete the file. */
4240 status = cli_close(cli1, fnum1);
4241 if (!NT_STATUS_IS_OK(status)) {
4242 printf("[10] close failed (%s)\n", nt_errstr(status));
4247 /* This should fail.. */
4248 if (NT_STATUS_IS_OK(cli_open(cli1, fname, O_RDONLY, DENY_NONE, &fnum1))) {
4249 printf("[10] open of %s succeeded should have been deleted on close !\n", fname);
4253 printf("tenth delete on close test succeeded.\n");
4255 cli_setatr(cli1, fname, 0, 0);
4256 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4258 /* What error do we get when attempting to open a read-only file with
4261 /* Create a readonly file. */
4262 status = cli_ntcreate(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA,
4263 FILE_ATTRIBUTE_READONLY, FILE_SHARE_NONE,
4264 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4265 if (!NT_STATUS_IS_OK(status)) {
4266 printf("[11] open of %s failed (%s)\n", fname, nt_errstr(status));
4271 status = cli_close(cli1, fnum1);
4272 if (!NT_STATUS_IS_OK(status)) {
4273 printf("[11] close failed (%s)\n", nt_errstr(status));
4278 /* Now try open for delete access. */
4279 if (NT_STATUS_IS_OK(cli_ntcreate(cli1, fname, 0, FILE_READ_ATTRIBUTES|DELETE_ACCESS,
4280 0, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4281 FILE_OVERWRITE_IF, 0, 0, &fnum1))) {
4282 printf("[11] open of %s succeeded should have been denied with ACCESS_DENIED!\n", fname);
4283 cli_close(cli1, fnum1);
4287 NTSTATUS nterr = cli_nt_error(cli1);
4288 if (!NT_STATUS_EQUAL(nterr,NT_STATUS_ACCESS_DENIED)) {
4289 printf("[11] open of %s should have been denied with ACCESS_DENIED! Got error %s\n", fname, nt_errstr(nterr));
4293 printf("eleventh delete on close test succeeded.\n");
4297 printf("finished delete test\n");
4300 /* FIXME: This will crash if we aborted before cli2 got
4301 * intialized, because these functions don't handle
4302 * uninitialized connections. */
4304 if (fnum1 != (uint16_t)-1) cli_close(cli1, fnum1);
4305 if (fnum2 != (uint16_t)-1) cli_close(cli1, fnum2);
4306 cli_setatr(cli1, fname, 0, 0);
4307 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4309 if (cli1 && !torture_close_connection(cli1)) {
4312 if (cli2 && !torture_close_connection(cli2)) {
4318 static bool run_deletetest_ln(int dummy)
4320 struct cli_state *cli;
4321 const char *fname = "\\delete1";
4322 const char *fname_ln = "\\delete1_ln";
4326 bool correct = true;
4329 printf("starting deletetest-ln\n");
4331 if (!torture_open_connection(&cli, 0)) {
4335 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4336 cli_unlink(cli, fname_ln, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4338 cli_sockopt(cli, sockops);
4340 /* Create the file. */
4341 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum);
4342 if (!NT_STATUS_IS_OK(status)) {
4343 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
4347 status = cli_close(cli, fnum);
4348 if (!NT_STATUS_IS_OK(status)) {
4349 printf("close1 failed (%s)\n", nt_errstr(status));
4353 /* Now create a hardlink. */
4354 status = cli_nt_hardlink(cli, fname, fname_ln);
4355 if (!NT_STATUS_IS_OK(status)) {
4356 printf("nt hardlink failed (%s)\n", nt_errstr(status));
4360 /* Open the original file. */
4361 status = cli_ntcreate(cli, fname, 0, FILE_READ_DATA,
4362 FILE_ATTRIBUTE_NORMAL,
4363 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4364 FILE_OPEN_IF, 0, 0, &fnum);
4365 if (!NT_STATUS_IS_OK(status)) {
4366 printf("ntcreate of %s failed (%s)\n", fname, nt_errstr(status));
4370 /* Unlink the hard link path. */
4371 status = cli_ntcreate(cli, fname_ln, 0, DELETE_ACCESS,
4372 FILE_ATTRIBUTE_NORMAL,
4373 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4374 FILE_OPEN_IF, 0, 0, &fnum1);
4375 if (!NT_STATUS_IS_OK(status)) {
4376 printf("ntcreate of %s failed (%s)\n", fname_ln, nt_errstr(status));
4379 status = cli_nt_delete_on_close(cli, fnum1, true);
4380 if (!NT_STATUS_IS_OK(status)) {
4381 d_printf("(%s) failed to set delete_on_close %s: %s\n",
4382 __location__, fname_ln, nt_errstr(status));
4386 status = cli_close(cli, fnum1);
4387 if (!NT_STATUS_IS_OK(status)) {
4388 printf("close %s failed (%s)\n",
4389 fname_ln, nt_errstr(status));
4393 status = cli_close(cli, fnum);
4394 if (!NT_STATUS_IS_OK(status)) {
4395 printf("close %s failed (%s)\n",
4396 fname, nt_errstr(status));
4400 /* Ensure the original file is still there. */
4401 status = cli_getatr(cli, fname, NULL, NULL, &t);
4402 if (!NT_STATUS_IS_OK(status)) {
4403 printf("%s getatr on file %s failed (%s)\n",
4410 /* Ensure the link path is gone. */
4411 status = cli_getatr(cli, fname_ln, NULL, NULL, &t);
4412 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
4413 printf("%s, getatr for file %s returned wrong error code %s "
4414 "- should have been deleted\n",
4416 fname_ln, nt_errstr(status));
4420 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4421 cli_unlink(cli, fname_ln, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4423 if (!torture_close_connection(cli)) {
4427 printf("finished deletetest-ln\n");
4433 print out server properties
4435 static bool run_properties(int dummy)
4437 struct cli_state *cli;
4438 bool correct = True;
4440 printf("starting properties test\n");
4444 if (!torture_open_connection(&cli, 0)) {
4448 cli_sockopt(cli, sockops);
4450 d_printf("Capabilities 0x%08x\n", cli->capabilities);
4452 if (!torture_close_connection(cli)) {
4461 /* FIRST_DESIRED_ACCESS 0xf019f */
4462 #define FIRST_DESIRED_ACCESS FILE_READ_DATA|FILE_WRITE_DATA|FILE_APPEND_DATA|\
4463 FILE_READ_EA| /* 0xf */ \
4464 FILE_WRITE_EA|FILE_READ_ATTRIBUTES| /* 0x90 */ \
4465 FILE_WRITE_ATTRIBUTES| /* 0x100 */ \
4466 DELETE_ACCESS|READ_CONTROL_ACCESS|\
4467 WRITE_DAC_ACCESS|WRITE_OWNER_ACCESS /* 0xf0000 */
4468 /* SECOND_DESIRED_ACCESS 0xe0080 */
4469 #define SECOND_DESIRED_ACCESS FILE_READ_ATTRIBUTES| /* 0x80 */ \
4470 READ_CONTROL_ACCESS|WRITE_DAC_ACCESS|\
4471 WRITE_OWNER_ACCESS /* 0xe0000 */
4474 #define THIRD_DESIRED_ACCESS FILE_READ_ATTRIBUTES| /* 0x80 */ \
4475 READ_CONTROL_ACCESS|WRITE_DAC_ACCESS|\
4477 WRITE_OWNER_ACCESS /* */
4481 Test ntcreate calls made by xcopy
4483 static bool run_xcopy(int dummy)
4485 static struct cli_state *cli1;
4486 const char *fname = "\\test.txt";
4487 bool correct = True;
4488 uint16_t fnum1, fnum2;
4491 printf("starting xcopy test\n");
4493 if (!torture_open_connection(&cli1, 0)) {
4497 status = cli_ntcreate(cli1, fname, 0, FIRST_DESIRED_ACCESS,
4498 FILE_ATTRIBUTE_ARCHIVE, FILE_SHARE_NONE,
4499 FILE_OVERWRITE_IF, 0x4044, 0, &fnum1);
4500 if (!NT_STATUS_IS_OK(status)) {
4501 printf("First open failed - %s\n", nt_errstr(status));
4505 status = cli_ntcreate(cli1, fname, 0, SECOND_DESIRED_ACCESS, 0,
4506 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
4507 FILE_OPEN, 0x200000, 0, &fnum2);
4508 if (!NT_STATUS_IS_OK(status)) {
4509 printf("second open failed - %s\n", nt_errstr(status));
4513 if (!torture_close_connection(cli1)) {
4521 Test rename on files open with share delete and no share delete.
4523 static bool run_rename(int dummy)
4525 static struct cli_state *cli1;
4526 const char *fname = "\\test.txt";
4527 const char *fname1 = "\\test1.txt";
4528 bool correct = True;
4533 printf("starting rename test\n");
4535 if (!torture_open_connection(&cli1, 0)) {
4539 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4540 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4542 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
4543 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ,
4544 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4545 if (!NT_STATUS_IS_OK(status)) {
4546 printf("First open failed - %s\n", nt_errstr(status));
4550 status = cli_rename(cli1, fname, fname1);
4551 if (!NT_STATUS_IS_OK(status)) {
4552 printf("First rename failed (SHARE_READ) (this is correct) - %s\n", nt_errstr(status));
4554 printf("First rename succeeded (SHARE_READ) - this should have failed !\n");
4558 status = cli_close(cli1, fnum1);
4559 if (!NT_STATUS_IS_OK(status)) {
4560 printf("close - 1 failed (%s)\n", nt_errstr(status));
4564 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4565 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4566 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS, FILE_ATTRIBUTE_NORMAL,
4568 FILE_SHARE_DELETE|FILE_SHARE_NONE,
4570 FILE_SHARE_DELETE|FILE_SHARE_READ,
4572 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4573 if (!NT_STATUS_IS_OK(status)) {
4574 printf("Second open failed - %s\n", nt_errstr(status));
4578 status = cli_rename(cli1, fname, fname1);
4579 if (!NT_STATUS_IS_OK(status)) {
4580 printf("Second rename failed (SHARE_DELETE | SHARE_READ) - this should have succeeded - %s\n", nt_errstr(status));
4583 printf("Second rename succeeded (SHARE_DELETE | SHARE_READ)\n");
4586 status = cli_close(cli1, fnum1);
4587 if (!NT_STATUS_IS_OK(status)) {
4588 printf("close - 2 failed (%s)\n", nt_errstr(status));
4592 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4593 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4595 status = cli_ntcreate(cli1, fname, 0, READ_CONTROL_ACCESS,
4596 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4597 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4598 if (!NT_STATUS_IS_OK(status)) {
4599 printf("Third open failed - %s\n", nt_errstr(status));
4608 if (!NT_STATUS_IS_OK(cli_ntcreate(cli1, fname, 0, DELETE_ACCESS, FILE_ATTRIBUTE_NORMAL,
4609 FILE_SHARE_NONE, FILE_OVERWRITE_IF, 0, 0, &fnum2))) {
4610 printf("Fourth open failed - %s\n", cli_errstr(cli1));
4613 if (!NT_STATUS_IS_OK(cli_nt_delete_on_close(cli1, fnum2, true))) {
4614 printf("[8] setting delete_on_close on file failed !\n");
4618 if (!NT_STATUS_IS_OK(cli_close(cli1, fnum2))) {
4619 printf("close - 4 failed (%s)\n", cli_errstr(cli1));
4625 status = cli_rename(cli1, fname, fname1);
4626 if (!NT_STATUS_IS_OK(status)) {
4627 printf("Third rename failed (SHARE_NONE) - this should have succeeded - %s\n", nt_errstr(status));
4630 printf("Third rename succeeded (SHARE_NONE)\n");
4633 status = cli_close(cli1, fnum1);
4634 if (!NT_STATUS_IS_OK(status)) {
4635 printf("close - 3 failed (%s)\n", nt_errstr(status));
4639 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4640 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4644 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
4645 FILE_ATTRIBUTE_NORMAL,
4646 FILE_SHARE_READ | FILE_SHARE_WRITE,
4647 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4648 if (!NT_STATUS_IS_OK(status)) {
4649 printf("Fourth open failed - %s\n", nt_errstr(status));
4653 status = cli_rename(cli1, fname, fname1);
4654 if (!NT_STATUS_IS_OK(status)) {
4655 printf("Fourth rename failed (SHARE_READ | SHARE_WRITE) (this is correct) - %s\n", nt_errstr(status));
4657 printf("Fourth rename succeeded (SHARE_READ | SHARE_WRITE) - this should have failed !\n");
4661 status = cli_close(cli1, fnum1);
4662 if (!NT_STATUS_IS_OK(status)) {
4663 printf("close - 4 failed (%s)\n", nt_errstr(status));
4667 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4668 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4672 status = cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS,
4673 FILE_ATTRIBUTE_NORMAL,
4674 FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE,
4675 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4676 if (!NT_STATUS_IS_OK(status)) {
4677 printf("Fifth open failed - %s\n", nt_errstr(status));
4681 status = cli_rename(cli1, fname, fname1);
4682 if (!NT_STATUS_IS_OK(status)) {
4683 printf("Fifth rename failed (SHARE_READ | SHARE_WRITE | SHARE_DELETE) - this should have succeeded - %s ! \n", nt_errstr(status));
4686 printf("Fifth rename succeeded (SHARE_READ | SHARE_WRITE | SHARE_DELETE) (this is correct) - %s\n", nt_errstr(status));
4690 * Now check if the first name still exists ...
4693 /* if (!NT_STATUS_OP(cli_ntcreate(cli1, fname, 0, GENERIC_READ_ACCESS, FILE_ATTRIBUTE_NORMAL,
4694 FILE_SHARE_READ | FILE_SHARE_WRITE | FILE_SHARE_DELETE, FILE_OVERWRITE_IF, 0, 0, &fnum2))) {
4695 printf("Opening original file after rename of open file fails: %s\n",
4699 printf("Opening original file after rename of open file works ...\n");
4700 (void)cli_close(cli1, fnum2);
4704 status = cli_close(cli1, fnum1);
4705 if (!NT_STATUS_IS_OK(status)) {
4706 printf("close - 5 failed (%s)\n", nt_errstr(status));
4710 /* Check that the renamed file has FILE_ATTRIBUTE_ARCHIVE. */
4711 status = cli_getatr(cli1, fname1, &attr, NULL, NULL);
4712 if (!NT_STATUS_IS_OK(status)) {
4713 printf("getatr on file %s failed - %s ! \n",
4714 fname1, nt_errstr(status));
4717 if (attr != FILE_ATTRIBUTE_ARCHIVE) {
4718 printf("Renamed file %s has wrong attr 0x%x "
4719 "(should be 0x%x)\n",
4722 (unsigned int)FILE_ATTRIBUTE_ARCHIVE);
4725 printf("Renamed file %s has archive bit set\n", fname1);
4729 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4730 cli_unlink(cli1, fname1, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4732 if (!torture_close_connection(cli1)) {
4739 static bool run_pipe_number(int dummy)
4741 struct cli_state *cli1;
4742 const char *pipe_name = "\\SPOOLSS";
4747 printf("starting pipenumber test\n");
4748 if (!torture_open_connection(&cli1, 0)) {
4752 cli_sockopt(cli1, sockops);
4754 status = cli_ntcreate(cli1, pipe_name, 0, FILE_READ_DATA,
4755 FILE_ATTRIBUTE_NORMAL,
4756 FILE_SHARE_READ|FILE_SHARE_WRITE,
4757 FILE_OPEN_IF, 0, 0, &fnum);
4758 if (!NT_STATUS_IS_OK(status)) {
4759 printf("Open of pipe %s failed with error (%s)\n", pipe_name, nt_errstr(status));
4763 printf("\r%6d", num_pipes);
4766 printf("pipe_number test - we can open %d %s pipes.\n", num_pipes, pipe_name );
4767 torture_close_connection(cli1);
4772 Test open mode returns on read-only files.
4774 static bool run_opentest(int dummy)
4776 static struct cli_state *cli1;
4777 static struct cli_state *cli2;
4778 const char *fname = "\\readonly.file";
4779 uint16_t fnum1, fnum2;
4782 bool correct = True;
4786 printf("starting open test\n");
4788 if (!torture_open_connection(&cli1, 0)) {
4792 cli_setatr(cli1, fname, 0, 0);
4793 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4795 cli_sockopt(cli1, sockops);
4797 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
4798 if (!NT_STATUS_IS_OK(status)) {
4799 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
4803 status = cli_close(cli1, fnum1);
4804 if (!NT_STATUS_IS_OK(status)) {
4805 printf("close2 failed (%s)\n", nt_errstr(status));
4809 status = cli_setatr(cli1, fname, FILE_ATTRIBUTE_READONLY, 0);
4810 if (!NT_STATUS_IS_OK(status)) {
4811 printf("cli_setatr failed (%s)\n", nt_errstr(status));
4815 status = cli_open(cli1, fname, O_RDONLY, DENY_WRITE, &fnum1);
4816 if (!NT_STATUS_IS_OK(status)) {
4817 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
4821 /* This will fail - but the error should be ERRnoaccess, not ERRbadshare. */
4822 cli_open(cli1, fname, O_RDWR, DENY_ALL, &fnum2);
4824 if (check_error(__LINE__, cli1, ERRDOS, ERRnoaccess,
4825 NT_STATUS_ACCESS_DENIED)) {
4826 printf("correct error code ERRDOS/ERRnoaccess returned\n");
4829 printf("finished open test 1\n");
4831 cli_close(cli1, fnum1);
4833 /* Now try not readonly and ensure ERRbadshare is returned. */
4835 cli_setatr(cli1, fname, 0, 0);
4837 status = cli_open(cli1, fname, O_RDONLY, DENY_WRITE, &fnum1);
4838 if (!NT_STATUS_IS_OK(status)) {
4839 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
4843 /* This will fail - but the error should be ERRshare. */
4844 cli_open(cli1, fname, O_RDWR, DENY_ALL, &fnum2);
4846 if (check_error(__LINE__, cli1, ERRDOS, ERRbadshare,
4847 NT_STATUS_SHARING_VIOLATION)) {
4848 printf("correct error code ERRDOS/ERRbadshare returned\n");
4851 status = cli_close(cli1, fnum1);
4852 if (!NT_STATUS_IS_OK(status)) {
4853 printf("close2 failed (%s)\n", nt_errstr(status));
4857 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4859 printf("finished open test 2\n");
4861 /* Test truncate open disposition on file opened for read. */
4862 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum1);
4863 if (!NT_STATUS_IS_OK(status)) {
4864 printf("(3) open (1) of %s failed (%s)\n", fname, nt_errstr(status));
4868 /* write 20 bytes. */
4870 memset(buf, '\0', 20);
4872 status = cli_writeall(cli1, fnum1, 0, (uint8_t *)buf, 0, 20, NULL);
4873 if (!NT_STATUS_IS_OK(status)) {
4874 printf("write failed (%s)\n", nt_errstr(status));
4878 status = cli_close(cli1, fnum1);
4879 if (!NT_STATUS_IS_OK(status)) {
4880 printf("(3) close1 failed (%s)\n", nt_errstr(status));
4884 /* Ensure size == 20. */
4885 status = cli_getatr(cli1, fname, NULL, &fsize, NULL);
4886 if (!NT_STATUS_IS_OK(status)) {
4887 printf("(3) getatr failed (%s)\n", nt_errstr(status));
4892 printf("(3) file size != 20\n");
4896 /* Now test if we can truncate a file opened for readonly. */
4897 status = cli_open(cli1, fname, O_RDONLY|O_TRUNC, DENY_NONE, &fnum1);
4898 if (!NT_STATUS_IS_OK(status)) {
4899 printf("(3) open (2) of %s failed (%s)\n", fname, nt_errstr(status));
4903 status = cli_close(cli1, fnum1);
4904 if (!NT_STATUS_IS_OK(status)) {
4905 printf("close2 failed (%s)\n", nt_errstr(status));
4909 /* Ensure size == 0. */
4910 status = cli_getatr(cli1, fname, NULL, &fsize, NULL);
4911 if (!NT_STATUS_IS_OK(status)) {
4912 printf("(3) getatr failed (%s)\n", nt_errstr(status));
4917 printf("(3) file size != 0\n");
4920 printf("finished open test 3\n");
4922 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4924 printf("Do ctemp tests\n");
4925 status = cli_ctemp(cli1, talloc_tos(), "\\", &fnum1, &tmp_path);
4926 if (!NT_STATUS_IS_OK(status)) {
4927 printf("ctemp failed (%s)\n", nt_errstr(status));
4931 printf("ctemp gave path %s\n", tmp_path);
4932 status = cli_close(cli1, fnum1);
4933 if (!NT_STATUS_IS_OK(status)) {
4934 printf("close of temp failed (%s)\n", nt_errstr(status));
4937 status = cli_unlink(cli1, tmp_path, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4938 if (!NT_STATUS_IS_OK(status)) {
4939 printf("unlink of temp failed (%s)\n", nt_errstr(status));
4942 /* Test the non-io opens... */
4944 if (!torture_open_connection(&cli2, 1)) {
4948 cli_setatr(cli2, fname, 0, 0);
4949 cli_unlink(cli2, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4951 cli_sockopt(cli2, sockops);
4953 printf("TEST #1 testing 2 non-io opens (no delete)\n");
4954 status = cli_ntcreate(cli1, fname, 0, FILE_READ_ATTRIBUTES,
4955 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4956 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4957 if (!NT_STATUS_IS_OK(status)) {
4958 printf("TEST #1 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
4962 status = cli_ntcreate(cli2, fname, 0, FILE_READ_ATTRIBUTES,
4963 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4964 FILE_OPEN_IF, 0, 0, &fnum2);
4965 if (!NT_STATUS_IS_OK(status)) {
4966 printf("TEST #1 open 2 of %s failed (%s)\n", fname, nt_errstr(status));
4970 status = cli_close(cli1, fnum1);
4971 if (!NT_STATUS_IS_OK(status)) {
4972 printf("TEST #1 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
4976 status = cli_close(cli2, fnum2);
4977 if (!NT_STATUS_IS_OK(status)) {
4978 printf("TEST #1 close 2 of %s failed (%s)\n", fname, nt_errstr(status));
4982 printf("non-io open test #1 passed.\n");
4984 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
4986 printf("TEST #2 testing 2 non-io opens (first with delete)\n");
4988 status = cli_ntcreate(cli1, fname, 0,
4989 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
4990 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4991 FILE_OVERWRITE_IF, 0, 0, &fnum1);
4992 if (!NT_STATUS_IS_OK(status)) {
4993 printf("TEST #2 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
4997 status = cli_ntcreate(cli2, fname, 0, FILE_READ_ATTRIBUTES,
4998 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
4999 FILE_OPEN_IF, 0, 0, &fnum2);
5000 if (!NT_STATUS_IS_OK(status)) {
5001 printf("TEST #2 open 2 of %s failed (%s)\n", fname, nt_errstr(status));
5005 status = cli_close(cli1, fnum1);
5006 if (!NT_STATUS_IS_OK(status)) {
5007 printf("TEST #2 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5011 status = cli_close(cli2, fnum2);
5012 if (!NT_STATUS_IS_OK(status)) {
5013 printf("TEST #2 close 2 of %s failed (%s)\n", fname, nt_errstr(status));
5017 printf("non-io open test #2 passed.\n");
5019 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5021 printf("TEST #3 testing 2 non-io opens (second with delete)\n");
5023 status = cli_ntcreate(cli1, fname, 0, FILE_READ_ATTRIBUTES,
5024 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5025 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5026 if (!NT_STATUS_IS_OK(status)) {
5027 printf("TEST #3 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
5031 status = cli_ntcreate(cli2, fname, 0,
5032 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5033 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5034 FILE_OPEN_IF, 0, 0, &fnum2);
5035 if (!NT_STATUS_IS_OK(status)) {
5036 printf("TEST #3 open 2 of %s failed (%s)\n", fname, nt_errstr(status));
5040 status = cli_close(cli1, fnum1);
5041 if (!NT_STATUS_IS_OK(status)) {
5042 printf("TEST #3 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5046 status = cli_close(cli2, fnum2);
5047 if (!NT_STATUS_IS_OK(status)) {
5048 printf("TEST #3 close 2 of %s failed (%s)\n", fname, nt_errstr(status));
5052 printf("non-io open test #3 passed.\n");
5054 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5056 printf("TEST #4 testing 2 non-io opens (both with delete)\n");
5058 status = cli_ntcreate(cli1, fname, 0,
5059 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5060 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5061 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5062 if (!NT_STATUS_IS_OK(status)) {
5063 printf("TEST #4 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
5067 status = cli_ntcreate(cli2, fname, 0,
5068 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5069 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5070 FILE_OPEN_IF, 0, 0, &fnum2);
5071 if (NT_STATUS_IS_OK(status)) {
5072 printf("TEST #4 open 2 of %s SUCCEEDED - should have failed (%s)\n", fname, nt_errstr(status));
5076 printf("TEST #4 open 2 of %s gave %s (correct error should be %s)\n", fname, nt_errstr(status), "sharing violation");
5078 status = cli_close(cli1, fnum1);
5079 if (!NT_STATUS_IS_OK(status)) {
5080 printf("TEST #4 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5084 printf("non-io open test #4 passed.\n");
5086 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5088 printf("TEST #5 testing 2 non-io opens (both with delete - both with file share delete)\n");
5090 status = cli_ntcreate(cli1, fname, 0,
5091 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5092 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_DELETE,
5093 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5094 if (!NT_STATUS_IS_OK(status)) {
5095 printf("TEST #5 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
5099 status = cli_ntcreate(cli2, fname, 0,
5100 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5101 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_DELETE,
5102 FILE_OPEN_IF, 0, 0, &fnum2);
5103 if (!NT_STATUS_IS_OK(status)) {
5104 printf("TEST #5 open 2 of %s failed (%s)\n", fname, nt_errstr(status));
5108 status = cli_close(cli1, fnum1);
5109 if (!NT_STATUS_IS_OK(status)) {
5110 printf("TEST #5 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5114 status = cli_close(cli2, fnum2);
5115 if (!NT_STATUS_IS_OK(status)) {
5116 printf("TEST #5 close 2 of %s failed (%s)\n", fname, nt_errstr(status));
5120 printf("non-io open test #5 passed.\n");
5122 printf("TEST #6 testing 1 non-io open, one io open\n");
5124 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5126 status = cli_ntcreate(cli1, fname, 0, FILE_READ_DATA,
5127 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5128 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5129 if (!NT_STATUS_IS_OK(status)) {
5130 printf("TEST #6 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
5134 status = cli_ntcreate(cli2, fname, 0, FILE_READ_ATTRIBUTES,
5135 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ,
5136 FILE_OPEN_IF, 0, 0, &fnum2);
5137 if (!NT_STATUS_IS_OK(status)) {
5138 printf("TEST #6 open 2 of %s failed (%s)\n", fname, nt_errstr(status));
5142 status = cli_close(cli1, fnum1);
5143 if (!NT_STATUS_IS_OK(status)) {
5144 printf("TEST #6 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5148 status = cli_close(cli2, fnum2);
5149 if (!NT_STATUS_IS_OK(status)) {
5150 printf("TEST #6 close 2 of %s failed (%s)\n", fname, nt_errstr(status));
5154 printf("non-io open test #6 passed.\n");
5156 printf("TEST #7 testing 1 non-io open, one io open with delete\n");
5158 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5160 status = cli_ntcreate(cli1, fname, 0, FILE_READ_DATA,
5161 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE,
5162 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5163 if (!NT_STATUS_IS_OK(status)) {
5164 printf("TEST #7 open 1 of %s failed (%s)\n", fname, nt_errstr(status));
5168 status = cli_ntcreate(cli2, fname, 0,
5169 DELETE_ACCESS|FILE_READ_ATTRIBUTES,
5170 FILE_ATTRIBUTE_NORMAL,
5171 FILE_SHARE_READ|FILE_SHARE_DELETE,
5172 FILE_OPEN_IF, 0, 0, &fnum2);
5173 if (NT_STATUS_IS_OK(status)) {
5174 printf("TEST #7 open 2 of %s SUCCEEDED - should have failed (%s)\n", fname, nt_errstr(status));
5178 printf("TEST #7 open 2 of %s gave %s (correct error should be %s)\n", fname, nt_errstr(status), "sharing violation");
5180 status = cli_close(cli1, fnum1);
5181 if (!NT_STATUS_IS_OK(status)) {
5182 printf("TEST #7 close 1 of %s failed (%s)\n", fname, nt_errstr(status));
5186 printf("non-io open test #7 passed.\n");
5188 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5190 printf("TEST #8 testing open without WRITE_ATTRIBUTES, updating close write time.\n");
5191 status = cli_ntcreate(cli1, fname, 0, FILE_WRITE_DATA, FILE_ATTRIBUTE_NORMAL,
5192 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
5193 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5194 if (!NT_STATUS_IS_OK(status)) {
5195 printf("TEST #8 open of %s failed (%s)\n", fname, nt_errstr(status));
5200 /* Write to ensure we have to update the file time. */
5201 status = cli_writeall(cli1, fnum1, 0, (const uint8_t *)"TEST DATA\n", 0, 10,
5203 if (!NT_STATUS_IS_OK(status)) {
5204 printf("TEST #8 cli_write failed: %s\n", nt_errstr(status));
5209 status = cli_close(cli1, fnum1);
5210 if (!NT_STATUS_IS_OK(status)) {
5211 printf("TEST #8 close of %s failed (%s)\n", fname, nt_errstr(status));
5217 if (!torture_close_connection(cli1)) {
5220 if (!torture_close_connection(cli2)) {
5227 NTSTATUS torture_setup_unix_extensions(struct cli_state *cli)
5229 uint16 major, minor;
5230 uint32 caplow, caphigh;
5233 if (!SERVER_HAS_UNIX_CIFS(cli)) {
5234 printf("Server doesn't support UNIX CIFS extensions.\n");
5235 return NT_STATUS_NOT_SUPPORTED;
5238 status = cli_unix_extensions_version(cli, &major, &minor, &caplow,
5240 if (!NT_STATUS_IS_OK(status)) {
5241 printf("Server didn't return UNIX CIFS extensions: %s\n",
5246 status = cli_set_unix_extensions_capabilities(cli, major, minor,
5248 if (!NT_STATUS_IS_OK(status)) {
5249 printf("Server doesn't support setting UNIX CIFS extensions: "
5250 "%s.\n", nt_errstr(status));
5254 return NT_STATUS_OK;
5258 Test POSIX open /mkdir calls.
5260 static bool run_simple_posix_open_test(int dummy)
5262 static struct cli_state *cli1;
5263 const char *fname = "posix:file";
5264 const char *hname = "posix:hlink";
5265 const char *sname = "posix:symlink";
5266 const char *dname = "posix:dir";
5269 uint16_t fnum1 = (uint16_t)-1;
5270 SMB_STRUCT_STAT sbuf;
5271 bool correct = false;
5274 printf("Starting simple POSIX open test\n");
5276 if (!torture_open_connection(&cli1, 0)) {
5280 cli_sockopt(cli1, sockops);
5282 status = torture_setup_unix_extensions(cli1);
5283 if (!NT_STATUS_IS_OK(status)) {
5287 cli_setatr(cli1, fname, 0, 0);
5288 cli_posix_unlink(cli1, fname);
5289 cli_setatr(cli1, dname, 0, 0);
5290 cli_posix_rmdir(cli1, dname);
5291 cli_setatr(cli1, hname, 0, 0);
5292 cli_posix_unlink(cli1, hname);
5293 cli_setatr(cli1, sname, 0, 0);
5294 cli_posix_unlink(cli1, sname);
5296 /* Create a directory. */
5297 status = cli_posix_mkdir(cli1, dname, 0777);
5298 if (!NT_STATUS_IS_OK(status)) {
5299 printf("POSIX mkdir of %s failed (%s)\n", dname, nt_errstr(status));
5303 status = cli_posix_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL,
5305 if (!NT_STATUS_IS_OK(status)) {
5306 printf("POSIX create of %s failed (%s)\n", fname, nt_errstr(status));
5310 /* Test ftruncate - set file size. */
5311 status = cli_ftruncate(cli1, fnum1, 1000);
5312 if (!NT_STATUS_IS_OK(status)) {
5313 printf("ftruncate failed (%s)\n", nt_errstr(status));
5317 /* Ensure st_size == 1000 */
5318 status = cli_posix_stat(cli1, fname, &sbuf);
5319 if (!NT_STATUS_IS_OK(status)) {
5320 printf("stat failed (%s)\n", nt_errstr(status));
5324 if (sbuf.st_ex_size != 1000) {
5325 printf("ftruncate - stat size (%u) != 1000\n", (unsigned int)sbuf.st_ex_size);
5329 /* Test ftruncate - set file size back to zero. */
5330 status = cli_ftruncate(cli1, fnum1, 0);
5331 if (!NT_STATUS_IS_OK(status)) {
5332 printf("ftruncate failed (%s)\n", nt_errstr(status));
5336 status = cli_close(cli1, fnum1);
5337 if (!NT_STATUS_IS_OK(status)) {
5338 printf("close failed (%s)\n", nt_errstr(status));
5342 /* Now open the file again for read only. */
5343 status = cli_posix_open(cli1, fname, O_RDONLY, 0, &fnum1);
5344 if (!NT_STATUS_IS_OK(status)) {
5345 printf("POSIX open of %s failed (%s)\n", fname, nt_errstr(status));
5349 /* Now unlink while open. */
5350 status = cli_posix_unlink(cli1, fname);
5351 if (!NT_STATUS_IS_OK(status)) {
5352 printf("POSIX unlink of %s failed (%s)\n", fname, nt_errstr(status));
5356 status = cli_close(cli1, fnum1);
5357 if (!NT_STATUS_IS_OK(status)) {
5358 printf("close(2) failed (%s)\n", nt_errstr(status));
5362 /* Ensure the file has gone. */
5363 status = cli_posix_open(cli1, fname, O_RDONLY, 0, &fnum1);
5364 if (NT_STATUS_IS_OK(status)) {
5365 printf("POSIX open of %s succeeded, should have been deleted.\n", fname);
5369 /* Create again to test open with O_TRUNC. */
5370 status = cli_posix_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, 0600, &fnum1);
5371 if (!NT_STATUS_IS_OK(status)) {
5372 printf("POSIX create of %s failed (%s)\n", fname, nt_errstr(status));
5376 /* Test ftruncate - set file size. */
5377 status = cli_ftruncate(cli1, fnum1, 1000);
5378 if (!NT_STATUS_IS_OK(status)) {
5379 printf("ftruncate failed (%s)\n", nt_errstr(status));
5383 /* Ensure st_size == 1000 */
5384 status = cli_posix_stat(cli1, fname, &sbuf);
5385 if (!NT_STATUS_IS_OK(status)) {
5386 printf("stat failed (%s)\n", nt_errstr(status));
5390 if (sbuf.st_ex_size != 1000) {
5391 printf("ftruncate - stat size (%u) != 1000\n", (unsigned int)sbuf.st_ex_size);
5395 status = cli_close(cli1, fnum1);
5396 if (!NT_STATUS_IS_OK(status)) {
5397 printf("close(2) failed (%s)\n", nt_errstr(status));
5401 /* Re-open with O_TRUNC. */
5402 status = cli_posix_open(cli1, fname, O_WRONLY|O_TRUNC, 0600, &fnum1);
5403 if (!NT_STATUS_IS_OK(status)) {
5404 printf("POSIX create of %s failed (%s)\n", fname, nt_errstr(status));
5408 /* Ensure st_size == 0 */
5409 status = cli_posix_stat(cli1, fname, &sbuf);
5410 if (!NT_STATUS_IS_OK(status)) {
5411 printf("stat failed (%s)\n", nt_errstr(status));
5415 if (sbuf.st_ex_size != 0) {
5416 printf("O_TRUNC - stat size (%u) != 0\n", (unsigned int)sbuf.st_ex_size);
5420 status = cli_close(cli1, fnum1);
5421 if (!NT_STATUS_IS_OK(status)) {
5422 printf("close failed (%s)\n", nt_errstr(status));
5426 status = cli_posix_unlink(cli1, fname);
5427 if (!NT_STATUS_IS_OK(status)) {
5428 printf("POSIX unlink of %s failed (%s)\n", fname, nt_errstr(status));
5432 status = cli_posix_open(cli1, dname, O_RDONLY, 0, &fnum1);
5433 if (!NT_STATUS_IS_OK(status)) {
5434 printf("POSIX open directory O_RDONLY of %s failed (%s)\n",
5435 dname, nt_errstr(status));
5439 cli_close(cli1, fnum1);
5441 /* What happens when we try and POSIX open a directory for write ? */
5442 status = cli_posix_open(cli1, dname, O_RDWR, 0, &fnum1);
5443 if (NT_STATUS_IS_OK(status)) {
5444 printf("POSIX open of directory %s succeeded, should have failed.\n", fname);
5447 if (!check_both_error(__LINE__, status, ERRDOS, EISDIR,
5448 NT_STATUS_FILE_IS_A_DIRECTORY)) {
5453 /* Create the file. */
5454 status = cli_posix_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL,
5456 if (!NT_STATUS_IS_OK(status)) {
5457 printf("POSIX create of %s failed (%s)\n", fname, nt_errstr(status));
5461 /* Write some data into it. */
5462 status = cli_writeall(cli1, fnum1, 0, (const uint8_t *)"TEST DATA\n", 0, 10,
5464 if (!NT_STATUS_IS_OK(status)) {
5465 printf("cli_write failed: %s\n", nt_errstr(status));
5469 cli_close(cli1, fnum1);
5471 /* Now create a hardlink. */
5472 status = cli_posix_hardlink(cli1, fname, hname);
5473 if (!NT_STATUS_IS_OK(status)) {
5474 printf("POSIX hardlink of %s failed (%s)\n", hname, nt_errstr(status));
5478 /* Now create a symlink. */
5479 status = cli_posix_symlink(cli1, fname, sname);
5480 if (!NT_STATUS_IS_OK(status)) {
5481 printf("POSIX symlink of %s failed (%s)\n", sname, nt_errstr(status));
5485 /* Open the hardlink for read. */
5486 status = cli_posix_open(cli1, hname, O_RDONLY, 0, &fnum1);
5487 if (!NT_STATUS_IS_OK(status)) {
5488 printf("POSIX open of %s failed (%s)\n", hname, nt_errstr(status));
5492 if (cli_read_old(cli1, fnum1, buf, 0, 10) != 10) {
5493 printf("POSIX read of %s failed (%s)\n", hname, cli_errstr(cli1));
5497 if (memcmp(buf, "TEST DATA\n", 10)) {
5498 printf("invalid data read from hardlink\n");
5502 /* Do a POSIX lock/unlock. */
5503 status = cli_posix_lock(cli1, fnum1, 0, 100, true, READ_LOCK);
5504 if (!NT_STATUS_IS_OK(status)) {
5505 printf("POSIX lock failed %s\n", nt_errstr(status));
5509 /* Punch a hole in the locked area. */
5510 status = cli_posix_unlock(cli1, fnum1, 10, 80);
5511 if (!NT_STATUS_IS_OK(status)) {
5512 printf("POSIX unlock failed %s\n", nt_errstr(status));
5516 cli_close(cli1, fnum1);
5518 /* Open the symlink for read - this should fail. A POSIX
5519 client should not be doing opens on a symlink. */
5520 status = cli_posix_open(cli1, sname, O_RDONLY, 0, &fnum1);
5521 if (NT_STATUS_IS_OK(status)) {
5522 printf("POSIX open of %s succeeded (should have failed)\n", sname);
5525 if (!check_both_error(__LINE__, status, ERRDOS, ERRbadpath,
5526 NT_STATUS_OBJECT_PATH_NOT_FOUND)) {
5527 printf("POSIX open of %s should have failed "
5528 "with NT_STATUS_OBJECT_PATH_NOT_FOUND, "
5529 "failed with %s instead.\n",
5530 sname, nt_errstr(status));
5535 status = cli_posix_readlink(cli1, sname, namebuf, sizeof(namebuf));
5536 if (!NT_STATUS_IS_OK(status)) {
5537 printf("POSIX readlink on %s failed (%s)\n", sname, nt_errstr(status));
5541 if (strcmp(namebuf, fname) != 0) {
5542 printf("POSIX readlink on %s failed to match name %s (read %s)\n",
5543 sname, fname, namebuf);
5547 status = cli_posix_rmdir(cli1, dname);
5548 if (!NT_STATUS_IS_OK(status)) {
5549 printf("POSIX rmdir failed (%s)\n", nt_errstr(status));
5553 printf("Simple POSIX open test passed\n");
5558 if (fnum1 != (uint16_t)-1) {
5559 cli_close(cli1, fnum1);
5560 fnum1 = (uint16_t)-1;
5563 cli_setatr(cli1, sname, 0, 0);
5564 cli_posix_unlink(cli1, sname);
5565 cli_setatr(cli1, hname, 0, 0);
5566 cli_posix_unlink(cli1, hname);
5567 cli_setatr(cli1, fname, 0, 0);
5568 cli_posix_unlink(cli1, fname);
5569 cli_setatr(cli1, dname, 0, 0);
5570 cli_posix_rmdir(cli1, dname);
5572 if (!torture_close_connection(cli1)) {
5580 static uint32 open_attrs_table[] = {
5581 FILE_ATTRIBUTE_NORMAL,
5582 FILE_ATTRIBUTE_ARCHIVE,
5583 FILE_ATTRIBUTE_READONLY,
5584 FILE_ATTRIBUTE_HIDDEN,
5585 FILE_ATTRIBUTE_SYSTEM,
5587 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY,
5588 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN,
5589 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM,
5590 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
5591 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
5592 FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
5594 FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
5595 FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
5596 FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
5597 FILE_ATTRIBUTE_HIDDEN,FILE_ATTRIBUTE_SYSTEM,
5600 struct trunc_open_results {
5607 static struct trunc_open_results attr_results[] = {
5608 { 0, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
5609 { 1, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
5610 { 2, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
5611 { 16, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
5612 { 17, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
5613 { 18, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
5614 { 51, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5615 { 54, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5616 { 56, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN },
5617 { 68, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5618 { 71, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5619 { 73, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM },
5620 { 99, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN,FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5621 { 102, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5622 { 104, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN },
5623 { 116, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5624 { 119, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5625 { 121, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM },
5626 { 170, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM|FILE_ATTRIBUTE_HIDDEN },
5627 { 173, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM },
5628 { 227, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5629 { 230, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
5630 { 232, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN },
5631 { 244, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5632 { 247, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
5633 { 249, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM }
5636 static bool run_openattrtest(int dummy)
5638 static struct cli_state *cli1;
5639 const char *fname = "\\openattr.file";
5641 bool correct = True;
5643 unsigned int i, j, k, l;
5646 printf("starting open attr test\n");
5648 if (!torture_open_connection(&cli1, 0)) {
5652 cli_sockopt(cli1, sockops);
5654 for (k = 0, i = 0; i < sizeof(open_attrs_table)/sizeof(uint32); i++) {
5655 cli_setatr(cli1, fname, 0, 0);
5656 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5658 status = cli_ntcreate(cli1, fname, 0, FILE_WRITE_DATA,
5659 open_attrs_table[i], FILE_SHARE_NONE,
5660 FILE_OVERWRITE_IF, 0, 0, &fnum1);
5661 if (!NT_STATUS_IS_OK(status)) {
5662 printf("open %d (1) of %s failed (%s)\n", i, fname, nt_errstr(status));
5666 status = cli_close(cli1, fnum1);
5667 if (!NT_STATUS_IS_OK(status)) {
5668 printf("close %d (1) of %s failed (%s)\n", i, fname, nt_errstr(status));
5672 for (j = 0; j < sizeof(open_attrs_table)/sizeof(uint32); j++) {
5673 status = cli_ntcreate(cli1, fname, 0,
5674 FILE_READ_DATA|FILE_WRITE_DATA,
5675 open_attrs_table[j],
5676 FILE_SHARE_NONE, FILE_OVERWRITE,
5678 if (!NT_STATUS_IS_OK(status)) {
5679 for (l = 0; l < sizeof(attr_results)/sizeof(struct trunc_open_results); l++) {
5680 if (attr_results[l].num == k) {
5681 printf("[%d] trunc open 0x%x -> 0x%x of %s failed - should have succeeded !(0x%x:%s)\n",
5682 k, open_attrs_table[i],
5683 open_attrs_table[j],
5684 fname, NT_STATUS_V(status), nt_errstr(status));
5689 if (!NT_STATUS_EQUAL(status, NT_STATUS_ACCESS_DENIED)) {
5690 printf("[%d] trunc open 0x%x -> 0x%x failed with wrong error code %s\n",
5691 k, open_attrs_table[i], open_attrs_table[j],
5696 printf("[%d] trunc open 0x%x -> 0x%x failed\n", k, open_attrs_table[i], open_attrs_table[j]);
5702 status = cli_close(cli1, fnum1);
5703 if (!NT_STATUS_IS_OK(status)) {
5704 printf("close %d (2) of %s failed (%s)\n", j, fname, nt_errstr(status));
5708 status = cli_getatr(cli1, fname, &attr, NULL, NULL);
5709 if (!NT_STATUS_IS_OK(status)) {
5710 printf("getatr(2) failed (%s)\n", nt_errstr(status));
5715 printf("[%d] getatr check [0x%x] trunc [0x%x] got attr 0x%x\n",
5716 k, open_attrs_table[i], open_attrs_table[j], attr );
5719 for (l = 0; l < sizeof(attr_results)/sizeof(struct trunc_open_results); l++) {
5720 if (attr_results[l].num == k) {
5721 if (attr != attr_results[l].result_attr ||
5722 open_attrs_table[i] != attr_results[l].init_attr ||
5723 open_attrs_table[j] != attr_results[l].trunc_attr) {
5724 printf("getatr check failed. [0x%x] trunc [0x%x] got attr 0x%x, should be 0x%x\n",
5725 open_attrs_table[i],
5726 open_attrs_table[j],
5728 attr_results[l].result_attr);
5738 cli_setatr(cli1, fname, 0, 0);
5739 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5741 printf("open attr test %s.\n", correct ? "passed" : "failed");
5743 if (!torture_close_connection(cli1)) {
5749 static NTSTATUS list_fn(const char *mnt, struct file_info *finfo,
5750 const char *name, void *state)
5752 int *matched = (int *)state;
5753 if (matched != NULL) {
5756 return NT_STATUS_OK;
5760 test directory listing speed
5762 static bool run_dirtest(int dummy)
5765 static struct cli_state *cli;
5767 struct timeval core_start;
5768 bool correct = True;
5771 printf("starting directory test\n");
5773 if (!torture_open_connection(&cli, 0)) {
5777 cli_sockopt(cli, sockops);
5780 for (i=0;i<torture_numops;i++) {
5782 slprintf(fname, sizeof(fname), "\\%x", (int)random());
5783 if (!NT_STATUS_IS_OK(cli_open(cli, fname, O_RDWR|O_CREAT, DENY_NONE, &fnum))) {
5784 fprintf(stderr,"Failed to open %s\n", fname);
5787 cli_close(cli, fnum);
5790 core_start = timeval_current();
5793 cli_list(cli, "a*.*", 0, list_fn, &matched);
5794 printf("Matched %d\n", matched);
5797 cli_list(cli, "b*.*", 0, list_fn, &matched);
5798 printf("Matched %d\n", matched);
5801 cli_list(cli, "xyzabc", 0, list_fn, &matched);
5802 printf("Matched %d\n", matched);
5804 printf("dirtest core %g seconds\n", timeval_elapsed(&core_start));
5807 for (i=0;i<torture_numops;i++) {
5809 slprintf(fname, sizeof(fname), "\\%x", (int)random());
5810 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5813 if (!torture_close_connection(cli)) {
5817 printf("finished dirtest\n");
5822 static NTSTATUS del_fn(const char *mnt, struct file_info *finfo, const char *mask,
5825 struct cli_state *pcli = (struct cli_state *)state;
5827 slprintf(fname, sizeof(fname), "\\LISTDIR\\%s", finfo->name);
5829 if (strcmp(finfo->name, ".") == 0 || strcmp(finfo->name, "..") == 0)
5830 return NT_STATUS_OK;
5832 if (finfo->mode & FILE_ATTRIBUTE_DIRECTORY) {
5833 if (!NT_STATUS_IS_OK(cli_rmdir(pcli, fname)))
5834 printf("del_fn: failed to rmdir %s\n,", fname );
5836 if (!NT_STATUS_IS_OK(cli_unlink(pcli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN)))
5837 printf("del_fn: failed to unlink %s\n,", fname );
5839 return NT_STATUS_OK;
5844 sees what IOCTLs are supported
5846 bool torture_ioctl_test(int dummy)
5848 static struct cli_state *cli;
5849 uint16_t device, function;
5851 const char *fname = "\\ioctl.dat";
5855 if (!torture_open_connection(&cli, 0)) {
5859 printf("starting ioctl test\n");
5861 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5863 status = cli_open(cli, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum);
5864 if (!NT_STATUS_IS_OK(status)) {
5865 printf("open of %s failed (%s)\n", fname, nt_errstr(status));
5869 status = cli_raw_ioctl(cli, fnum, 0x2d0000 | (0x0420<<2), &blob);
5870 printf("ioctl device info: %s\n", nt_errstr(status));
5872 status = cli_raw_ioctl(cli, fnum, IOCTL_QUERY_JOB_INFO, &blob);
5873 printf("ioctl job info: %s\n", nt_errstr(status));
5875 for (device=0;device<0x100;device++) {
5876 printf("ioctl test with device = 0x%x\n", device);
5877 for (function=0;function<0x100;function++) {
5878 uint32 code = (device<<16) | function;
5880 status = cli_raw_ioctl(cli, fnum, code, &blob);
5882 if (NT_STATUS_IS_OK(status)) {
5883 printf("ioctl 0x%x OK : %d bytes\n", (int)code,
5885 data_blob_free(&blob);
5890 if (!torture_close_connection(cli)) {
5899 tries varients of chkpath
5901 bool torture_chkpath_test(int dummy)
5903 static struct cli_state *cli;
5908 if (!torture_open_connection(&cli, 0)) {
5912 printf("starting chkpath test\n");
5914 /* cleanup from an old run */
5915 cli_rmdir(cli, "\\chkpath.dir\\dir2");
5916 cli_unlink(cli, "\\chkpath.dir\\*", FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5917 cli_rmdir(cli, "\\chkpath.dir");
5919 status = cli_mkdir(cli, "\\chkpath.dir");
5920 if (!NT_STATUS_IS_OK(status)) {
5921 printf("mkdir1 failed : %s\n", nt_errstr(status));
5925 status = cli_mkdir(cli, "\\chkpath.dir\\dir2");
5926 if (!NT_STATUS_IS_OK(status)) {
5927 printf("mkdir2 failed : %s\n", nt_errstr(status));
5931 status = cli_open(cli, "\\chkpath.dir\\foo.txt", O_RDWR|O_CREAT|O_EXCL,
5933 if (!NT_STATUS_IS_OK(status)) {
5934 printf("open1 failed (%s)\n", nt_errstr(status));
5937 cli_close(cli, fnum);
5939 status = cli_chkpath(cli, "\\chkpath.dir");
5940 if (!NT_STATUS_IS_OK(status)) {
5941 printf("chkpath1 failed: %s\n", nt_errstr(status));
5945 status = cli_chkpath(cli, "\\chkpath.dir\\dir2");
5946 if (!NT_STATUS_IS_OK(status)) {
5947 printf("chkpath2 failed: %s\n", nt_errstr(status));
5951 status = cli_chkpath(cli, "\\chkpath.dir\\foo.txt");
5952 if (!NT_STATUS_IS_OK(status)) {
5953 ret = check_error(__LINE__, cli, ERRDOS, ERRbadpath,
5954 NT_STATUS_NOT_A_DIRECTORY);
5956 printf("* chkpath on a file should fail\n");
5960 if (!NT_STATUS_IS_OK(cli_chkpath(cli, "\\chkpath.dir\\bar.txt"))) {
5961 ret = check_error(__LINE__, cli, ERRDOS, ERRbadfile,
5962 NT_STATUS_OBJECT_NAME_NOT_FOUND);
5964 printf("* chkpath on a non existant file should fail\n");
5968 if (!NT_STATUS_IS_OK(cli_chkpath(cli, "\\chkpath.dir\\dirxx\\bar.txt"))) {
5969 ret = check_error(__LINE__, cli, ERRDOS, ERRbadpath,
5970 NT_STATUS_OBJECT_PATH_NOT_FOUND);
5972 printf("* chkpath on a non existent component should fail\n");
5976 cli_rmdir(cli, "\\chkpath.dir\\dir2");
5977 cli_unlink(cli, "\\chkpath.dir\\*", FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
5978 cli_rmdir(cli, "\\chkpath.dir");
5980 if (!torture_close_connection(cli)) {
5987 static bool run_eatest(int dummy)
5989 static struct cli_state *cli;
5990 const char *fname = "\\eatest.txt";
5991 bool correct = True;
5995 struct ea_struct *ea_list = NULL;
5996 TALLOC_CTX *mem_ctx = talloc_init("eatest");
5999 printf("starting eatest\n");
6001 if (!torture_open_connection(&cli, 0)) {
6002 talloc_destroy(mem_ctx);
6006 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
6008 status = cli_ntcreate(cli, fname, 0,
6009 FIRST_DESIRED_ACCESS, FILE_ATTRIBUTE_ARCHIVE,
6010 FILE_SHARE_NONE, FILE_OVERWRITE_IF,
6012 if (!NT_STATUS_IS_OK(status)) {
6013 printf("open failed - %s\n", nt_errstr(status));
6014 talloc_destroy(mem_ctx);
6018 for (i = 0; i < 10; i++) {
6019 fstring ea_name, ea_val;
6021 slprintf(ea_name, sizeof(ea_name), "EA_%d", i);
6022 memset(ea_val, (char)i+1, i+1);
6023 status = cli_set_ea_fnum(cli, fnum, ea_name, ea_val, i+1);
6024 if (!NT_STATUS_IS_OK(status)) {
6025 printf("ea_set of name %s failed - %s\n", ea_name,
6027 talloc_destroy(mem_ctx);
6032 cli_close(cli, fnum);
6033 for (i = 0; i < 10; i++) {
6034 fstring ea_name, ea_val;
6036 slprintf(ea_name, sizeof(ea_name), "EA_%d", i+10);
6037 memset(ea_val, (char)i+1, i+1);
6038 status = cli_set_ea_path(cli, fname, ea_name, ea_val, i+1);
6039 if (!NT_STATUS_IS_OK(status)) {
6040 printf("ea_set of name %s failed - %s\n", ea_name,
6042 talloc_destroy(mem_ctx);
6047 status = cli_get_ea_list_path(cli, fname, mem_ctx, &num_eas, &ea_list);
6048 if (!NT_STATUS_IS_OK(status)) {
6049 printf("ea_get list failed - %s\n", nt_errstr(status));
6053 printf("num_eas = %d\n", (int)num_eas);
6055 if (num_eas != 20) {
6056 printf("Should be 20 EA's stored... failing.\n");
6060 for (i = 0; i < num_eas; i++) {
6061 printf("%d: ea_name = %s. Val = ", i, ea_list[i].name);
6062 dump_data(0, ea_list[i].value.data,
6063 ea_list[i].value.length);
6066 /* Setting EA's to zero length deletes them. Test this */
6067 printf("Now deleting all EA's - case indepenent....\n");
6070 cli_set_ea_path(cli, fname, "", "", 0);
6072 for (i = 0; i < 20; i++) {
6074 slprintf(ea_name, sizeof(ea_name), "ea_%d", i);
6075 status = cli_set_ea_path(cli, fname, ea_name, "", 0);
6076 if (!NT_STATUS_IS_OK(status)) {
6077 printf("ea_set of name %s failed - %s\n", ea_name,
6079 talloc_destroy(mem_ctx);
6085 status = cli_get_ea_list_path(cli, fname, mem_ctx, &num_eas, &ea_list);
6086 if (!NT_STATUS_IS_OK(status)) {
6087 printf("ea_get list failed - %s\n", nt_errstr(status));
6091 printf("num_eas = %d\n", (int)num_eas);
6092 for (i = 0; i < num_eas; i++) {
6093 printf("%d: ea_name = %s. Val = ", i, ea_list[i].name);
6094 dump_data(0, ea_list[i].value.data,
6095 ea_list[i].value.length);
6099 printf("deleting EA's failed.\n");
6103 /* Try and delete a non existant EA. */
6104 status = cli_set_ea_path(cli, fname, "foo", "", 0);
6105 if (!NT_STATUS_IS_OK(status)) {
6106 printf("deleting non-existant EA 'foo' should succeed. %s\n",
6111 talloc_destroy(mem_ctx);
6112 if (!torture_close_connection(cli)) {
6119 static bool run_dirtest1(int dummy)
6122 static struct cli_state *cli;
6125 bool correct = True;
6127 printf("starting directory test\n");
6129 if (!torture_open_connection(&cli, 0)) {
6133 cli_sockopt(cli, sockops);
6135 cli_list(cli, "\\LISTDIR\\*", 0, del_fn, cli);
6136 cli_list(cli, "\\LISTDIR\\*", FILE_ATTRIBUTE_DIRECTORY, del_fn, cli);
6137 cli_rmdir(cli, "\\LISTDIR");
6138 cli_mkdir(cli, "\\LISTDIR");
6140 /* Create 1000 files and 1000 directories. */
6141 for (i=0;i<1000;i++) {
6143 slprintf(fname, sizeof(fname), "\\LISTDIR\\f%d", i);
6144 if (!NT_STATUS_IS_OK(cli_ntcreate(cli, fname, 0, GENERIC_ALL_ACCESS, FILE_ATTRIBUTE_ARCHIVE,
6145 FILE_SHARE_READ|FILE_SHARE_WRITE, FILE_OVERWRITE_IF, 0, 0, &fnum))) {
6146 fprintf(stderr,"Failed to open %s\n", fname);
6149 cli_close(cli, fnum);
6151 for (i=0;i<1000;i++) {
6153 slprintf(fname, sizeof(fname), "\\LISTDIR\\d%d", i);
6154 if (!NT_STATUS_IS_OK(cli_mkdir(cli, fname))) {
6155 fprintf(stderr,"Failed to open %s\n", fname);
6160 /* Now ensure that doing an old list sees both files and directories. */
6162 cli_list_old(cli, "\\LISTDIR\\*", FILE_ATTRIBUTE_DIRECTORY, list_fn, &num_seen);
6163 printf("num_seen = %d\n", num_seen );
6164 /* We should see 100 files + 1000 directories + . and .. */
6165 if (num_seen != 2002)
6168 /* Ensure if we have the "must have" bits we only see the
6172 cli_list_old(cli, "\\LISTDIR\\*", (FILE_ATTRIBUTE_DIRECTORY<<8)|FILE_ATTRIBUTE_DIRECTORY, list_fn, &num_seen);
6173 printf("num_seen = %d\n", num_seen );
6174 if (num_seen != 1002)
6178 cli_list_old(cli, "\\LISTDIR\\*", (FILE_ATTRIBUTE_ARCHIVE<<8)|FILE_ATTRIBUTE_DIRECTORY, list_fn, &num_seen);
6179 printf("num_seen = %d\n", num_seen );
6180 if (num_seen != 1000)
6183 /* Delete everything. */
6184 cli_list(cli, "\\LISTDIR\\*", 0, del_fn, cli);
6185 cli_list(cli, "\\LISTDIR\\*", FILE_ATTRIBUTE_DIRECTORY, del_fn, cli);
6186 cli_rmdir(cli, "\\LISTDIR");
6189 printf("Matched %d\n", cli_list(cli, "a*.*", 0, list_fn, NULL));
6190 printf("Matched %d\n", cli_list(cli, "b*.*", 0, list_fn, NULL));
6191 printf("Matched %d\n", cli_list(cli, "xyzabc", 0, list_fn, NULL));
6194 if (!torture_close_connection(cli)) {
6198 printf("finished dirtest1\n");
6203 static bool run_error_map_extract(int dummy) {
6205 static struct cli_state *c_dos;
6206 static struct cli_state *c_nt;
6218 /* NT-Error connection */
6220 if (!(c_nt = open_nbt_connection())) {
6224 c_nt->use_spnego = False;
6226 status = cli_negprot(c_nt);
6228 if (!NT_STATUS_IS_OK(status)) {
6229 printf("%s rejected the NT-error negprot (%s)\n", host,
6235 status = cli_session_setup(c_nt, "", "", 0, "", 0, workgroup);
6236 if (!NT_STATUS_IS_OK(status)) {
6237 printf("%s rejected the NT-error initial session setup (%s)\n",host, nt_errstr(status));
6241 /* DOS-Error connection */
6243 if (!(c_dos = open_nbt_connection())) {
6247 c_dos->use_spnego = False;
6248 c_dos->force_dos_errors = True;
6250 status = cli_negprot(c_dos);
6251 if (!NT_STATUS_IS_OK(status)) {
6252 printf("%s rejected the DOS-error negprot (%s)\n", host,
6254 cli_shutdown(c_dos);
6258 status = cli_session_setup(c_dos, "", "", 0, "", 0, workgroup);
6259 if (!NT_STATUS_IS_OK(status)) {
6260 printf("%s rejected the DOS-error initial session setup (%s)\n",
6261 host, nt_errstr(status));
6265 for (error=(0xc0000000 | 0x1); error < (0xc0000000| 0xFFF); error++) {
6266 fstr_sprintf(user, "%X", error);
6268 status = cli_session_setup(c_nt, user,
6269 password, strlen(password),
6270 password, strlen(password),
6272 if (NT_STATUS_IS_OK(status)) {
6273 printf("/** Session setup succeeded. This shouldn't happen...*/\n");
6276 /* Case #1: 32-bit NT errors */
6277 if (cli_is_nt_error(c_nt)) {
6278 nt_status = cli_nt_error(c_nt);
6280 printf("/** Dos error on NT connection! (%s) */\n",
6282 nt_status = NT_STATUS(0xc0000000);
6285 status = cli_session_setup(c_dos, user,
6286 password, strlen(password),
6287 password, strlen(password),
6289 if (NT_STATUS_IS_OK(status)) {
6290 printf("/** Session setup succeeded. This shouldn't happen...*/\n");
6293 /* Case #1: 32-bit NT errors */
6294 if (!cli_is_dos_error(c_dos)) {
6295 printf("/** NT error on DOS connection! (%s) */\n",
6297 errnum = errclass = 0;
6299 cli_dos_error(c_dos, &errclass, &errnum);
6302 if (NT_STATUS_V(nt_status) != error) {
6303 printf("/*\t{ This NT error code was 'sqashed'\n\t from %s to %s \n\t during the session setup }\n*/\n",
6304 get_nt_error_c_code(talloc_tos(), NT_STATUS(error)),
6305 get_nt_error_c_code(talloc_tos(), nt_status));
6308 printf("\t{%s,\t%s,\t%s},\n",
6309 smb_dos_err_class(errclass),
6310 smb_dos_err_name(errclass, errnum),
6311 get_nt_error_c_code(talloc_tos(), NT_STATUS(error)));
6316 static bool run_sesssetup_bench(int dummy)
6318 static struct cli_state *c;
6319 const char *fname = "\\file.dat";
6324 if (!torture_open_connection(&c, 0)) {
6328 status = cli_ntcreate(c, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS,
6329 FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF,
6330 FILE_DELETE_ON_CLOSE, 0, &fnum);
6331 if (!NT_STATUS_IS_OK(status)) {
6332 d_printf("open %s failed: %s\n", fname, nt_errstr(status));
6336 for (i=0; i<torture_numops; i++) {
6337 status = cli_session_setup(
6339 password, strlen(password),
6340 password, strlen(password),
6342 if (!NT_STATUS_IS_OK(status)) {
6343 d_printf("(%s) cli_session_setup failed: %s\n",
6344 __location__, nt_errstr(status));
6348 d_printf("\r%d ", (int)c->vuid);
6350 status = cli_ulogoff(c);
6351 if (!NT_STATUS_IS_OK(status)) {
6352 d_printf("(%s) cli_ulogoff failed: %s\n",
6353 __location__, nt_errstr(status));
6362 static bool subst_test(const char *str, const char *user, const char *domain,
6363 uid_t uid, gid_t gid, const char *expected)
6368 subst = talloc_sub_specified(talloc_tos(), str, user, domain, uid, gid);
6370 if (strcmp(subst, expected) != 0) {
6371 printf("sub_specified(%s, %s, %s, %d, %d) returned [%s], expected "
6372 "[%s]\n", str, user, domain, (int)uid, (int)gid, subst,
6381 static void chain1_open_completion(struct tevent_req *req)
6385 status = cli_open_recv(req, &fnum);
6388 d_printf("cli_open_recv returned %s: %d\n",
6390 NT_STATUS_IS_OK(status) ? fnum : -1);
6393 static void chain1_write_completion(struct tevent_req *req)
6397 status = cli_write_andx_recv(req, &written);
6400 d_printf("cli_write_andx_recv returned %s: %d\n",
6402 NT_STATUS_IS_OK(status) ? (int)written : -1);
6405 static void chain1_close_completion(struct tevent_req *req)
6408 bool *done = (bool *)tevent_req_callback_data_void(req);
6410 status = cli_close_recv(req);
6415 d_printf("cli_close returned %s\n", nt_errstr(status));
6418 static bool run_chain1(int dummy)
6420 struct cli_state *cli1;
6421 struct event_context *evt = event_context_init(NULL);
6422 struct tevent_req *reqs[3], *smbreqs[3];
6424 const char *str = "foobar";
6427 printf("starting chain1 test\n");
6428 if (!torture_open_connection(&cli1, 0)) {
6432 cli_sockopt(cli1, sockops);
6434 reqs[0] = cli_open_create(talloc_tos(), evt, cli1, "\\test",
6435 O_CREAT|O_RDWR, 0, &smbreqs[0]);
6436 if (reqs[0] == NULL) return false;
6437 tevent_req_set_callback(reqs[0], chain1_open_completion, NULL);
6440 reqs[1] = cli_write_andx_create(talloc_tos(), evt, cli1, 0, 0,
6441 (const uint8_t *)str, 0, strlen(str)+1,
6442 smbreqs, 1, &smbreqs[1]);
6443 if (reqs[1] == NULL) return false;
6444 tevent_req_set_callback(reqs[1], chain1_write_completion, NULL);
6446 reqs[2] = cli_close_create(talloc_tos(), evt, cli1, 0, &smbreqs[2]);
6447 if (reqs[2] == NULL) return false;
6448 tevent_req_set_callback(reqs[2], chain1_close_completion, &done);
6450 status = cli_smb_chain_send(smbreqs, ARRAY_SIZE(smbreqs));
6451 if (!NT_STATUS_IS_OK(status)) {
6456 event_loop_once(evt);
6459 torture_close_connection(cli1);
6463 static void chain2_sesssetup_completion(struct tevent_req *req)
6466 status = cli_session_setup_guest_recv(req);
6467 d_printf("sesssetup returned %s\n", nt_errstr(status));
6470 static void chain2_tcon_completion(struct tevent_req *req)
6472 bool *done = (bool *)tevent_req_callback_data_void(req);
6474 status = cli_tcon_andx_recv(req);
6475 d_printf("tcon_and_x returned %s\n", nt_errstr(status));
6479 static bool run_chain2(int dummy)
6481 struct cli_state *cli1;
6482 struct event_context *evt = event_context_init(NULL);
6483 struct tevent_req *reqs[2], *smbreqs[2];
6487 printf("starting chain2 test\n");
6488 status = cli_start_connection(&cli1, lp_netbios_name(), host, NULL,
6489 port_to_use, Undefined, 0);
6490 if (!NT_STATUS_IS_OK(status)) {
6494 cli_sockopt(cli1, sockops);
6496 reqs[0] = cli_session_setup_guest_create(talloc_tos(), evt, cli1,
6498 if (reqs[0] == NULL) return false;
6499 tevent_req_set_callback(reqs[0], chain2_sesssetup_completion, NULL);
6501 reqs[1] = cli_tcon_andx_create(talloc_tos(), evt, cli1, "IPC$",
6502 "?????", NULL, 0, &smbreqs[1]);
6503 if (reqs[1] == NULL) return false;
6504 tevent_req_set_callback(reqs[1], chain2_tcon_completion, &done);
6506 status = cli_smb_chain_send(smbreqs, ARRAY_SIZE(smbreqs));
6507 if (!NT_STATUS_IS_OK(status)) {
6512 event_loop_once(evt);
6515 torture_close_connection(cli1);
6520 struct torture_createdel_state {
6521 struct tevent_context *ev;
6522 struct cli_state *cli;
6525 static void torture_createdel_created(struct tevent_req *subreq);
6526 static void torture_createdel_closed(struct tevent_req *subreq);
6528 static struct tevent_req *torture_createdel_send(TALLOC_CTX *mem_ctx,
6529 struct tevent_context *ev,
6530 struct cli_state *cli,
6533 struct tevent_req *req, *subreq;
6534 struct torture_createdel_state *state;
6536 req = tevent_req_create(mem_ctx, &state,
6537 struct torture_createdel_state);
6544 subreq = cli_ntcreate_send(
6545 state, ev, cli, name, 0,
6546 FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
6547 FILE_ATTRIBUTE_NORMAL,
6548 FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
6549 FILE_OPEN_IF, FILE_DELETE_ON_CLOSE, 0);
6551 if (tevent_req_nomem(subreq, req)) {
6552 return tevent_req_post(req, ev);
6554 tevent_req_set_callback(subreq, torture_createdel_created, req);
6558 static void torture_createdel_created(struct tevent_req *subreq)
6560 struct tevent_req *req = tevent_req_callback_data(
6561 subreq, struct tevent_req);
6562 struct torture_createdel_state *state = tevent_req_data(
6563 req, struct torture_createdel_state);
6567 status = cli_ntcreate_recv(subreq, &fnum);
6568 TALLOC_FREE(subreq);
6569 if (!NT_STATUS_IS_OK(status)) {
6570 DEBUG(10, ("cli_ntcreate_recv returned %s\n",
6571 nt_errstr(status)));
6572 tevent_req_nterror(req, status);
6576 subreq = cli_close_send(state, state->ev, state->cli, fnum);
6577 if (tevent_req_nomem(subreq, req)) {
6580 tevent_req_set_callback(subreq, torture_createdel_closed, req);
6583 static void torture_createdel_closed(struct tevent_req *subreq)
6585 struct tevent_req *req = tevent_req_callback_data(
6586 subreq, struct tevent_req);
6589 status = cli_close_recv(subreq);
6590 if (!NT_STATUS_IS_OK(status)) {
6591 DEBUG(10, ("cli_close_recv returned %s\n", nt_errstr(status)));
6592 tevent_req_nterror(req, status);
6595 tevent_req_done(req);
6598 static NTSTATUS torture_createdel_recv(struct tevent_req *req)
6600 return tevent_req_simple_recv_ntstatus(req);
6603 struct torture_createdels_state {
6604 struct tevent_context *ev;
6605 struct cli_state *cli;
6606 const char *base_name;
6610 struct tevent_req **reqs;
6613 static void torture_createdels_done(struct tevent_req *subreq);
6615 static struct tevent_req *torture_createdels_send(TALLOC_CTX *mem_ctx,
6616 struct tevent_context *ev,
6617 struct cli_state *cli,
6618 const char *base_name,
6622 struct tevent_req *req;
6623 struct torture_createdels_state *state;
6626 req = tevent_req_create(mem_ctx, &state,
6627 struct torture_createdels_state);
6633 state->base_name = talloc_strdup(state, base_name);
6634 if (tevent_req_nomem(state->base_name, req)) {
6635 return tevent_req_post(req, ev);
6637 state->num_files = MAX(num_parallel, num_files);
6639 state->received = 0;
6641 state->reqs = talloc_array(state, struct tevent_req *, num_parallel);
6642 if (tevent_req_nomem(state->reqs, req)) {
6643 return tevent_req_post(req, ev);
6646 for (i=0; i<num_parallel; i++) {
6649 name = talloc_asprintf(state, "%s%8.8d", state->base_name,
6651 if (tevent_req_nomem(name, req)) {
6652 return tevent_req_post(req, ev);
6654 state->reqs[i] = torture_createdel_send(
6655 state->reqs, state->ev, state->cli, name);
6656 if (tevent_req_nomem(state->reqs[i], req)) {
6657 return tevent_req_post(req, ev);
6659 name = talloc_move(state->reqs[i], &name);
6660 tevent_req_set_callback(state->reqs[i],
6661 torture_createdels_done, req);
6667 static void torture_createdels_done(struct tevent_req *subreq)
6669 struct tevent_req *req = tevent_req_callback_data(
6670 subreq, struct tevent_req);
6671 struct torture_createdels_state *state = tevent_req_data(
6672 req, struct torture_createdels_state);
6673 size_t num_parallel = talloc_array_length(state->reqs);
6678 status = torture_createdel_recv(subreq);
6679 if (!NT_STATUS_IS_OK(status)){
6680 DEBUG(10, ("torture_createdel_recv returned %s\n",
6681 nt_errstr(status)));
6682 TALLOC_FREE(subreq);
6683 tevent_req_nterror(req, status);
6687 for (i=0; i<num_parallel; i++) {
6688 if (subreq == state->reqs[i]) {
6692 if (i == num_parallel) {
6693 DEBUG(10, ("received something we did not send\n"));
6694 tevent_req_nterror(req, NT_STATUS_INTERNAL_ERROR);
6697 TALLOC_FREE(state->reqs[i]);
6699 if (state->sent >= state->num_files) {
6700 tevent_req_done(req);
6704 name = talloc_asprintf(state, "%s%8.8d", state->base_name,
6706 if (tevent_req_nomem(name, req)) {
6709 state->reqs[i] = torture_createdel_send(state->reqs, state->ev,
6711 if (tevent_req_nomem(state->reqs[i], req)) {
6714 name = talloc_move(state->reqs[i], &name);
6715 tevent_req_set_callback(state->reqs[i], torture_createdels_done, req);
6719 static NTSTATUS torture_createdels_recv(struct tevent_req *req)
6721 return tevent_req_simple_recv_ntstatus(req);
6724 struct swallow_notify_state {
6725 struct tevent_context *ev;
6726 struct cli_state *cli;
6728 uint32_t completion_filter;
6730 bool (*fn)(uint32_t action, const char *name, void *priv);
6734 static void swallow_notify_done(struct tevent_req *subreq);
6736 static struct tevent_req *swallow_notify_send(TALLOC_CTX *mem_ctx,
6737 struct tevent_context *ev,
6738 struct cli_state *cli,
6740 uint32_t completion_filter,
6742 bool (*fn)(uint32_t action,
6747 struct tevent_req *req, *subreq;
6748 struct swallow_notify_state *state;
6750 req = tevent_req_create(mem_ctx, &state,
6751 struct swallow_notify_state);
6758 state->completion_filter = completion_filter;
6759 state->recursive = recursive;
6763 subreq = cli_notify_send(state, state->ev, state->cli, state->fnum,
6764 0xffff, state->completion_filter,
6766 if (tevent_req_nomem(subreq, req)) {
6767 return tevent_req_post(req, ev);
6769 tevent_req_set_callback(subreq, swallow_notify_done, req);
6773 static void swallow_notify_done(struct tevent_req *subreq)
6775 struct tevent_req *req = tevent_req_callback_data(
6776 subreq, struct tevent_req);
6777 struct swallow_notify_state *state = tevent_req_data(
6778 req, struct swallow_notify_state);
6780 uint32_t i, num_changes;
6781 struct notify_change *changes;
6783 status = cli_notify_recv(subreq, state, &num_changes, &changes);
6784 TALLOC_FREE(subreq);
6785 if (!NT_STATUS_IS_OK(status)) {
6786 DEBUG(10, ("cli_notify_recv returned %s\n",
6787 nt_errstr(status)));
6788 tevent_req_nterror(req, status);
6792 for (i=0; i<num_changes; i++) {
6793 state->fn(changes[i].action, changes[i].name, state->priv);
6795 TALLOC_FREE(changes);
6797 subreq = cli_notify_send(state, state->ev, state->cli, state->fnum,
6798 0xffff, state->completion_filter,
6800 if (tevent_req_nomem(subreq, req)) {
6803 tevent_req_set_callback(subreq, swallow_notify_done, req);
6806 static bool print_notifies(uint32_t action, const char *name, void *priv)
6808 if (DEBUGLEVEL > 5) {
6809 d_printf("%d %s\n", (int)action, name);
6814 static void notify_bench_done(struct tevent_req *req)
6816 int *num_finished = (int *)tevent_req_callback_data_void(req);
6820 static bool run_notify_bench(int dummy)
6822 const char *dname = "\\notify-bench";
6823 struct tevent_context *ev;
6826 struct tevent_req *req1;
6827 struct tevent_req *req2 = NULL;
6828 int i, num_unc_names;
6829 int num_finished = 0;
6831 printf("starting notify-bench test\n");
6833 if (use_multishare_conn) {
6835 unc_list = file_lines_load(multishare_conn_fname,
6836 &num_unc_names, 0, NULL);
6837 if (!unc_list || num_unc_names <= 0) {
6838 d_printf("Failed to load unc names list from '%s'\n",
6839 multishare_conn_fname);
6842 TALLOC_FREE(unc_list);
6847 ev = tevent_context_init(talloc_tos());
6849 d_printf("tevent_context_init failed\n");
6853 for (i=0; i<num_unc_names; i++) {
6854 struct cli_state *cli;
6857 base_fname = talloc_asprintf(talloc_tos(), "%s\\file%3.3d.",
6859 if (base_fname == NULL) {
6863 if (!torture_open_connection(&cli, i)) {
6867 status = cli_ntcreate(cli, dname, 0,
6868 MAXIMUM_ALLOWED_ACCESS,
6869 0, FILE_SHARE_READ|FILE_SHARE_WRITE|
6871 FILE_OPEN_IF, FILE_DIRECTORY_FILE, 0,
6874 if (!NT_STATUS_IS_OK(status)) {
6875 d_printf("Could not create %s: %s\n", dname,
6880 req1 = swallow_notify_send(talloc_tos(), ev, cli, dnum,
6881 FILE_NOTIFY_CHANGE_FILE_NAME |
6882 FILE_NOTIFY_CHANGE_DIR_NAME |
6883 FILE_NOTIFY_CHANGE_ATTRIBUTES |
6884 FILE_NOTIFY_CHANGE_LAST_WRITE,
6885 false, print_notifies, NULL);
6887 d_printf("Could not create notify request\n");
6891 req2 = torture_createdels_send(talloc_tos(), ev, cli,
6892 base_fname, 10, torture_numops);
6894 d_printf("Could not create createdels request\n");
6897 TALLOC_FREE(base_fname);
6899 tevent_req_set_callback(req2, notify_bench_done,
6903 while (num_finished < num_unc_names) {
6905 ret = tevent_loop_once(ev);
6907 d_printf("tevent_loop_once failed\n");
6912 if (!tevent_req_poll(req2, ev)) {
6913 d_printf("tevent_req_poll failed\n");
6916 status = torture_createdels_recv(req2);
6917 d_printf("torture_createdels_recv returned %s\n", nt_errstr(status));
6922 static bool run_mangle1(int dummy)
6924 struct cli_state *cli;
6925 const char *fname = "this_is_a_long_fname_to_be_mangled.txt";
6929 time_t change_time, access_time, write_time;
6933 printf("starting mangle1 test\n");
6934 if (!torture_open_connection(&cli, 0)) {
6938 cli_sockopt(cli, sockops);
6940 status = cli_ntcreate(cli, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS,
6941 FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF,
6943 if (!NT_STATUS_IS_OK(status)) {
6944 d_printf("open %s failed: %s\n", fname, nt_errstr(status));
6947 cli_close(cli, fnum);
6949 status = cli_qpathinfo_alt_name(cli, fname, alt_name);
6950 if (!NT_STATUS_IS_OK(status)) {
6951 d_printf("cli_qpathinfo_alt_name failed: %s\n",
6955 d_printf("alt_name: %s\n", alt_name);
6957 status = cli_open(cli, alt_name, O_RDONLY, DENY_NONE, &fnum);
6958 if (!NT_STATUS_IS_OK(status)) {
6959 d_printf("cli_open(%s) failed: %s\n", alt_name,
6963 cli_close(cli, fnum);
6965 status = cli_qpathinfo1(cli, alt_name, &change_time, &access_time,
6966 &write_time, &size, &mode);
6967 if (!NT_STATUS_IS_OK(status)) {
6968 d_printf("cli_qpathinfo1(%s) failed: %s\n", alt_name,
6976 static size_t null_source(uint8_t *buf, size_t n, void *priv)
6978 size_t *to_pull = (size_t *)priv;
6979 size_t thistime = *to_pull;
6981 thistime = MIN(thistime, n);
6982 if (thistime == 0) {
6986 memset(buf, 0, thistime);
6987 *to_pull -= thistime;
6991 static bool run_windows_write(int dummy)
6993 struct cli_state *cli1;
6997 const char *fname = "\\writetest.txt";
6998 struct timeval start_time;
7003 printf("starting windows_write test\n");
7004 if (!torture_open_connection(&cli1, 0)) {
7008 status = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE, &fnum);
7009 if (!NT_STATUS_IS_OK(status)) {
7010 printf("open failed (%s)\n", nt_errstr(status));
7014 cli_sockopt(cli1, sockops);
7016 start_time = timeval_current();
7018 for (i=0; i<torture_numops; i++) {
7020 off_t start = i * torture_blocksize;
7021 size_t to_pull = torture_blocksize - 1;
7023 status = cli_writeall(cli1, fnum, 0, &c,
7024 start + torture_blocksize - 1, 1, NULL);
7025 if (!NT_STATUS_IS_OK(status)) {
7026 printf("cli_write failed: %s\n", nt_errstr(status));
7030 status = cli_push(cli1, fnum, 0, i * torture_blocksize, torture_blocksize,
7031 null_source, &to_pull);
7032 if (!NT_STATUS_IS_OK(status)) {
7033 printf("cli_push returned: %s\n", nt_errstr(status));
7038 seconds = timeval_elapsed(&start_time);
7039 kbytes = (double)torture_blocksize * torture_numops;
7042 printf("Wrote %d kbytes in %.2f seconds: %d kb/sec\n", (int)kbytes,
7043 (double)seconds, (int)(kbytes/seconds));
7047 cli_close(cli1, fnum);
7048 cli_unlink(cli1, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7049 torture_close_connection(cli1);
7053 static bool run_cli_echo(int dummy)
7055 struct cli_state *cli;
7058 printf("starting cli_echo test\n");
7059 if (!torture_open_connection(&cli, 0)) {
7062 cli_sockopt(cli, sockops);
7064 status = cli_echo(cli, 5, data_blob_const("hello", 5));
7066 d_printf("cli_echo returned %s\n", nt_errstr(status));
7068 torture_close_connection(cli);
7069 return NT_STATUS_IS_OK(status);
7072 static bool run_uid_regression_test(int dummy)
7074 static struct cli_state *cli;
7077 bool correct = True;
7080 printf("starting uid regression test\n");
7082 if (!torture_open_connection(&cli, 0)) {
7086 cli_sockopt(cli, sockops);
7088 /* Ok - now save then logoff our current user. */
7089 old_vuid = cli->vuid;
7091 status = cli_ulogoff(cli);
7092 if (!NT_STATUS_IS_OK(status)) {
7093 d_printf("(%s) cli_ulogoff failed: %s\n",
7094 __location__, nt_errstr(status));
7099 cli->vuid = old_vuid;
7101 /* Try an operation. */
7102 status = cli_mkdir(cli, "\\uid_reg_test");
7103 if (NT_STATUS_IS_OK(status)) {
7104 d_printf("(%s) cli_mkdir succeeded\n",
7109 /* Should be bad uid. */
7110 if (!check_error(__LINE__, cli, ERRSRV, ERRbaduid,
7111 NT_STATUS_USER_SESSION_DELETED)) {
7117 old_cnum = cli_state_get_tid(cli);
7119 /* Now try a SMBtdis with the invald vuid set to zero. */
7122 /* This should succeed. */
7123 status = cli_tdis(cli);
7125 if (NT_STATUS_IS_OK(status)) {
7126 d_printf("First tdis with invalid vuid should succeed.\n");
7128 d_printf("First tdis failed (%s)\n", nt_errstr(status));
7133 cli->vuid = old_vuid;
7134 cli_state_set_tid(cli, old_cnum);
7136 /* This should fail. */
7137 status = cli_tdis(cli);
7138 if (NT_STATUS_IS_OK(status)) {
7139 d_printf("Second tdis with invalid vuid should fail - succeeded instead !.\n");
7143 /* Should be bad tid. */
7144 if (!check_error(__LINE__, cli, ERRSRV, ERRinvnid,
7145 NT_STATUS_NETWORK_NAME_DELETED)) {
7151 cli_rmdir(cli, "\\uid_reg_test");
7160 static const char *illegal_chars = "*\\/?<>|\":";
7161 static char force_shortname_chars[] = " +,.[];=\177";
7163 static NTSTATUS shortname_del_fn(const char *mnt, struct file_info *finfo,
7164 const char *mask, void *state)
7166 struct cli_state *pcli = (struct cli_state *)state;
7168 NTSTATUS status = NT_STATUS_OK;
7170 slprintf(fname, sizeof(fname), "\\shortname\\%s", finfo->name);
7172 if (strcmp(finfo->name, ".") == 0 || strcmp(finfo->name, "..") == 0)
7173 return NT_STATUS_OK;
7175 if (finfo->mode & FILE_ATTRIBUTE_DIRECTORY) {
7176 status = cli_rmdir(pcli, fname);
7177 if (!NT_STATUS_IS_OK(status)) {
7178 printf("del_fn: failed to rmdir %s\n,", fname );
7181 status = cli_unlink(pcli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7182 if (!NT_STATUS_IS_OK(status)) {
7183 printf("del_fn: failed to unlink %s\n,", fname );
7195 static NTSTATUS shortname_list_fn(const char *mnt, struct file_info *finfo,
7196 const char *name, void *state)
7198 struct sn_state *s = (struct sn_state *)state;
7202 printf("shortname list: i = %d, name = |%s|, shortname = |%s|\n",
7203 i, finfo->name, finfo->short_name);
7206 if (strchr(force_shortname_chars, i)) {
7207 if (!finfo->short_name) {
7208 /* Shortname not created when it should be. */
7209 d_printf("(%s) ERROR: Shortname was not created for file %s containing %d\n",
7210 __location__, finfo->name, i);
7213 } else if (finfo->short_name){
7214 /* Shortname created when it should not be. */
7215 d_printf("(%s) ERROR: Shortname %s was created for file %s\n",
7216 __location__, finfo->short_name, finfo->name);
7220 return NT_STATUS_OK;
7223 static bool run_shortname_test(int dummy)
7225 static struct cli_state *cli;
7226 bool correct = True;
7232 printf("starting shortname test\n");
7234 if (!torture_open_connection(&cli, 0)) {
7238 cli_sockopt(cli, sockops);
7240 cli_list(cli, "\\shortname\\*", 0, shortname_del_fn, cli);
7241 cli_list(cli, "\\shortname\\*", FILE_ATTRIBUTE_DIRECTORY, shortname_del_fn, cli);
7242 cli_rmdir(cli, "\\shortname");
7244 status = cli_mkdir(cli, "\\shortname");
7245 if (!NT_STATUS_IS_OK(status)) {
7246 d_printf("(%s) cli_mkdir of \\shortname failed: %s\n",
7247 __location__, nt_errstr(status));
7252 strlcpy(fname, "\\shortname\\", sizeof(fname));
7253 strlcat(fname, "test .txt", sizeof(fname));
7257 for (i = 32; i < 128; i++) {
7258 uint16_t fnum = (uint16_t)-1;
7262 if (strchr(illegal_chars, i)) {
7267 status = cli_ntcreate(cli, fname, 0, GENERIC_ALL_ACCESS, FILE_ATTRIBUTE_NORMAL,
7268 FILE_SHARE_READ|FILE_SHARE_WRITE, FILE_OVERWRITE_IF, 0, 0, &fnum);
7269 if (!NT_STATUS_IS_OK(status)) {
7270 d_printf("(%s) cli_nt_create of %s failed: %s\n",
7271 __location__, fname, nt_errstr(status));
7275 cli_close(cli, fnum);
7278 status = cli_list(cli, "\\shortname\\test*.*", 0,
7279 shortname_list_fn, &s);
7280 if (s.matched != 1) {
7281 d_printf("(%s) failed to list %s: %s\n",
7282 __location__, fname, nt_errstr(status));
7287 status = cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7288 if (!NT_STATUS_IS_OK(status)) {
7289 d_printf("(%s) failed to delete %s: %s\n",
7290 __location__, fname, nt_errstr(status));
7303 cli_list(cli, "\\shortname\\*", 0, shortname_del_fn, cli);
7304 cli_list(cli, "\\shortname\\*", FILE_ATTRIBUTE_DIRECTORY, shortname_del_fn, cli);
7305 cli_rmdir(cli, "\\shortname");
7306 torture_close_connection(cli);
7310 static void pagedsearch_cb(struct tevent_req *req)
7313 struct tldap_message *msg;
7316 rc = tldap_search_paged_recv(req, talloc_tos(), &msg);
7317 if (rc != TLDAP_SUCCESS) {
7318 d_printf("tldap_search_paged_recv failed: %s\n",
7319 tldap_err2string(rc));
7322 if (tldap_msg_type(msg) != TLDAP_RES_SEARCH_ENTRY) {
7326 if (!tldap_entry_dn(msg, &dn)) {
7327 d_printf("tldap_entry_dn failed\n");
7330 d_printf("%s\n", dn);
7334 static bool run_tldap(int dummy)
7336 struct tldap_context *ld;
7339 struct sockaddr_storage addr;
7340 struct tevent_context *ev;
7341 struct tevent_req *req;
7345 if (!resolve_name(host, &addr, 0, false)) {
7346 d_printf("could not find host %s\n", host);
7349 status = open_socket_out(&addr, 389, 9999, &fd);
7350 if (!NT_STATUS_IS_OK(status)) {
7351 d_printf("open_socket_out failed: %s\n", nt_errstr(status));
7355 ld = tldap_context_create(talloc_tos(), fd);
7358 d_printf("tldap_context_create failed\n");
7362 rc = tldap_fetch_rootdse(ld);
7363 if (rc != TLDAP_SUCCESS) {
7364 d_printf("tldap_fetch_rootdse failed: %s\n",
7365 tldap_errstr(talloc_tos(), ld, rc));
7369 basedn = tldap_talloc_single_attribute(
7370 tldap_rootdse(ld), "defaultNamingContext", talloc_tos());
7371 if (basedn == NULL) {
7372 d_printf("no defaultNamingContext\n");
7375 d_printf("defaultNamingContext: %s\n", basedn);
7377 ev = tevent_context_init(talloc_tos());
7379 d_printf("tevent_context_init failed\n");
7383 req = tldap_search_paged_send(talloc_tos(), ev, ld, basedn,
7384 TLDAP_SCOPE_SUB, "(objectclass=*)",
7386 NULL, 0, NULL, 0, 0, 0, 0, 5);
7388 d_printf("tldap_search_paged_send failed\n");
7391 tevent_req_set_callback(req, pagedsearch_cb, NULL);
7393 tevent_req_poll(req, ev);
7397 /* test search filters against rootDSE */
7398 filter = "(&(|(name=samba)(nextRid<=10000000)(usnChanged>=10)(samba~=ambas)(!(name=s*m*a)))"
7399 "(|(name:=samba)(name:dn:2.5.13.5:=samba)(:dn:2.5.13.5:=samba)(!(name=*samba))))";
7401 rc = tldap_search(ld, "", TLDAP_SCOPE_BASE, filter,
7402 NULL, 0, 0, NULL, 0, NULL, 0, 0, 0, 0,
7403 talloc_tos(), NULL, NULL);
7404 if (rc != TLDAP_SUCCESS) {
7405 d_printf("tldap_search with complex filter failed: %s\n",
7406 tldap_errstr(talloc_tos(), ld, rc));
7414 /* Torture test to ensure no regression of :
7415 https://bugzilla.samba.org/show_bug.cgi?id=7084
7418 static bool run_dir_createtime(int dummy)
7420 struct cli_state *cli;
7421 const char *dname = "\\testdir";
7422 const char *fname = "\\testdir\\testfile";
7424 struct timespec create_time;
7425 struct timespec create_time1;
7429 if (!torture_open_connection(&cli, 0)) {
7433 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7434 cli_rmdir(cli, dname);
7436 status = cli_mkdir(cli, dname);
7437 if (!NT_STATUS_IS_OK(status)) {
7438 printf("mkdir failed: %s\n", nt_errstr(status));
7442 status = cli_qpathinfo2(cli, dname, &create_time, NULL, NULL, NULL,
7444 if (!NT_STATUS_IS_OK(status)) {
7445 printf("cli_qpathinfo2 returned %s\n",
7450 /* Sleep 3 seconds, then create a file. */
7453 status = cli_open(cli, fname, O_RDWR | O_CREAT | O_EXCL,
7455 if (!NT_STATUS_IS_OK(status)) {
7456 printf("cli_open failed: %s\n", nt_errstr(status));
7460 status = cli_qpathinfo2(cli, dname, &create_time1, NULL, NULL, NULL,
7462 if (!NT_STATUS_IS_OK(status)) {
7463 printf("cli_qpathinfo2 (2) returned %s\n",
7468 if (timespec_compare(&create_time1, &create_time)) {
7469 printf("run_dir_createtime: create time was updated (error)\n");
7471 printf("run_dir_createtime: create time was not updated (correct)\n");
7477 cli_unlink(cli, fname, FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7478 cli_rmdir(cli, dname);
7479 if (!torture_close_connection(cli)) {
7486 static bool run_streamerror(int dummy)
7488 struct cli_state *cli;
7489 const char *dname = "\\testdir";
7490 const char *streamname =
7491 "testdir:{4c8cc155-6c1e-11d1-8e41-00c04fb9386d}:$DATA";
7493 time_t change_time, access_time, write_time;
7495 uint16_t mode, fnum;
7498 if (!torture_open_connection(&cli, 0)) {
7502 cli_unlink(cli, "\\testdir\\*", FILE_ATTRIBUTE_SYSTEM | FILE_ATTRIBUTE_HIDDEN);
7503 cli_rmdir(cli, dname);
7505 status = cli_mkdir(cli, dname);
7506 if (!NT_STATUS_IS_OK(status)) {
7507 printf("mkdir failed: %s\n", nt_errstr(status));
7511 cli_qpathinfo1(cli, streamname, &change_time, &access_time, &write_time,
7513 status = cli_nt_error(cli);
7515 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
7516 printf("pathinfo returned %s, expected "
7517 "NT_STATUS_OBJECT_NAME_NOT_FOUND\n",
7522 status = cli_ntcreate(cli, streamname, 0x16,
7523 FILE_READ_DATA|FILE_READ_EA|
7524 FILE_READ_ATTRIBUTES|READ_CONTROL_ACCESS,
7525 FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ,
7526 FILE_OPEN, 0, 0, &fnum);
7528 if (!NT_STATUS_EQUAL(status, NT_STATUS_OBJECT_NAME_NOT_FOUND)) {
7529 printf("ntcreate returned %s, expected "
7530 "NT_STATUS_OBJECT_NAME_NOT_FOUND\n",
7536 cli_rmdir(cli, dname);
7540 static bool run_local_substitute(int dummy)
7544 ok &= subst_test("%U", "bla", "", -1, -1, "bla");
7545 ok &= subst_test("%u%U", "bla", "", -1, -1, "blabla");
7546 ok &= subst_test("%g", "", "", -1, -1, "NO_GROUP");
7547 ok &= subst_test("%G", "", "", -1, -1, "NO_GROUP");
7548 ok &= subst_test("%g", "", "", -1, 0, gidtoname(0));
7549 ok &= subst_test("%G", "", "", -1, 0, gidtoname(0));
7550 ok &= subst_test("%D%u", "u", "dom", -1, 0, "domu");
7551 ok &= subst_test("%i %I", "", "", -1, -1, "0.0.0.0 0.0.0.0");
7553 /* Different captialization rules in sub_basic... */
7555 ok &= (strcmp(talloc_sub_basic(talloc_tos(), "BLA", "dom", "%U%D"),
7561 static bool run_local_base64(int dummy)
7566 for (i=1; i<2000; i++) {
7567 DATA_BLOB blob1, blob2;
7570 blob1.data = talloc_array(talloc_tos(), uint8_t, i);
7572 generate_random_buffer(blob1.data, blob1.length);
7574 b64 = base64_encode_data_blob(talloc_tos(), blob1);
7576 d_fprintf(stderr, "base64_encode_data_blob failed "
7577 "for %d bytes\n", i);
7580 blob2 = base64_decode_data_blob(b64);
7583 if (data_blob_cmp(&blob1, &blob2)) {
7584 d_fprintf(stderr, "data_blob_cmp failed for %d "
7588 TALLOC_FREE(blob1.data);
7589 data_blob_free(&blob2);
7594 static bool run_local_gencache(int dummy)
7600 if (!gencache_set("foo", "bar", time(NULL) + 1000)) {
7601 d_printf("%s: gencache_set() failed\n", __location__);
7605 if (!gencache_get("foo", NULL, NULL)) {
7606 d_printf("%s: gencache_get() failed\n", __location__);
7610 if (!gencache_get("foo", &val, &tm)) {
7611 d_printf("%s: gencache_get() failed\n", __location__);
7615 if (strcmp(val, "bar") != 0) {
7616 d_printf("%s: gencache_get() returned %s, expected %s\n",
7617 __location__, val, "bar");
7624 if (!gencache_del("foo")) {
7625 d_printf("%s: gencache_del() failed\n", __location__);
7628 if (gencache_del("foo")) {
7629 d_printf("%s: second gencache_del() succeeded\n",
7634 if (gencache_get("foo", &val, &tm)) {
7635 d_printf("%s: gencache_get() on deleted entry "
7636 "succeeded\n", __location__);
7640 blob = data_blob_string_const_null("bar");
7641 tm = time(NULL) + 60;
7643 if (!gencache_set_data_blob("foo", &blob, tm)) {
7644 d_printf("%s: gencache_set_data_blob() failed\n", __location__);
7648 if (!gencache_get_data_blob("foo", &blob, NULL, NULL)) {
7649 d_printf("%s: gencache_get_data_blob() failed\n", __location__);
7653 if (strcmp((const char *)blob.data, "bar") != 0) {
7654 d_printf("%s: gencache_get_data_blob() returned %s, expected %s\n",
7655 __location__, (const char *)blob.data, "bar");
7656 data_blob_free(&blob);
7660 data_blob_free(&blob);
7662 if (!gencache_del("foo")) {
7663 d_printf("%s: gencache_del() failed\n", __location__);
7666 if (gencache_del("foo")) {
7667 d_printf("%s: second gencache_del() succeeded\n",
7672 if (gencache_get_data_blob("foo", &blob, NULL, NULL)) {
7673 d_printf("%s: gencache_get_data_blob() on deleted entry "
7674 "succeeded\n", __location__);
7681 static bool rbt_testval(struct db_context *db, const char *key,
7684 struct db_record *rec;
7685 TDB_DATA data = string_tdb_data(value);
7689 rec = db->fetch_locked(db, db, string_tdb_data(key));
7691 d_fprintf(stderr, "fetch_locked failed\n");
7694 status = rec->store(rec, data, 0);
7695 if (!NT_STATUS_IS_OK(status)) {
7696 d_fprintf(stderr, "store failed: %s\n", nt_errstr(status));
7701 rec = db->fetch_locked(db, db, string_tdb_data(key));
7703 d_fprintf(stderr, "second fetch_locked failed\n");
7706 if ((rec->value.dsize != data.dsize)
7707 || (memcmp(rec->value.dptr, data.dptr, data.dsize) != 0)) {
7708 d_fprintf(stderr, "Got wrong data back\n");
7718 static bool run_local_rbtree(int dummy)
7720 struct db_context *db;
7724 db = db_open_rbt(NULL);
7727 d_fprintf(stderr, "db_open_rbt failed\n");
7731 for (i=0; i<1000; i++) {
7734 if (asprintf(&key, "key%ld", random()) == -1) {
7737 if (asprintf(&value, "value%ld", random()) == -1) {
7742 if (!rbt_testval(db, key, value)) {
7749 if (asprintf(&value, "value%ld", random()) == -1) {
7754 if (!rbt_testval(db, key, value)) {
7773 local test for character set functions
7775 This is a very simple test for the functionality in convert_string_error()
7777 static bool run_local_convert_string(int dummy)
7779 TALLOC_CTX *tmp_ctx = talloc_new(NULL);
7780 const char *test_strings[2] = { "March", "M\303\244rz" };
7784 for (i=0; i<2; i++) {
7785 const char *str = test_strings[i];
7786 int len = strlen(str);
7787 size_t converted_size;
7790 memset(dst, 'X', sizeof(dst));
7792 /* first try with real source length */
7793 ret = convert_string_error(CH_UNIX, CH_UTF8,
7798 d_fprintf(stderr, "Failed to convert '%s' to CH_DISPLAY\n", str);
7802 if (converted_size != len) {
7803 d_fprintf(stderr, "Converted size of '%s' should be %d - got %d\n",
7804 str, len, (int)converted_size);
7808 if (strncmp(str, dst, converted_size) != 0) {
7809 d_fprintf(stderr, "Expected '%s' to match '%s'\n", str, dst);
7813 if (strlen(str) != converted_size) {
7814 d_fprintf(stderr, "Expected '%s' length %d - got %d\n", str,
7815 (int)strlen(str), (int)converted_size);
7819 if (dst[converted_size] != 'X') {
7820 d_fprintf(stderr, "Expected no termination of '%s'\n", dst);
7824 /* now with srclen==-1, this causes the nul to be
7826 ret = convert_string_error(CH_UNIX, CH_UTF8,
7831 d_fprintf(stderr, "Failed to convert '%s' to CH_DISPLAY\n", str);
7835 if (converted_size != len+1) {
7836 d_fprintf(stderr, "Converted size of '%s' should be %d - got %d\n",
7837 str, len, (int)converted_size);
7841 if (strncmp(str, dst, converted_size) != 0) {
7842 d_fprintf(stderr, "Expected '%s' to match '%s'\n", str, dst);
7846 if (len+1 != converted_size) {
7847 d_fprintf(stderr, "Expected '%s' length %d - got %d\n", str,
7848 len+1, (int)converted_size);
7852 if (dst[converted_size] != 'X') {
7853 d_fprintf(stderr, "Expected no termination of '%s'\n", dst);
7860 TALLOC_FREE(tmp_ctx);
7863 TALLOC_FREE(tmp_ctx);
7868 struct talloc_dict_test {
7872 static int talloc_dict_traverse_fn(DATA_BLOB key, void *data, void *priv)
7874 int *count = (int *)priv;
7879 static bool run_local_talloc_dict(int dummy)
7881 struct talloc_dict *dict;
7882 struct talloc_dict_test *t;
7885 dict = talloc_dict_init(talloc_tos());
7890 t = talloc(talloc_tos(), struct talloc_dict_test);
7897 if (!talloc_dict_set(dict, data_blob_const(&key, sizeof(key)), t)) {
7902 if (talloc_dict_traverse(dict, talloc_dict_traverse_fn, &count) != 0) {
7915 static bool run_local_string_to_sid(int dummy) {
7918 if (string_to_sid(&sid, "S--1-5-32-545")) {
7919 printf("allowing S--1-5-32-545\n");
7922 if (string_to_sid(&sid, "S-1-5-32-+545")) {
7923 printf("allowing S-1-5-32-+545\n");
7926 if (string_to_sid(&sid, "S-1-2-3-4-5-6-7-8-9-0-1-2-3-4-5-6-7-8-9-0")) {
7927 printf("allowing S-1-2-3-4-5-6-7-8-9-0-1-2-3-4-5-6-7-8-9-0\n");
7930 if (string_to_sid(&sid, "S-1-5-32-545-abc")) {
7931 printf("allowing S-1-5-32-545-abc\n");
7934 if (!string_to_sid(&sid, "S-1-5-32-545")) {
7935 printf("could not parse S-1-5-32-545\n");
7938 if (!dom_sid_equal(&sid, &global_sid_Builtin_Users)) {
7939 printf("mis-parsed S-1-5-32-545 as %s\n",
7940 sid_string_tos(&sid));
7946 static bool run_local_binary_to_sid(int dummy) {
7947 struct dom_sid *sid = talloc(NULL, struct dom_sid);
7948 static const char good_binary_sid[] = {
7949 0x1, /* revision number */
7951 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, /* id_auth */
7952 0x1, 0x1, 0x1, 0x1, /* auth[0] */
7953 0x1, 0x1, 0x1, 0x1, /* auth[1] */
7954 0x1, 0x1, 0x1, 0x1, /* auth[2] */
7955 0x1, 0x1, 0x1, 0x1, /* auth[3] */
7956 0x1, 0x1, 0x1, 0x1, /* auth[4] */
7957 0x1, 0x1, 0x1, 0x1, /* auth[5] */
7958 0x1, 0x1, 0x1, 0x1, /* auth[6] */
7959 0x1, 0x1, 0x1, 0x1, /* auth[7] */
7960 0x1, 0x1, 0x1, 0x1, /* auth[8] */
7961 0x1, 0x1, 0x1, 0x1, /* auth[9] */
7962 0x1, 0x1, 0x1, 0x1, /* auth[10] */
7963 0x1, 0x1, 0x1, 0x1, /* auth[11] */
7964 0x1, 0x1, 0x1, 0x1, /* auth[12] */
7965 0x1, 0x1, 0x1, 0x1, /* auth[13] */
7966 0x1, 0x1, 0x1, 0x1, /* auth[14] */
7969 static const char long_binary_sid[] = {
7970 0x1, /* revision number */
7972 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, /* id_auth */
7973 0x1, 0x1, 0x1, 0x1, /* auth[0] */
7974 0x1, 0x1, 0x1, 0x1, /* auth[1] */
7975 0x1, 0x1, 0x1, 0x1, /* auth[2] */
7976 0x1, 0x1, 0x1, 0x1, /* auth[3] */
7977 0x1, 0x1, 0x1, 0x1, /* auth[4] */
7978 0x1, 0x1, 0x1, 0x1, /* auth[5] */
7979 0x1, 0x1, 0x1, 0x1, /* auth[6] */
7980 0x1, 0x1, 0x1, 0x1, /* auth[7] */
7981 0x1, 0x1, 0x1, 0x1, /* auth[8] */
7982 0x1, 0x1, 0x1, 0x1, /* auth[9] */
7983 0x1, 0x1, 0x1, 0x1, /* auth[10] */
7984 0x1, 0x1, 0x1, 0x1, /* auth[11] */
7985 0x1, 0x1, 0x1, 0x1, /* auth[12] */
7986 0x1, 0x1, 0x1, 0x1, /* auth[13] */
7987 0x1, 0x1, 0x1, 0x1, /* auth[14] */
7988 0x1, 0x1, 0x1, 0x1, /* auth[15] */
7989 0x1, 0x1, 0x1, 0x1, /* auth[16] */
7990 0x1, 0x1, 0x1, 0x1, /* auth[17] */
7993 static const char long_binary_sid2[] = {
7994 0x1, /* revision number */
7996 0x1, 0x1, 0x1, 0x1, 0x1, 0x1, /* id_auth */
7997 0x1, 0x1, 0x1, 0x1, /* auth[0] */
7998 0x1, 0x1, 0x1, 0x1, /* auth[1] */
7999 0x1, 0x1, 0x1, 0x1, /* auth[2] */
8000 0x1, 0x1, 0x1, 0x1, /* auth[3] */
8001 0x1, 0x1, 0x1, 0x1, /* auth[4] */
8002 0x1, 0x1, 0x1, 0x1, /* auth[5] */
8003 0x1, 0x1, 0x1, 0x1, /* auth[6] */
8004 0x1, 0x1, 0x1, 0x1, /* auth[7] */
8005 0x1, 0x1, 0x1, 0x1, /* auth[8] */
8006 0x1, 0x1, 0x1, 0x1, /* auth[9] */
8007 0x1, 0x1, 0x1, 0x1, /* auth[10] */
8008 0x1, 0x1, 0x1, 0x1, /* auth[11] */
8009 0x1, 0x1, 0x1, 0x1, /* auth[12] */
8010 0x1, 0x1, 0x1, 0x1, /* auth[13] */
8011 0x1, 0x1, 0x1, 0x1, /* auth[14] */
8012 0x1, 0x1, 0x1, 0x1, /* auth[15] */
8013 0x1, 0x1, 0x1, 0x1, /* auth[16] */
8014 0x1, 0x1, 0x1, 0x1, /* auth[17] */
8015 0x1, 0x1, 0x1, 0x1, /* auth[18] */
8016 0x1, 0x1, 0x1, 0x1, /* auth[19] */
8017 0x1, 0x1, 0x1, 0x1, /* auth[20] */
8018 0x1, 0x1, 0x1, 0x1, /* auth[21] */
8019 0x1, 0x1, 0x1, 0x1, /* auth[22] */
8020 0x1, 0x1, 0x1, 0x1, /* auth[23] */
8021 0x1, 0x1, 0x1, 0x1, /* auth[24] */
8022 0x1, 0x1, 0x1, 0x1, /* auth[25] */
8023 0x1, 0x1, 0x1, 0x1, /* auth[26] */
8024 0x1, 0x1, 0x1, 0x1, /* auth[27] */
8025 0x1, 0x1, 0x1, 0x1, /* auth[28] */
8026 0x1, 0x1, 0x1, 0x1, /* auth[29] */
8027 0x1, 0x1, 0x1, 0x1, /* auth[30] */
8028 0x1, 0x1, 0x1, 0x1, /* auth[31] */
8031 if (!sid_parse(good_binary_sid, sizeof(good_binary_sid), sid)) {
8034 if (sid_parse(long_binary_sid2, sizeof(long_binary_sid2), sid)) {
8037 if (sid_parse(long_binary_sid, sizeof(long_binary_sid), sid)) {
8043 /* Split a path name into filename and stream name components. Canonicalise
8044 * such that an implicit $DATA token is always explicit.
8046 * The "specification" of this function can be found in the
8047 * run_local_stream_name() function in torture.c, I've tried those
8048 * combinations against a W2k3 server.
8051 static NTSTATUS split_ntfs_stream_name(TALLOC_CTX *mem_ctx, const char *fname,
8052 char **pbase, char **pstream)
8055 char *stream = NULL;
8056 char *sname; /* stream name */
8057 const char *stype; /* stream type */
8059 DEBUG(10, ("split_ntfs_stream_name called for [%s]\n", fname));
8061 sname = strchr_m(fname, ':');
8063 if (lp_posix_pathnames() || (sname == NULL)) {
8064 if (pbase != NULL) {
8065 base = talloc_strdup(mem_ctx, fname);
8066 NT_STATUS_HAVE_NO_MEMORY(base);
8071 if (pbase != NULL) {
8072 base = talloc_strndup(mem_ctx, fname, PTR_DIFF(sname, fname));
8073 NT_STATUS_HAVE_NO_MEMORY(base);
8078 stype = strchr_m(sname, ':');
8080 if (stype == NULL) {
8081 sname = talloc_strdup(mem_ctx, sname);
8085 if (strcasecmp_m(stype, ":$DATA") != 0) {
8087 * If there is an explicit stream type, so far we only
8088 * allow $DATA. Is there anything else allowed? -- vl
8090 DEBUG(10, ("[%s] is an invalid stream type\n", stype));
8092 return NT_STATUS_OBJECT_NAME_INVALID;
8094 sname = talloc_strndup(mem_ctx, sname, PTR_DIFF(stype, sname));
8098 if (sname == NULL) {
8100 return NT_STATUS_NO_MEMORY;
8103 if (sname[0] == '\0') {
8105 * no stream name, so no stream
8110 if (pstream != NULL) {
8111 stream = talloc_asprintf(mem_ctx, "%s:%s", sname, stype);
8112 if (stream == NULL) {
8115 return NT_STATUS_NO_MEMORY;
8118 * upper-case the type field
8120 strupper_m(strchr_m(stream, ':')+1);
8124 if (pbase != NULL) {
8127 if (pstream != NULL) {
8130 return NT_STATUS_OK;
8133 static bool test_stream_name(const char *fname, const char *expected_base,
8134 const char *expected_stream,
8135 NTSTATUS expected_status)
8139 char *stream = NULL;
8141 status = split_ntfs_stream_name(talloc_tos(), fname, &base, &stream);
8142 if (!NT_STATUS_EQUAL(status, expected_status)) {
8146 if (!NT_STATUS_IS_OK(status)) {
8150 if (base == NULL) goto error;
8152 if (strcmp(expected_base, base) != 0) goto error;
8154 if ((expected_stream != NULL) && (stream == NULL)) goto error;
8155 if ((expected_stream == NULL) && (stream != NULL)) goto error;
8157 if ((stream != NULL) && (strcmp(expected_stream, stream) != 0))
8161 TALLOC_FREE(stream);
8165 d_fprintf(stderr, "Do test_stream(%s, %s, %s, %s)\n",
8166 fname, expected_base ? expected_base : "<NULL>",
8167 expected_stream ? expected_stream : "<NULL>",
8168 nt_errstr(expected_status));
8169 d_fprintf(stderr, "-> base=%s, stream=%s, status=%s\n",
8170 base ? base : "<NULL>", stream ? stream : "<NULL>",
8173 TALLOC_FREE(stream);
8177 static bool run_local_stream_name(int dummy)
8181 ret &= test_stream_name(
8182 "bla", "bla", NULL, NT_STATUS_OK);
8183 ret &= test_stream_name(
8184 "bla::$DATA", "bla", NULL, NT_STATUS_OK);
8185 ret &= test_stream_name(
8186 "bla:blub:", "bla", NULL, NT_STATUS_OBJECT_NAME_INVALID);
8187 ret &= test_stream_name(
8188 "bla::", NULL, NULL, NT_STATUS_OBJECT_NAME_INVALID);
8189 ret &= test_stream_name(
8190 "bla::123", "bla", NULL, NT_STATUS_OBJECT_NAME_INVALID);
8191 ret &= test_stream_name(
8192 "bla:$DATA", "bla", "$DATA:$DATA", NT_STATUS_OK);
8193 ret &= test_stream_name(
8194 "bla:x:$DATA", "bla", "x:$DATA", NT_STATUS_OK);
8195 ret &= test_stream_name(
8196 "bla:x", "bla", "x:$DATA", NT_STATUS_OK);
8201 static bool data_blob_equal(DATA_BLOB a, DATA_BLOB b)
8203 if (a.length != b.length) {
8204 printf("a.length=%d != b.length=%d\n",
8205 (int)a.length, (int)b.length);
8208 if (memcmp(a.data, b.data, a.length) != 0) {
8209 printf("a.data and b.data differ\n");
8215 static bool run_local_memcache(int dummy)
8217 struct memcache *cache;
8219 DATA_BLOB d1, d2, d3;
8220 DATA_BLOB v1, v2, v3;
8222 TALLOC_CTX *mem_ctx;
8224 size_t size1, size2;
8227 cache = memcache_init(NULL, 100);
8229 if (cache == NULL) {
8230 printf("memcache_init failed\n");
8234 d1 = data_blob_const("d1", 2);
8235 d2 = data_blob_const("d2", 2);
8236 d3 = data_blob_const("d3", 2);
8238 k1 = data_blob_const("d1", 2);
8239 k2 = data_blob_const("d2", 2);
8241 memcache_add(cache, STAT_CACHE, k1, d1);
8242 memcache_add(cache, GETWD_CACHE, k2, d2);
8244 if (!memcache_lookup(cache, STAT_CACHE, k1, &v1)) {
8245 printf("could not find k1\n");
8248 if (!data_blob_equal(d1, v1)) {
8252 if (!memcache_lookup(cache, GETWD_CACHE, k2, &v2)) {
8253 printf("could not find k2\n");
8256 if (!data_blob_equal(d2, v2)) {
8260 memcache_add(cache, STAT_CACHE, k1, d3);
8262 if (!memcache_lookup(cache, STAT_CACHE, k1, &v3)) {
8263 printf("could not find replaced k1\n");
8266 if (!data_blob_equal(d3, v3)) {
8270 memcache_add(cache, GETWD_CACHE, k1, d1);
8272 if (memcache_lookup(cache, GETWD_CACHE, k2, &v2)) {
8273 printf("Did find k2, should have been purged\n");
8279 cache = memcache_init(NULL, 0);
8281 mem_ctx = talloc_init("foo");
8283 str1 = talloc_strdup(mem_ctx, "string1");
8284 str2 = talloc_strdup(mem_ctx, "string2");
8286 memcache_add_talloc(cache, SINGLETON_CACHE_TALLOC,
8287 data_blob_string_const("torture"), &str1);
8288 size1 = talloc_total_size(cache);
8290 memcache_add_talloc(cache, SINGLETON_CACHE_TALLOC,
8291 data_blob_string_const("torture"), &str2);
8292 size2 = talloc_total_size(cache);
8294 printf("size1=%d, size2=%d\n", (int)size1, (int)size2);
8296 if (size2 > size1) {
8297 printf("memcache leaks memory!\n");
8307 static void wbclient_done(struct tevent_req *req)
8310 struct winbindd_response *wb_resp;
8311 int *i = (int *)tevent_req_callback_data_void(req);
8313 wbc_err = wb_trans_recv(req, req, &wb_resp);
8316 d_printf("wb_trans_recv %d returned %s\n", *i, wbcErrorString(wbc_err));
8319 static bool run_local_wbclient(int dummy)
8321 struct event_context *ev;
8322 struct wb_context **wb_ctx;
8323 struct winbindd_request wb_req;
8324 bool result = false;
8327 BlockSignals(True, SIGPIPE);
8329 ev = tevent_context_init_byname(talloc_tos(), "epoll");
8334 wb_ctx = talloc_array(ev, struct wb_context *, nprocs);
8335 if (wb_ctx == NULL) {
8339 ZERO_STRUCT(wb_req);
8340 wb_req.cmd = WINBINDD_PING;
8342 d_printf("nprocs=%d, numops=%d\n", (int)nprocs, (int)torture_numops);
8344 for (i=0; i<nprocs; i++) {
8345 wb_ctx[i] = wb_context_init(ev, NULL);
8346 if (wb_ctx[i] == NULL) {
8349 for (j=0; j<torture_numops; j++) {
8350 struct tevent_req *req;
8351 req = wb_trans_send(ev, ev, wb_ctx[i],
8352 (j % 2) == 0, &wb_req);
8356 tevent_req_set_callback(req, wbclient_done, &i);
8362 while (i < nprocs * torture_numops) {
8363 event_loop_once(ev);
8372 static void getaddrinfo_finished(struct tevent_req *req)
8374 char *name = (char *)tevent_req_callback_data_void(req);
8375 struct addrinfo *ainfo;
8378 res = getaddrinfo_recv(req, &ainfo);
8380 d_printf("gai(%s) returned %s\n", name, gai_strerror(res));
8383 d_printf("gai(%s) succeeded\n", name);
8384 freeaddrinfo(ainfo);
8387 static bool run_getaddrinfo_send(int dummy)
8389 TALLOC_CTX *frame = talloc_stackframe();
8390 struct fncall_context *ctx;
8391 struct tevent_context *ev;
8392 bool result = false;
8393 const char *names[4] = { "www.samba.org", "notfound.samba.org",
8394 "www.slashdot.org", "heise.de" };
8395 struct tevent_req *reqs[4];
8398 ev = event_context_init(frame);
8403 ctx = fncall_context_init(frame, 4);
8405 for (i=0; i<ARRAY_SIZE(names); i++) {
8406 reqs[i] = getaddrinfo_send(frame, ev, ctx, names[i], NULL,
8408 if (reqs[i] == NULL) {
8411 tevent_req_set_callback(reqs[i], getaddrinfo_finished,
8412 discard_const_p(void, names[i]));
8415 for (i=0; i<ARRAY_SIZE(reqs); i++) {
8416 tevent_loop_once(ev);
8425 static bool dbtrans_inc(struct db_context *db)
8427 struct db_record *rec;
8432 rec = db->fetch_locked(db, db, string_term_tdb_data("transtest"));
8434 printf(__location__ "fetch_lock failed\n");
8438 if (rec->value.dsize != sizeof(uint32_t)) {
8439 printf(__location__ "value.dsize = %d\n",
8440 (int)rec->value.dsize);
8444 val = (uint32_t *)rec->value.dptr;
8447 status = rec->store(rec, make_tdb_data((uint8_t *)val,
8450 if (!NT_STATUS_IS_OK(status)) {
8451 printf(__location__ "store failed: %s\n",
8462 static bool run_local_dbtrans(int dummy)
8464 struct db_context *db;
8465 struct db_record *rec;
8470 db = db_open(talloc_tos(), "transtest.tdb", 0, TDB_DEFAULT,
8471 O_RDWR|O_CREAT, 0600);
8473 printf("Could not open transtest.db\n");
8477 res = db->transaction_start(db);
8479 printf(__location__ "transaction_start failed\n");
8483 rec = db->fetch_locked(db, db, string_term_tdb_data("transtest"));
8485 printf(__location__ "fetch_lock failed\n");
8489 if (rec->value.dptr == NULL) {
8491 status = rec->store(
8492 rec, make_tdb_data((uint8_t *)&initial,
8495 if (!NT_STATUS_IS_OK(status)) {
8496 printf(__location__ "store returned %s\n",
8504 res = db->transaction_commit(db);
8506 printf(__location__ "transaction_commit failed\n");
8514 res = db->transaction_start(db);
8516 printf(__location__ "transaction_start failed\n");
8520 if (!dbwrap_fetch_uint32(db, "transtest", &val)) {
8521 printf(__location__ "dbwrap_fetch_uint32 failed\n");
8525 for (i=0; i<10; i++) {
8526 if (!dbtrans_inc(db)) {
8531 if (!dbwrap_fetch_uint32(db, "transtest", &val2)) {
8532 printf(__location__ "dbwrap_fetch_uint32 failed\n");
8536 if (val2 != val + 10) {
8537 printf(__location__ "val=%d, val2=%d\n",
8538 (int)val, (int)val2);
8542 printf("val2=%d\r", val2);
8544 res = db->transaction_commit(db);
8546 printf(__location__ "transaction_commit failed\n");
8556 * Just a dummy test to be run under a debugger. There's no real way
8557 * to inspect the tevent_select specific function from outside of
8561 static bool run_local_tevent_select(int dummy)
8563 struct tevent_context *ev;
8564 struct tevent_fd *fd1, *fd2;
8565 bool result = false;
8567 ev = tevent_context_init_byname(NULL, "select");
8569 d_fprintf(stderr, "tevent_context_init_byname failed\n");
8573 fd1 = tevent_add_fd(ev, ev, 2, 0, NULL, NULL);
8575 d_fprintf(stderr, "tevent_add_fd failed\n");
8578 fd2 = tevent_add_fd(ev, ev, 3, 0, NULL, NULL);
8580 d_fprintf(stderr, "tevent_add_fd failed\n");
8585 fd2 = tevent_add_fd(ev, ev, 1, 0, NULL, NULL);
8587 d_fprintf(stderr, "tevent_add_fd failed\n");
8597 static double create_procs(bool (*fn)(int), bool *result)
8600 volatile pid_t *child_status;
8601 volatile bool *child_status_out;
8604 struct timeval start;
8608 child_status = (volatile pid_t *)shm_setup(sizeof(pid_t)*nprocs);
8609 if (!child_status) {
8610 printf("Failed to setup shared memory\n");
8614 child_status_out = (volatile bool *)shm_setup(sizeof(bool)*nprocs);
8615 if (!child_status_out) {
8616 printf("Failed to setup result status shared memory\n");
8620 for (i = 0; i < nprocs; i++) {
8621 child_status[i] = 0;
8622 child_status_out[i] = True;
8625 start = timeval_current();
8627 for (i=0;i<nprocs;i++) {
8630 pid_t mypid = getpid();
8631 sys_srandom(((int)mypid) ^ ((int)time(NULL)));
8633 slprintf(myname,sizeof(myname),"CLIENT%d", i);
8636 if (torture_open_connection(¤t_cli, i)) break;
8638 printf("pid %d failed to start\n", (int)getpid());
8644 child_status[i] = getpid();
8646 while (child_status[i] && timeval_elapsed(&start) < 5) smb_msleep(2);
8648 child_status_out[i] = fn(i);
8655 for (i=0;i<nprocs;i++) {
8656 if (child_status[i]) synccount++;
8658 if (synccount == nprocs) break;
8660 } while (timeval_elapsed(&start) < 30);
8662 if (synccount != nprocs) {
8663 printf("FAILED TO START %d CLIENTS (started %d)\n", nprocs, synccount);
8665 return timeval_elapsed(&start);
8668 /* start the client load */
8669 start = timeval_current();
8671 for (i=0;i<nprocs;i++) {
8672 child_status[i] = 0;
8675 printf("%d clients started\n", nprocs);
8677 for (i=0;i<nprocs;i++) {
8678 while (waitpid(0, &status, 0) == -1 && errno == EINTR) /* noop */ ;
8683 for (i=0;i<nprocs;i++) {
8684 if (!child_status_out[i]) {
8688 return timeval_elapsed(&start);
8691 #define FLAG_MULTIPROC 1
8698 {"FDPASS", run_fdpasstest, 0},
8699 {"LOCK1", run_locktest1, 0},
8700 {"LOCK2", run_locktest2, 0},
8701 {"LOCK3", run_locktest3, 0},
8702 {"LOCK4", run_locktest4, 0},
8703 {"LOCK5", run_locktest5, 0},
8704 {"LOCK6", run_locktest6, 0},
8705 {"LOCK7", run_locktest7, 0},
8706 {"LOCK8", run_locktest8, 0},
8707 {"LOCK9", run_locktest9, 0},
8708 {"UNLINK", run_unlinktest, 0},
8709 {"BROWSE", run_browsetest, 0},
8710 {"ATTR", run_attrtest, 0},
8711 {"TRANS2", run_trans2test, 0},
8712 {"MAXFID", run_maxfidtest, FLAG_MULTIPROC},
8713 {"TORTURE",run_torture, FLAG_MULTIPROC},
8714 {"RANDOMIPC", run_randomipc, 0},
8715 {"NEGNOWAIT", run_negprot_nowait, 0},
8716 {"NBENCH", run_nbench, 0},
8717 {"NBENCH2", run_nbench2, 0},
8718 {"OPLOCK1", run_oplock1, 0},
8719 {"OPLOCK2", run_oplock2, 0},
8720 {"OPLOCK4", run_oplock4, 0},
8721 {"DIR", run_dirtest, 0},
8722 {"DIR1", run_dirtest1, 0},
8723 {"DIR-CREATETIME", run_dir_createtime, 0},
8724 {"DENY1", torture_denytest1, 0},
8725 {"DENY2", torture_denytest2, 0},
8726 {"TCON", run_tcon_test, 0},
8727 {"TCONDEV", run_tcon_devtype_test, 0},
8728 {"RW1", run_readwritetest, 0},
8729 {"RW2", run_readwritemulti, FLAG_MULTIPROC},
8730 {"RW3", run_readwritelarge, 0},
8731 {"RW-SIGNING", run_readwritelarge_signtest, 0},
8732 {"OPEN", run_opentest, 0},
8733 {"POSIX", run_simple_posix_open_test, 0},
8734 {"POSIX-APPEND", run_posix_append, 0},
8735 {"CASE-INSENSITIVE-CREATE", run_case_insensitive_create, 0},
8736 {"ASYNC-ECHO", run_async_echo, 0},
8737 { "UID-REGRESSION-TEST", run_uid_regression_test, 0},
8738 { "SHORTNAME-TEST", run_shortname_test, 0},
8739 { "ADDRCHANGE", run_addrchange, 0},
8741 {"OPENATTR", run_openattrtest, 0},
8743 {"XCOPY", run_xcopy, 0},
8744 {"RENAME", run_rename, 0},
8745 {"DELETE", run_deletetest, 0},
8746 {"DELETE-LN", run_deletetest_ln, 0},
8747 {"PROPERTIES", run_properties, 0},
8748 {"MANGLE", torture_mangle, 0},
8749 {"MANGLE1", run_mangle1, 0},
8750 {"W2K", run_w2ktest, 0},
8751 {"TRANS2SCAN", torture_trans2_scan, 0},
8752 {"NTTRANSSCAN", torture_nttrans_scan, 0},
8753 {"UTABLE", torture_utable, 0},
8754 {"CASETABLE", torture_casetable, 0},
8755 {"ERRMAPEXTRACT", run_error_map_extract, 0},
8756 {"PIPE_NUMBER", run_pipe_number, 0},
8757 {"TCON2", run_tcon2_test, 0},
8758 {"IOCTL", torture_ioctl_test, 0},
8759 {"CHKPATH", torture_chkpath_test, 0},
8760 {"FDSESS", run_fdsesstest, 0},
8761 { "EATEST", run_eatest, 0},
8762 { "SESSSETUP_BENCH", run_sesssetup_bench, 0},
8763 { "CHAIN1", run_chain1, 0},
8764 { "CHAIN2", run_chain2, 0},
8765 { "WINDOWS-WRITE", run_windows_write, 0},
8766 { "NTTRANS-CREATE", run_nttrans_create, 0},
8767 { "CLI_ECHO", run_cli_echo, 0},
8768 { "GETADDRINFO", run_getaddrinfo_send, 0},
8769 { "TLDAP", run_tldap },
8770 { "STREAMERROR", run_streamerror },
8771 { "NOTIFY-BENCH", run_notify_bench },
8772 { "BAD-NBT-SESSION", run_bad_nbt_session },
8773 { "SMB-ANY-CONNECT", run_smb_any_connect },
8774 { "NOTIFY-ONLINE", run_notify_online },
8775 { "SMB2-BASIC", run_smb2_basic },
8776 { "LOCAL-SUBSTITUTE", run_local_substitute, 0},
8777 { "LOCAL-GENCACHE", run_local_gencache, 0},
8778 { "LOCAL-TALLOC-DICT", run_local_talloc_dict, 0},
8779 { "LOCAL-BASE64", run_local_base64, 0},
8780 { "LOCAL-RBTREE", run_local_rbtree, 0},
8781 { "LOCAL-MEMCACHE", run_local_memcache, 0},
8782 { "LOCAL-STREAM-NAME", run_local_stream_name, 0},
8783 { "LOCAL-WBCLIENT", run_local_wbclient, 0},
8784 { "LOCAL-string_to_sid", run_local_string_to_sid, 0},
8785 { "LOCAL-binary_to_sid", run_local_binary_to_sid, 0},
8786 { "LOCAL-DBTRANS", run_local_dbtrans, 0},
8787 { "LOCAL-TEVENT-SELECT", run_local_tevent_select, 0},
8788 { "LOCAL-CONVERT-STRING", run_local_convert_string, 0},
8793 /****************************************************************************
8794 run a specified test or "ALL"
8795 ****************************************************************************/
8796 static bool run_test(const char *name)
8803 if (strequal(name,"ALL")) {
8804 for (i=0;torture_ops[i].name;i++) {
8805 run_test(torture_ops[i].name);
8810 for (i=0;torture_ops[i].name;i++) {
8811 fstr_sprintf(randomfname, "\\XX%x",
8812 (unsigned)random());
8814 if (strequal(name, torture_ops[i].name)) {
8816 printf("Running %s\n", name);
8817 if (torture_ops[i].flags & FLAG_MULTIPROC) {
8818 t = create_procs(torture_ops[i].fn, &result);
8821 printf("TEST %s FAILED!\n", name);
8824 struct timeval start;
8825 start = timeval_current();
8826 if (!torture_ops[i].fn(0)) {
8828 printf("TEST %s FAILED!\n", name);
8830 t = timeval_elapsed(&start);
8832 printf("%s took %g secs\n\n", name, t);
8837 printf("Did not find a test named %s\n", name);
8845 static void usage(void)
8849 printf("WARNING samba4 test suite is much more complete nowadays.\n");
8850 printf("Please use samba4 torture.\n\n");
8852 printf("Usage: smbtorture //server/share <options> TEST1 TEST2 ...\n");
8854 printf("\t-d debuglevel\n");
8855 printf("\t-U user%%pass\n");
8856 printf("\t-k use kerberos\n");
8857 printf("\t-N numprocs\n");
8858 printf("\t-n my_netbios_name\n");
8859 printf("\t-W workgroup\n");
8860 printf("\t-o num_operations\n");
8861 printf("\t-O socket_options\n");
8862 printf("\t-m maximum protocol\n");
8863 printf("\t-L use oplocks\n");
8864 printf("\t-c CLIENT.TXT specify client load file for NBENCH\n");
8865 printf("\t-A showall\n");
8866 printf("\t-p port\n");
8867 printf("\t-s seed\n");
8868 printf("\t-b unclist_filename specify multiple shares for multiple connections\n");
8869 printf("\t-f filename filename to test\n");
8872 printf("tests are:");
8873 for (i=0;torture_ops[i].name;i++) {
8874 printf(" %s", torture_ops[i].name);
8878 printf("default test is ALL\n");
8883 /****************************************************************************
8885 ****************************************************************************/
8886 int main(int argc,char *argv[])
8892 bool correct = True;
8893 TALLOC_CTX *frame = talloc_stackframe();
8894 int seed = time(NULL);
8896 #ifdef HAVE_SETBUFFER
8897 setbuffer(stdout, NULL, 0);
8900 setup_logging("smbtorture", DEBUG_STDOUT);
8904 if (is_default_dyn_CONFIGFILE()) {
8905 if(getenv("SMB_CONF_PATH")) {
8906 set_dyn_CONFIGFILE(getenv("SMB_CONF_PATH"));
8909 lp_load(get_dyn_CONFIGFILE(),True,False,False,True);
8916 for(p = argv[1]; *p; p++)
8920 if (strncmp(argv[1], "//", 2)) {
8924 fstrcpy(host, &argv[1][2]);
8925 p = strchr_m(&host[2],'/');
8930 fstrcpy(share, p+1);
8932 fstrcpy(myname, get_myname(talloc_tos()));
8934 fprintf(stderr, "Failed to get my hostname.\n");
8938 if (*username == 0 && getenv("LOGNAME")) {
8939 fstrcpy(username,getenv("LOGNAME"));
8945 fstrcpy(workgroup, lp_workgroup());
8947 while ((opt = getopt(argc, argv, "p:hW:U:n:N:O:o:m:Ll:d:Aec:ks:b:B:f:"))
8951 port_to_use = atoi(optarg);
8954 seed = atoi(optarg);
8957 fstrcpy(workgroup,optarg);
8960 max_protocol = interpret_protocol(optarg, max_protocol);
8963 nprocs = atoi(optarg);
8966 torture_numops = atoi(optarg);
8969 lp_set_cmdline("log level", optarg);
8978 local_path = optarg;
8981 torture_showall = True;
8984 fstrcpy(myname, optarg);
8987 client_txt = optarg;
8994 use_kerberos = True;
8996 d_printf("No kerberos support compiled in\n");
9002 fstrcpy(username,optarg);
9003 p = strchr_m(username,'%');
9006 fstrcpy(password, p+1);
9011 fstrcpy(multishare_conn_fname, optarg);
9012 use_multishare_conn = True;
9015 torture_blocksize = atoi(optarg);
9018 test_filename = SMB_STRDUP(optarg);
9021 printf("Unknown option %c (%d)\n", (char)opt, opt);
9026 d_printf("using seed %d\n", seed);
9030 if(use_kerberos && !gotuser) gotpass = True;
9033 p = getpass("Password:");
9035 fstrcpy(password, p);
9040 printf("host=%s share=%s user=%s myname=%s\n",
9041 host, share, username, myname);
9043 if (argc == optind) {
9044 correct = run_test("ALL");
9046 for (i=optind;i<argc;i++) {
9047 if (!run_test(argv[i])) {