Fix some nonempty blank lines
[nivanova/samba-autobuild/.git] / source3 / torture / torture.c
index 4828861906fd013cd75b062978ddf5cfcee189ac..b0cf33ecafe297151d6389a7f55d1cd0978fc416 100644 (file)
@@ -2,25 +2,26 @@
    Unix SMB/CIFS implementation.
    SMB torture tester
    Copyright (C) Andrew Tridgell 1997-1998
-   
+
    This program is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
-   the Free Software Foundation; either version 2 of the License, or
+   the Free Software Foundation; either version 3 of the License, or
    (at your option) any later version.
-   
+
    This program is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.
-   
+
    You should have received a copy of the GNU General Public License
-   along with this program; if not, write to the Free Software
-   Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
+   along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */
 
-#define NO_SYSLOG
-
 #include "includes.h"
+#include "wbc_async.h"
+
+extern char *optarg;
+extern int optind;
 
 static fstring host, workgroup, share, password, username, myname;
 static int max_protocol = PROTOCOL_NT1;
@@ -28,21 +29,26 @@ static const char *sockops="TCP_NODELAY";
 static int nprocs=1;
 static int port_to_use=0;
 int torture_numops=100;
+int torture_blocksize=1024*1024;
 static int procnum; /* records process count number when forking */
 static struct cli_state *current_cli;
 static fstring randomfname;
-static BOOL use_oplocks;
-static BOOL use_level_II_oplocks;
+static bool use_oplocks;
+static bool use_level_II_oplocks;
 static const char *client_txt = "client_oplocks.txt";
-static BOOL use_kerberos;
+static bool use_kerberos;
+static fstring multishare_conn_fname;
+static bool use_multishare_conn = False;
+static bool do_encrypt;
 
-BOOL torture_showall = False;
+bool torture_showall = False;
 
-static double create_procs(BOOL (*fn)(int), BOOL *result);
+static double create_procs(bool (*fn)(int), bool *result);
 
 
 static struct timeval tp1,tp2;
 
+
 void start_timer(void)
 {
        GetTimeOfDay(&tp1);
@@ -88,33 +94,85 @@ void *shm_setup(int size)
           See Stevens "advanced programming in unix env" for details
           */
        shmctl(shmid, IPC_RMID, 0);
-       
+
        return ret;
 }
 
+/********************************************************************
+ Ensure a connection is encrypted.
+********************************************************************/
 
-static BOOL open_nbt_connection(struct cli_state *c)
+static bool force_cli_encryption(struct cli_state *c,
+                       const char *sharename)
 {
-       struct nmb_name called, calling;
-       struct in_addr ip;
+       uint16 major, minor;
+       uint32 caplow, caphigh;
+       NTSTATUS status;
+
+       if (!SERVER_HAS_UNIX_CIFS(c)) {
+               d_printf("Encryption required and "
+                       "server that doesn't support "
+                       "UNIX extensions - failing connect\n");
+                       return false;
+       }
+
+       if (!cli_unix_extensions_version(c, &major, &minor, &caplow, &caphigh)) {
+               d_printf("Encryption required and "
+                       "can't get UNIX CIFS extensions "
+                       "version from server.\n");
+               return false;
+       }
+
+       if (!(caplow & CIFS_UNIX_TRANSPORT_ENCRYPTION_CAP)) {
+               d_printf("Encryption required and "
+                       "share %s doesn't support "
+                       "encryption.\n", sharename);
+               return false;
+       }
+
+       if (c->use_kerberos) {
+               status = cli_gss_smb_encryption_start(c);
+       } else {
+               status = cli_raw_ntlm_smb_encryption_start(c,
+                                               username,
+                                               password,
+                                               workgroup);
+       }
+
+       if (!NT_STATUS_IS_OK(status)) {
+               d_printf("Encryption required and "
+                       "setup failed with error %s.\n",
+                       nt_errstr(status));
+               return false;
+       }
+
+       return true;
+}
+
 
-       ZERO_STRUCTP(c);
+static struct cli_state *open_nbt_connection(void)
+{
+       struct nmb_name called, calling;
+       struct sockaddr_storage ss;
+       struct cli_state *c;
+       NTSTATUS status;
 
        make_nmb_name(&calling, myname, 0x0);
        make_nmb_name(&called , host, 0x20);
 
-        zero_ip(&ip);
+        zero_sockaddr(&ss);
 
-       if (!cli_initialise(c)) {
+       if (!(c = cli_initialise())) {
                printf("Failed initialize cli_struct to connect with %s\n", host);
-               return False;
+               return NULL;
        }
 
        c->port = port_to_use;
 
-       if (!cli_connect(c, host, &ip)) {
-               printf("Failed to connect with %s\n", host);
-               return False;
+       status = cli_connect(c, host, &ss);
+       if (!NT_STATUS_IS_OK(status)) {
+               printf("Failed to connect with %s. Error %s\n", host, nt_errstr(status) );
+               return NULL;
        }
 
        c->use_kerberos = use_kerberos;
@@ -125,12 +183,13 @@ static BOOL open_nbt_connection(struct cli_state *c)
 
        if (!cli_session_request(c, &calling, &called)) {
                /*
-                * Well, that failed, try *SMBSERVER ... 
+                * Well, that failed, try *SMBSERVER ...
                 * However, we must reconnect as well ...
                 */
-               if (!cli_connect(c, host, &ip)) {
-                       printf("Failed to connect with %s\n", host);
-                       return False;
+               status = cli_connect(c, host, &ss);
+               if (!NT_STATUS_IS_OK(status)) {
+                       printf("Failed to connect with %s. Error %s\n", host, nt_errstr(status) );
+                       return NULL;
                }
 
                make_nmb_name(&called, "*SMBSERVER", 0x20);
@@ -139,58 +198,165 @@ static BOOL open_nbt_connection(struct cli_state *c)
                        printf("We tried with a called name of %s & %s\n",
                                host, "*SMBSERVER");
                        cli_shutdown(c);
-                       return False;
+                       return NULL;
                }
        }
 
-       return True;
+       return c;
+}
+
+/* Insert a NULL at the first separator of the given path and return a pointer
+ * to the remainder of the string.
+ */
+static char *
+terminate_path_at_separator(char * path)
+{
+       char * p;
+
+       if (!path) {
+               return NULL;
+       }
+
+       if ((p = strchr_m(path, '/'))) {
+               *p = '\0';
+               return p + 1;
+       }
+
+       if ((p = strchr_m(path, '\\'))) {
+               *p = '\0';
+               return p + 1;
+       }
+
+       /* No separator. */
+       return NULL;
+}
+
+/*
+  parse a //server/share type UNC name
+*/
+bool smbcli_parse_unc(const char *unc_name, TALLOC_CTX *mem_ctx,
+                     char **hostname, char **sharename)
+{
+       char *p;
+
+       *hostname = *sharename = NULL;
+
+       if (strncmp(unc_name, "\\\\", 2) &&
+           strncmp(unc_name, "//", 2)) {
+               return False;
+       }
+
+       *hostname = talloc_strdup(mem_ctx, &unc_name[2]);
+       p = terminate_path_at_separator(*hostname);
+
+       if (p && *p) {
+               *sharename = talloc_strdup(mem_ctx, p);
+               terminate_path_at_separator(*sharename);
+       }
+
+       if (*hostname && *sharename) {
+               return True;
+       }
+
+       TALLOC_FREE(*hostname);
+       TALLOC_FREE(*sharename);
+       return False;
 }
 
-BOOL torture_open_connection(struct cli_state **c)
+static bool torture_open_connection_share(struct cli_state **c,
+                                  const char *hostname, 
+                                  const char *sharename)
 {
-       BOOL retry;
+       bool retry;
        int flags = 0;
        NTSTATUS status;
 
        if (use_kerberos)
                flags |= CLI_FULL_CONNECTION_USE_KERBEROS;
-       
+       if (use_oplocks)
+               flags |= CLI_FULL_CONNECTION_OPLOCKS;
+       if (use_level_II_oplocks)
+               flags |= CLI_FULL_CONNECTION_LEVEL_II_OPLOCKS;
+
        status = cli_full_connection(c, myname,
-                                    host, NULL, port_to_use, 
-                                    share, "?????", 
+                                    hostname, NULL, port_to_use, 
+                                    sharename, "?????", 
                                     username, workgroup, 
                                     password, flags, Undefined, &retry);
        if (!NT_STATUS_IS_OK(status)) {
+               printf("failed to open share connection: //%s/%s port:%d - %s\n",
+                       hostname, sharename, port_to_use, nt_errstr(status));
                return False;
        }
 
-       if (use_oplocks) (*c)->use_oplocks = True;
-       if (use_level_II_oplocks) (*c)->use_level_II_oplocks = True;
        (*c)->timeout = 120000; /* set a really long timeout (2 minutes) */
 
+       if (do_encrypt) {
+               return force_cli_encryption(*c,
+                                       sharename);
+       }
        return True;
 }
 
-BOOL torture_cli_session_setup2(struct cli_state *cli, uint16 *new_vuid)
+bool torture_open_connection(struct cli_state **c, int conn_index)
+{
+       char **unc_list = NULL;
+       int num_unc_names = 0;
+       bool result;
+
+       if (use_multishare_conn==True) {
+               char *h, *s;
+               unc_list = file_lines_load(multishare_conn_fname, &num_unc_names, 0, NULL);
+               if (!unc_list || num_unc_names <= 0) {
+                       printf("Failed to load unc names list from '%s'\n", multishare_conn_fname);
+                       exit(1);
+               }
+
+               if (!smbcli_parse_unc(unc_list[conn_index % num_unc_names],
+                                     NULL, &h, &s)) {
+                       printf("Failed to parse UNC name %s\n",
+                              unc_list[conn_index % num_unc_names]);
+                       TALLOC_FREE(unc_list);
+                       exit(1);
+               }
+
+               result = torture_open_connection_share(c, h, s);
+
+               /* h, s were copied earlier */
+               TALLOC_FREE(unc_list);
+               return result;
+       }
+
+       return torture_open_connection_share(c, host, share);
+}
+
+bool torture_cli_session_setup2(struct cli_state *cli, uint16 *new_vuid)
 {
        uint16 old_vuid = cli->vuid;
        fstring old_user_name;
        size_t passlen = strlen(password);
-       BOOL ret;
+       NTSTATUS status;
+       bool ret;
 
        fstrcpy(old_user_name, cli->user_name);
        cli->vuid = 0;
-       ret = cli_session_setup(cli, username, password, passlen, password, passlen, workgroup);
+       ret = NT_STATUS_IS_OK(cli_session_setup(cli, username,
+                                               password, passlen,
+                                               password, passlen,
+                                               workgroup));
        *new_vuid = cli->vuid;
        cli->vuid = old_vuid;
-       fstrcpy(cli->user_name, old_user_name);
+       status = cli_set_username(cli, old_user_name);
+       if (!NT_STATUS_IS_OK(status)) {
+               return false;
+       }
        return ret;
 }
 
 
-BOOL torture_close_connection(struct cli_state *c)
+bool torture_close_connection(struct cli_state *c)
 {
-       BOOL ret = True;
+       bool ret = True;
        if (!cli_tdis(c)) {
                printf("tdis failed (%s)\n", cli_errstr(c));
                ret = False;
@@ -203,20 +369,20 @@ BOOL torture_close_connection(struct cli_state *c)
 
 
 /* check if the server produced the expected error code */
-static BOOL check_error(int line, struct cli_state *c, 
+static bool check_error(int line, struct cli_state *c, 
                        uint8 eclass, uint32 ecode, NTSTATUS nterr)
 {
         if (cli_is_dos_error(c)) {
-                uint8 class;
+                uint8 cclass;
                 uint32 num;
 
                 /* Check DOS error */
 
-                cli_dos_error(c, &class, &num);
+                cli_dos_error(c, &cclass, &num);
 
-                if (eclass != class || ecode != num) {
+                if (eclass != cclass || ecode != num) {
                         printf("unexpected error code class=%d code=%d\n", 
-                               (int)class, (int)num);
+                               (int)cclass, (int)num);
                         printf(" expected %d/%d %s (line=%d)\n", 
                                (int)eclass, (int)ecode, nt_errstr(nterr), line);
                         return False;
@@ -240,7 +406,7 @@ static BOOL check_error(int line, struct cli_state *c,
 }
 
 
-static BOOL wait_lock(struct cli_state *c, int fnum, uint32 offset, uint32 len)
+static bool wait_lock(struct cli_state *c, int fnum, uint32 offset, uint32 len)
 {
        while (!cli_lock(c, fnum, offset, len, -1, WRITE_LOCK)) {
                if (!check_error(__LINE__, c, ERRDOS, ERRlock, NT_STATUS_LOCK_NOT_GRANTED)) return False;
@@ -249,7 +415,7 @@ static BOOL wait_lock(struct cli_state *c, int fnum, uint32 offset, uint32 len)
 }
 
 
-static BOOL rw_torture(struct cli_state *c)
+static bool rw_torture(struct cli_state *c)
 {
        const char *lockfname = "\\torture.lck";
        fstring fname;
@@ -258,7 +424,9 @@ static BOOL rw_torture(struct cli_state *c)
        pid_t pid2, pid = getpid();
        int i, j;
        char buf[1024];
-       BOOL correct = True;
+       bool correct = True;
+
+       memset(buf, '\0', sizeof(buf));
 
        fnum2 = cli_open(c, lockfname, O_RDWR | O_CREAT | O_EXCL, 
                         DENY_NONE);
@@ -338,17 +506,17 @@ static BOOL rw_torture(struct cli_state *c)
        return correct;
 }
 
-static BOOL run_torture(int dummy)
+static bool run_torture(int dummy)
 {
        struct cli_state *cli;
-        BOOL ret;
+        bool ret;
 
        cli = current_cli;
 
        cli_sockopt(cli, sockops);
 
        ret = rw_torture(cli);
-       
+
        if (!torture_close_connection(cli)) {
                ret = False;
        }
@@ -356,7 +524,7 @@ static BOOL run_torture(int dummy)
        return ret;
 }
 
-static BOOL rw_torture3(struct cli_state *c, char *lockfname)
+static bool rw_torture3(struct cli_state *c, char *lockfname)
 {
        int fnum = -1;
        unsigned int i = 0;
@@ -365,7 +533,7 @@ static BOOL rw_torture3(struct cli_state *c, char *lockfname)
        unsigned count;
        unsigned countprev = 0;
        ssize_t sent = 0;
-       BOOL correct = True;
+       bool correct = True;
 
        srandom(1);
        for (i = 0; i < sizeof(buf); i += sizeof(uint32))
@@ -455,15 +623,15 @@ static BOOL rw_torture3(struct cli_state *c, char *lockfname)
        return correct;
 }
 
-static BOOL rw_torture2(struct cli_state *c1, struct cli_state *c2)
+static bool rw_torture2(struct cli_state *c1, struct cli_state *c2)
 {
        const char *lockfname = "\\torture2.lck";
        int fnum1;
        int fnum2;
        int i;
-       uchar buf[131072];
-       uchar buf_rd[131072];
-       BOOL correct = True;
+       char buf[131072];
+       char buf_rd[131072];
+       bool correct = True;
        ssize_t bytes_read;
 
        if (!cli_unlink(c1, lockfname)) {
@@ -493,7 +661,7 @@ static BOOL rw_torture2(struct cli_state *c1, struct cli_state *c2)
                        printf("%d\r", i); fflush(stdout);
                }
 
-               generate_random_buffer(buf, buf_size);
+               generate_random_buffer((unsigned char *)buf, buf_size);
 
                if (cli_write(c1, fnum1, 0, buf, 0, buf_size) != buf_size) {
                        printf("write failed (%s)\n", cli_errstr(c1));
@@ -503,7 +671,7 @@ static BOOL rw_torture2(struct cli_state *c1, struct cli_state *c2)
 
                if ((bytes_read = cli_read(c2, fnum2, buf_rd, 0, buf_size)) != buf_size) {
                        printf("read failed (%s)\n", cli_errstr(c2));
-                       printf("read %d, expected %ld\n", bytes_read, 
+                       printf("read %d, expected %ld\n", (int)bytes_read, 
                               (unsigned long)buf_size); 
                        correct = False;
                        break;
@@ -534,12 +702,12 @@ static BOOL rw_torture2(struct cli_state *c1, struct cli_state *c2)
        return correct;
 }
 
-static BOOL run_readwritetest(int dummy)
+static bool run_readwritetest(int dummy)
 {
        static struct cli_state *cli1, *cli2;
-       BOOL test1, test2;
+       bool test1, test2 = False;
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
        cli_sockopt(cli1, sockops);
@@ -566,10 +734,10 @@ static BOOL run_readwritetest(int dummy)
        return (test1 && test2);
 }
 
-static BOOL run_readwritemulti(int dummy)
+static bool run_readwritemulti(int dummy)
 {
        struct cli_state *cli;
-       BOOL test;
+       bool test;
 
        cli = current_cli;
 
@@ -581,29 +749,29 @@ static BOOL run_readwritemulti(int dummy)
        if (!torture_close_connection(cli)) {
                test = False;
        }
-       
+
        return test;
 }
 
-static BOOL run_readwritelarge(int dummy)
+static bool run_readwritelarge(int dummy)
 {
        static struct cli_state *cli1;
        int fnum1;
        const char *lockfname = "\\large.dat";
        SMB_OFF_T fsize;
        char buf[126*1024];
-       BOOL correct = True;
-       if (!torture_open_connection(&cli1)) {
+       bool correct = True;
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
        cli_sockopt(cli1, sockops);
        memset(buf,'\0',sizeof(buf));
-       
+
        cli1->max_xmit = 128*1024;
-       
+
        printf("starting readwritelarge\n");
+
        cli_unlink(cli1, lockfname);
 
        fnum1 = cli_open(cli1, lockfname, O_RDWR | O_CREAT | O_EXCL, DENY_NONE);
@@ -611,7 +779,7 @@ static BOOL run_readwritelarge(int dummy)
                printf("open read/write of %s failed (%s)\n", lockfname, cli_errstr(cli1));
                return False;
        }
-   
+
        cli_write(cli1, fnum1, 0, buf, 0, sizeof(buf));
 
        if (!cli_qfileinfo(cli1, fnum1, NULL, &fsize, NULL, NULL, NULL, NULL, NULL)) {
@@ -643,11 +811,11 @@ static BOOL run_readwritelarge(int dummy)
                printf("open read/write of %s failed (%s)\n", lockfname, cli_errstr(cli1));
                return False;
        }
-       
+
        cli1->max_xmit = 4*1024;
-       
+
        cli_smbwrite(cli1, fnum1, buf, 0, sizeof(buf));
-       
+
        if (!cli_qfileinfo(cli1, fnum1, NULL, &fsize, NULL, NULL, NULL, NULL, NULL)) {
                printf("qfileinfo failed (%s)\n", cli_errstr(cli1));
                correct = False;
@@ -680,7 +848,7 @@ static BOOL run_readwritelarge(int dummy)
                printf("close failed (%s)\n", cli_errstr(cli1));
                correct = False;
        }
-       
+
        if (!torture_close_connection(cli1)) {
                correct = False;
        }
@@ -693,16 +861,15 @@ int nbio_id;
 #define ival(s) strtol(s, NULL, 0)
 
 /* run a test that simulates an approximate netbench client load */
-static BOOL run_netbench(int client)
+static bool run_netbench(int client)
 {
        struct cli_state *cli;
        int i;
-       fstring fname;
-       pstring line;
+       char line[1024];
        char cname[20];
        FILE *f;
        const char *params[20];
-       BOOL correct = True;
+       bool correct = True;
 
        cli = current_cli;
 
@@ -712,7 +879,7 @@ static BOOL run_netbench(int client)
 
        nb_setup(cli);
 
-       slprintf(cname,sizeof(fname), "client%d", client);
+       slprintf(cname,sizeof(cname)-1, "client%d", client);
 
        f = fopen(client_txt, "r");
 
@@ -722,6 +889,7 @@ static BOOL run_netbench(int client)
        }
 
        while (fgets(line, sizeof(line)-1, f)) {
+               char *saveptr;
                line_count++;
 
                line[strlen(line)-1] = 0;
@@ -729,11 +897,11 @@ static BOOL run_netbench(int client)
                /* printf("[%d] %s\n", line_count, line); */
 
                all_string_sub(line,"client1", cname, sizeof(line));
-               
+
                /* parse the command parameters */
-               params[0] = strtok(line," ");
+               params[0] = strtok_r(line, " ", &saveptr);
                i = 0;
-               while (params[i]) params[++i] = strtok(NULL," ");
+               while (params[i]) params[++i] = strtok_r(NULL, " ", &saveptr);
 
                params[i] = "";
 
@@ -785,16 +953,16 @@ static BOOL run_netbench(int client)
        if (!torture_close_connection(cli)) {
                correct = False;
        }
-       
+
        return correct;
 }
 
 
 /* run a test that simulates an approximate netbench client load */
-static BOOL run_nbench(int dummy)
+static bool run_nbench(int dummy)
 {
        double t;
-       BOOL correct = True;
+       bool correct = True;
 
        nbio_shmem(nprocs);
 
@@ -818,7 +986,7 @@ static BOOL run_nbench(int dummy)
      must not use posix semantics)
   2) support for lock timeouts
  */
-static BOOL run_locktest1(int dummy)
+static bool run_locktest1(int dummy)
 {
        struct cli_state *cli1, *cli2;
        const char *fname = "\\lockt1.lck";
@@ -826,7 +994,7 @@ static BOOL run_locktest1(int dummy)
        time_t t1, t2;
        unsigned lock_timeout;
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
        cli_sockopt(cli1, sockops);
@@ -931,7 +1099,7 @@ static BOOL run_locktest1(int dummy)
   this checks to see if a secondary tconx can use open files from an
   earlier tconx
  */
-static BOOL run_tcon_test(int dummy)
+static bool run_tcon_test(int dummy)
 {
        static struct cli_state *cli;
        const char *fname = "\\tcontest.tmp";
@@ -939,9 +1107,12 @@ static BOOL run_tcon_test(int dummy)
        uint16 cnum1, cnum2, cnum3;
        uint16 vuid1, vuid2;
        char buf[4];
-       BOOL ret = True;
+       bool ret = True;
+       NTSTATUS status;
 
-       if (!torture_open_connection(&cli)) {
+       memset(buf, '\0', sizeof(buf));
+
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
        cli_sockopt(cli, sockops);
@@ -964,10 +1135,11 @@ static BOOL run_tcon_test(int dummy)
                return False;
        }
 
-       if (!cli_send_tconX(cli, share, "?????",
-                           password, strlen(password)+1)) {
+       status = cli_tcon_andx(cli, share, "?????",
+                              password, strlen(password)+1);
+       if (!NT_STATUS_IS_OK(status)) {
                printf("%s refused 2nd tree connect (%s)\n", host,
-                          cli_errstr(cli));
+                      nt_errstr(status));
                cli_shutdown(cli);
                return False;
        }
@@ -1036,21 +1208,23 @@ static BOOL run_tcon_test(int dummy)
 /*
  checks for old style tcon support
  */
-static BOOL run_tcon2_test(int dummy)
+static bool run_tcon2_test(int dummy)
 {
        static struct cli_state *cli;
        uint16 cnum, max_xmit;
        char *service;
        NTSTATUS status;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
        cli_sockopt(cli, sockops);
 
        printf("starting tcon2 test\n");
 
-       asprintf(&service, "\\\\%s\\%s", host, share);
+       if (asprintf(&service, "\\\\%s\\%s", host, share) == -1) {
+               return false;
+       }
 
        status = cli_raw_tcon(cli, service, password, "?????", &max_xmit, &cnum);
 
@@ -1069,19 +1243,19 @@ static BOOL run_tcon2_test(int dummy)
        return True;
 }
 
-static BOOL tcon_devtest(struct cli_state *cli,
+static bool tcon_devtest(struct cli_state *cli,
                         const char *myshare, const char *devtype,
                         const char *return_devtype,
                         NTSTATUS expected_error)
 {
-       BOOL status;
-       BOOL ret;
+       NTSTATUS status;
+       bool ret;
 
-       status = cli_send_tconX(cli, myshare, devtype,
-                               password, strlen(password)+1);
+       status = cli_tcon_andx(cli, myshare, devtype,
+                              password, strlen(password)+1);
 
        if (NT_STATUS_IS_OK(expected_error)) {
-               if (status) {
+               if (NT_STATUS_IS_OK(status)) {
                        if (strcmp(cli->dev, return_devtype) == 0) {
                                ret = True;
                        } else { 
@@ -1099,7 +1273,7 @@ static BOOL tcon_devtest(struct cli_state *cli,
                }
                cli_tdis(cli);
        } else {
-               if (status) {
+               if (NT_STATUS_IS_OK(status)) {
                        printf("tconx to share %s with type %s "
                               "should have failed but succeeded\n",
                               myshare, devtype);
@@ -1120,13 +1294,13 @@ static BOOL tcon_devtest(struct cli_state *cli,
 /*
  checks for correct tconX support
  */
-static BOOL run_tcon_devtype_test(int dummy)
+static bool run_tcon_devtype_test(int dummy)
 {
        static struct cli_state *cli1 = NULL;
-       BOOL retry;
+       bool retry;
        int flags = 0;
        NTSTATUS status;
-       BOOL ret = True;
+       bool ret = True;
 
        status = cli_full_connection(&cli1, myname,
                                     host, NULL, port_to_use,
@@ -1150,7 +1324,7 @@ static BOOL run_tcon_devtype_test(int dummy)
 
        if (!tcon_devtest(cli1, "IPC$", "IPC", "IPC", NT_STATUS_OK))
                ret = False;
-                       
+
        if (!tcon_devtest(cli1, "IPC$", "FOOBA", NULL, NT_STATUS_BAD_DEVICE_TYPE))
                ret = False;
 
@@ -1165,7 +1339,7 @@ static BOOL run_tcon_devtype_test(int dummy)
 
        if (!tcon_devtest(cli1, share, "IPC", NULL, NT_STATUS_BAD_DEVICE_TYPE))
                ret = False;
-                       
+
        if (!tcon_devtest(cli1, share, "FOOBA", NULL, NT_STATUS_BAD_DEVICE_TYPE))
                ret = False;
 
@@ -1189,14 +1363,14 @@ static BOOL run_tcon_devtype_test(int dummy)
 
   3) the server denies unlock requests by an incorrect client PID
 */
-static BOOL run_locktest2(int dummy)
+static bool run_locktest2(int dummy)
 {
        static struct cli_state *cli;
        const char *fname = "\\lockt2.lck";
        int fnum1, fnum2, fnum3;
-       BOOL correct = True;
+       bool correct = True;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -1325,17 +1499,17 @@ static BOOL run_locktest2(int dummy)
 
   1) the server supports the full offset range in lock requests
 */
-static BOOL run_locktest3(int dummy)
+static bool run_locktest3(int dummy)
 {
        static struct cli_state *cli1, *cli2;
        const char *fname = "\\lockt3.lck";
        int fnum1, fnum2, i;
        uint32 offset;
-       BOOL correct = True;
+       bool correct = True;
 
 #define NEXT_OFFSET offset += (~(uint32)0) / torture_numops
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
        cli_sockopt(cli1, sockops);
@@ -1433,7 +1607,7 @@ static BOOL run_locktest3(int dummy)
        if (!torture_close_connection(cli1)) {
                correct = False;
        }
-       
+
        if (!torture_close_connection(cli2)) {
                correct = False;
        }
@@ -1450,16 +1624,16 @@ static BOOL run_locktest3(int dummy)
 /*
   looks at overlapping locks
 */
-static BOOL run_locktest4(int dummy)
+static bool run_locktest4(int dummy)
 {
        static struct cli_state *cli1, *cli2;
        const char *fname = "\\lockt4.lck";
        int fnum1, fnum2, f;
-       BOOL ret;
+       bool ret;
        char buf[1000];
-       BOOL correct = True;
+       bool correct = True;
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
 
@@ -1485,7 +1659,7 @@ static BOOL run_locktest4(int dummy)
              cli_lock(cli1, fnum1, 2, 4, 0, WRITE_LOCK);
        EXPECTED(ret, False);
        printf("the same process %s set overlapping write locks\n", ret?"can":"cannot");
-           
+
        ret = cli_lock(cli1, fnum1, 10, 4, 0, READ_LOCK) &&
              cli_lock(cli1, fnum1, 12, 4, 0, READ_LOCK);
        EXPECTED(ret, True);
@@ -1495,17 +1669,17 @@ static BOOL run_locktest4(int dummy)
              cli_lock(cli2, fnum2, 22, 4, 0, WRITE_LOCK);
        EXPECTED(ret, False);
        printf("a different connection %s set overlapping write locks\n", ret?"can":"cannot");
-           
+
        ret = cli_lock(cli1, fnum1, 30, 4, 0, READ_LOCK) &&
              cli_lock(cli2, fnum2, 32, 4, 0, READ_LOCK);
        EXPECTED(ret, True);
        printf("a different connection %s set overlapping read locks\n", ret?"can":"cannot");
-       
+
        ret = (cli_setpid(cli1, 1), cli_lock(cli1, fnum1, 40, 4, 0, WRITE_LOCK)) &&
              (cli_setpid(cli1, 2), cli_lock(cli1, fnum1, 42, 4, 0, WRITE_LOCK));
        EXPECTED(ret, False);
        printf("a different pid %s set overlapping write locks\n", ret?"can":"cannot");
-           
+
        ret = (cli_setpid(cli1, 1), cli_lock(cli1, fnum1, 50, 4, 0, READ_LOCK)) &&
              (cli_setpid(cli1, 2), cli_lock(cli1, fnum1, 52, 4, 0, READ_LOCK));
        EXPECTED(ret, True);
@@ -1621,16 +1795,16 @@ static BOOL run_locktest4(int dummy)
 /*
   looks at lock upgrade/downgrade.
 */
-static BOOL run_locktest5(int dummy)
+static bool run_locktest5(int dummy)
 {
        static struct cli_state *cli1, *cli2;
        const char *fname = "\\lockt5.lck";
        int fnum1, fnum2, fnum3;
-       BOOL ret;
+       bool ret;
        char buf[1000];
-       BOOL correct = True;
+       bool correct = True;
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
 
@@ -1738,14 +1912,14 @@ static BOOL run_locktest5(int dummy)
        }
 
        printf("finished locktest5\n");
-       
+
        return correct;
 }
 
 /*
   tries the unusual lockingX locktype bits
 */
-static BOOL run_locktest6(int dummy)
+static bool run_locktest6(int dummy)
 {
        static struct cli_state *cli;
        const char *fname[1] = { "\\lock6.txt" };
@@ -1753,7 +1927,7 @@ static BOOL run_locktest6(int dummy)
        int fnum;
        NTSTATUS status;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -1785,15 +1959,15 @@ static BOOL run_locktest6(int dummy)
        return True;
 }
 
-static BOOL run_locktest7(int dummy)
+static bool run_locktest7(int dummy)
 {
        struct cli_state *cli1;
        const char *fname = "\\lockt7.lck";
        int fnum1;
        char buf[200];
-       BOOL correct = False;
+       bool correct = False;
 
-       if (!torture_open_connection(&cli1)) {
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
 
@@ -1922,14 +2096,14 @@ fail:
 test whether fnums and tids open on one VC are available on another (a major
 security hole)
 */
-static BOOL run_fdpasstest(int dummy)
+static bool run_fdpasstest(int dummy)
 {
        struct cli_state *cli1, *cli2;
        const char *fname = "\\fdpass.tst";
        int fnum1;
-       pstring buf;
+       char buf[1024];
 
-       if (!torture_open_connection(&cli1) || !torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli1, 0) || !torture_open_connection(&cli2, 1)) {
                return False;
        }
        cli_sockopt(cli1, sockops);
@@ -1970,7 +2144,7 @@ static BOOL run_fdpasstest(int dummy)
        return True;
 }
 
-static BOOL run_fdsesstest(int dummy)
+static bool run_fdsesstest(int dummy)
 {
        struct cli_state *cli;
        uint16 new_vuid;
@@ -1981,10 +2155,10 @@ static BOOL run_fdsesstest(int dummy)
        const char *fname1 = "\\fdsess1.tst";
        int fnum1;
        int fnum2;
-       pstring buf;
-       BOOL ret = True;
+       char buf[1024];
+       bool ret = True;
 
-       if (!torture_open_connection(&cli))
+       if (!torture_open_connection(&cli, 0))
                return False;
        cli_sockopt(cli, sockops);
 
@@ -1992,7 +2166,7 @@ static BOOL run_fdsesstest(int dummy)
                return False;
 
        saved_cnum = cli->cnum;
-       if (!cli_send_tconX(cli, share, "?????", "", 1))
+       if (!NT_STATUS_IS_OK(cli_tcon_andx(cli, share, "?????", "", 1)))
                return False;
        new_cnum = cli->cnum;
        cli->cnum = saved_cnum;
@@ -2059,14 +2233,14 @@ static BOOL run_fdsesstest(int dummy)
 
   1) the server does not allow an unlink on a file that is open
 */
-static BOOL run_unlinktest(int dummy)
+static bool run_unlinktest(int dummy)
 {
        struct cli_state *cli;
        const char *fname = "\\unlink.tst";
        int fnum;
-       BOOL correct = True;
+       bool correct = True;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -2100,7 +2274,7 @@ static BOOL run_unlinktest(int dummy)
        }
 
        printf("unlink test finished\n");
-       
+
        return correct;
 }
 
@@ -2108,14 +2282,14 @@ static BOOL run_unlinktest(int dummy)
 /*
 test how many open files this server supports on the one socket
 */
-static BOOL run_maxfidtest(int dummy)
+static bool run_maxfidtest(int dummy)
 {
        struct cli_state *cli;
-       const char *template = "\\maxfid.%d.%d";
+       const char *ftemplate = "\\maxfid.%d.%d";
        fstring fname;
        int fnums[0x11000], i;
        int retries=4;
-       BOOL correct = True;
+       bool correct = True;
 
        cli = current_cli;
 
@@ -2127,7 +2301,7 @@ static BOOL run_maxfidtest(int dummy)
        cli_sockopt(cli, sockops);
 
        for (i=0; i<0x11000; i++) {
-               slprintf(fname,sizeof(fname)-1,template, i,(int)getpid());
+               slprintf(fname,sizeof(fname)-1,ftemplate, i,(int)getpid());
                if ((fnums[i] = cli_open(cli, fname, 
                                        O_RDWR|O_CREAT|O_TRUNC, DENY_NONE)) ==
                    -1) {
@@ -2143,7 +2317,7 @@ static BOOL run_maxfidtest(int dummy)
 
        printf("cleaning up\n");
        for (;i>=0;i--) {
-               slprintf(fname,sizeof(fname)-1,template, i,(int)getpid());
+               slprintf(fname,sizeof(fname)-1,ftemplate, i,(int)getpid());
                cli_close(cli, fnums[i]);
                if (!cli_unlink(cli, fname)) {
                        printf("unlink of %s failed (%s)\n", 
@@ -2171,23 +2345,23 @@ static void rand_buf(char *buf, int len)
 }
 
 /* send smb negprot commands, not reading the response */
-static BOOL run_negprot_nowait(int dummy)
+static bool run_negprot_nowait(int dummy)
 {
        int i;
-       static struct cli_state cli;
-       BOOL correct = True;
+       static struct cli_state *cli;
+       bool correct = True;
 
        printf("starting negprot nowait test\n");
 
-       if (!open_nbt_connection(&cli)) {
+       if (!(cli = open_nbt_connection())) {
                return False;
        }
 
        for (i=0;i<50000;i++) {
-               cli_negprot_send(&cli);
+               cli_negprot_sendsync(cli);
        }
 
-       if (!torture_close_connection(&cli)) {
+       if (!torture_close_connection(cli)) {
                correct = False;
        }
 
@@ -2198,20 +2372,20 @@ static BOOL run_negprot_nowait(int dummy)
 
 
 /* send random IPC commands */
-static BOOL run_randomipc(int dummy)
+static bool run_randomipc(int dummy)
 {
        char *rparam = NULL;
        char *rdata = NULL;
-       int rdrcnt,rprcnt;
-       pstring param;
+       unsigned int rdrcnt,rprcnt;
+       char param[1024];
        int api, param_len, i;
        struct cli_state *cli;
-       BOOL correct = True;
+       bool correct = True;
        int count = 50000;
 
        printf("starting random ipc test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -2220,7 +2394,7 @@ static BOOL run_randomipc(int dummy)
                param_len = (sys_random() % 64);
 
                rand_buf(param, param_len);
-  
+
                SSVAL(param,0,api); 
 
                cli_api(cli, 
@@ -2257,14 +2431,14 @@ static void browse_callback(const char *sname, uint32 stype,
   This test checks the browse list code
 
 */
-static BOOL run_browsetest(int dummy)
+static bool run_browsetest(int dummy)
 {
        static struct cli_state *cli;
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting browse test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -2292,17 +2466,17 @@ static BOOL run_browsetest(int dummy)
 /*
   This checks how the getatr calls works
 */
-static BOOL run_attrtest(int dummy)
+static bool run_attrtest(int dummy)
 {
        struct cli_state *cli;
        int fnum;
        time_t t, t2;
        const char *fname = "\\attrib123456789.tst";
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting attrib test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -2356,34 +2530,35 @@ static BOOL run_attrtest(int dummy)
 /*
   This checks a couple of trans2 calls
 */
-static BOOL run_trans2test(int dummy)
+static bool run_trans2test(int dummy)
 {
        struct cli_state *cli;
        int fnum;
        SMB_OFF_T size;
-       time_t c_time, a_time, m_time, w_time, m_time2;
+       time_t c_time, a_time, m_time;
+       struct timespec c_time_ts, a_time_ts, m_time_ts, w_time_ts, m_time2_ts;
        const char *fname = "\\trans2.tst";
        const char *dname = "\\trans2";
        const char *fname2 = "\\trans2\\trans2.tst";
-       pstring pname;
-       BOOL correct = True;
+       char pname[1024];
+       bool correct = True;
 
        printf("starting trans2 test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
        cli_unlink(cli, fname);
        fnum = cli_open(cli, fname, 
                        O_RDWR | O_CREAT | O_TRUNC, DENY_NONE);
-       if (!cli_qfileinfo(cli, fnum, NULL, &size, &c_time, &a_time, &m_time,
-                          NULL, NULL)) {
+       if (!cli_qfileinfo(cli, fnum, NULL, &size, &c_time_ts, &a_time_ts, &w_time_ts,
+                          &m_time_ts, NULL)) {
                printf("ERROR: qfileinfo failed (%s)\n", cli_errstr(cli));
                correct = False;
        }
 
-       if (!cli_qfilename(cli, fnum, pname)) {
+       if (!cli_qfilename(cli, fnum, pname, sizeof(pname))) {
                printf("ERROR: qfilename failed (%s)\n", cli_errstr(cli));
                correct = False;
        }
@@ -2433,13 +2608,13 @@ static BOOL run_trans2test(int dummy)
        fnum = cli_open(cli, fname, 
                        O_RDWR | O_CREAT | O_TRUNC, DENY_NONE);
        cli_close(cli, fnum);
-       if (!cli_qpathinfo2(cli, fname, &c_time, &a_time, &m_time
-                           &w_time, &size, NULL, NULL)) {
+       if (!cli_qpathinfo2(cli, fname, &c_time_ts, &a_time_ts, &w_time_ts
+                           &m_time_ts, &size, NULL, NULL)) {
                printf("ERROR: qpathinfo2 failed (%s)\n", cli_errstr(cli));
                correct = False;
        } else {
-               if (w_time < 60*60*24*2) {
-                       printf("write time=%s", ctime(&w_time));
+               if (w_time_ts.tv_sec < 60*60*24*2) {
+                       printf("write time=%s", ctime(&w_time_ts.tv_sec));
                        printf("This system appears to set a initial 0 write time\n");
                        correct = False;
                }
@@ -2450,13 +2625,13 @@ static BOOL run_trans2test(int dummy)
 
        /* check if the server updates the directory modification time
            when creating a new file */
-       if (!cli_mkdir(cli, dname)) {
+       if (!NT_STATUS_IS_OK(cli_mkdir(cli, dname))) {
                printf("ERROR: mkdir failed (%s)\n", cli_errstr(cli));
                correct = False;
        }
        sleep(3);
-       if (!cli_qpathinfo2(cli, "\\trans2\\", &c_time, &a_time, &m_time
-                           &w_time, &size, NULL, NULL)) {
+       if (!cli_qpathinfo2(cli, "\\trans2\\", &c_time_ts, &a_time_ts, &w_time_ts
+                           &m_time_ts, &size, NULL, NULL)) {
                printf("ERROR: qpathinfo2 failed (%s)\n", cli_errstr(cli));
                correct = False;
        }
@@ -2465,12 +2640,13 @@ static BOOL run_trans2test(int dummy)
                        O_RDWR | O_CREAT | O_TRUNC, DENY_NONE);
        cli_write(cli, fnum,  0, (char *)&fnum, 0, sizeof(fnum));
        cli_close(cli, fnum);
-       if (!cli_qpathinfo2(cli, "\\trans2\\", &c_time, &a_time, &m_time2
-                           &w_time, &size, NULL, NULL)) {
+       if (!cli_qpathinfo2(cli, "\\trans2\\", &c_time_ts, &a_time_ts, &w_time_ts
+                           &m_time2_ts, &size, NULL, NULL)) {
                printf("ERROR: qpathinfo2 failed (%s)\n", cli_errstr(cli));
                correct = False;
        } else {
-               if (m_time2 == m_time) {
+               if (memcmp(&m_time_ts, &m_time2_ts, sizeof(struct timespec))
+                   == 0) {
                        printf("This system does not update directory modification times\n");
                        correct = False;
                }
@@ -2491,35 +2667,35 @@ static BOOL run_trans2test(int dummy)
   This checks new W2K calls.
 */
 
-static BOOL new_trans(struct cli_state *pcli, int fnum, int level)
+static bool new_trans(struct cli_state *pcli, int fnum, int level)
 {
        char *buf = NULL;
        uint32 len;
-       BOOL correct = True;
+       bool correct = True;
 
        if (!cli_qfileinfo_test(pcli, fnum, level, &buf, &len)) {
                printf("ERROR: qfileinfo (%d) failed (%s)\n", level, cli_errstr(pcli));
                correct = False;
        } else {
                printf("qfileinfo: level %d, len = %u\n", level, len);
-               dump_data(0, buf, len);
+               dump_data(0, (uint8 *)buf, len);
                printf("\n");
        }
        SAFE_FREE(buf);
        return correct;
 }
 
-static BOOL run_w2ktest(int dummy)
+static bool run_w2ktest(int dummy)
 {
        struct cli_state *cli;
        int fnum;
        const char *fname = "\\w2ktest\\w2k.tst";
        int level;
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting w2k test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -2537,7 +2713,7 @@ static BOOL run_w2ktest(int dummy)
        }
 
        printf("w2k test finished\n");
-       
+
        return correct;
 }
 
@@ -2545,16 +2721,16 @@ static BOOL run_w2ktest(int dummy)
 /*
   this is a harness for some oplock tests
  */
-static BOOL run_oplock1(int dummy)
+static bool run_oplock1(int dummy)
 {
        struct cli_state *cli1;
        const char *fname = "\\lockt1.lck";
        int fnum1;
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting oplock test 1\n");
 
-       if (!torture_open_connection(&cli1)) {
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
 
@@ -2594,17 +2770,17 @@ static BOOL run_oplock1(int dummy)
        return correct;
 }
 
-static BOOL run_oplock2(int dummy)
+static bool run_oplock2(int dummy)
 {
        struct cli_state *cli1, *cli2;
        const char *fname = "\\lockt2.lck";
        int fnum1, fnum2;
        int saved_use_oplocks = use_oplocks;
        char buf[4];
-       BOOL correct = True;
-       volatile BOOL *shared_correct;
+       bool correct = True;
+       volatile bool *shared_correct;
 
-       shared_correct = (volatile BOOL *)shm_setup(sizeof(BOOL));
+       shared_correct = (volatile bool *)shm_setup(sizeof(bool));
        *shared_correct = True;
 
        use_level_II_oplocks = True;
@@ -2612,7 +2788,7 @@ static BOOL run_oplock2(int dummy)
 
        printf("starting oplock test 2\n");
 
-       if (!torture_open_connection(&cli1)) {
+       if (!torture_open_connection(&cli1, 0)) {
                use_level_II_oplocks = False;
                use_oplocks = saved_use_oplocks;
                return False;
@@ -2621,7 +2797,7 @@ static BOOL run_oplock2(int dummy)
        cli1->use_oplocks = True;
        cli1->use_level_II_oplocks = True;
 
-       if (!torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli2, 1)) {
                use_level_II_oplocks = False;
                use_oplocks = saved_use_oplocks;
                return False;
@@ -2730,23 +2906,23 @@ static BOOL run_oplock2(int dummy)
 }
 
 /* handler for oplock 3 tests */
-static BOOL oplock3_handler(struct cli_state *cli, int fnum, unsigned char level)
+static bool oplock3_handler(struct cli_state *cli, int fnum, unsigned char level)
 {
        printf("got oplock break fnum=%d level=%d\n",
               fnum, level);
        return cli_oplock_ack(cli, fnum, level);
 }
 
-static BOOL run_oplock3(int dummy)
+static bool run_oplock3(int dummy)
 {
        struct cli_state *cli;
        const char *fname = "\\oplockt3.dat";
        int fnum;
        char buf[4] = "abcd";
-       BOOL correct = True;
-       volatile BOOL *shared_correct;
+       bool correct = True;
+       volatile bool *shared_correct;
 
-       shared_correct = (volatile BOOL *)shm_setup(sizeof(BOOL));
+       shared_correct = (volatile bool *)shm_setup(sizeof(bool));
        *shared_correct = True;
 
        printf("starting oplock test 3\n");
@@ -2755,7 +2931,7 @@ static BOOL run_oplock3(int dummy)
                /* Child code */
                use_oplocks = True;
                use_level_II_oplocks = True;
-               if (!torture_open_connection(&cli)) {
+               if (!torture_open_connection(&cli, 0)) {
                        *shared_correct = False;
                        exit(0);
                } 
@@ -2769,7 +2945,7 @@ static BOOL run_oplock3(int dummy)
        /* parent code */
        use_oplocks = True;
        use_level_II_oplocks = True;
-       if (!torture_open_connection(&cli)) { 
+       if (!torture_open_connection(&cli, 1)) { /* other is forked */
                return False;
        }
        cli_oplock_handler(cli, oplock3_handler);
@@ -2791,32 +2967,32 @@ static BOOL run_oplock3(int dummy)
 /*
   Test delete on close semantics.
  */
-static BOOL run_deletetest(int dummy)
+static bool run_deletetest(int dummy)
 {
        struct cli_state *cli1 = NULL;
        struct cli_state *cli2 = NULL;
        const char *fname = "\\delete.file";
        int fnum1 = -1;
        int fnum2 = -1;
-       BOOL correct = True;
-       
+       bool correct = True;
+
        printf("starting delete test\n");
-       
-       if (!torture_open_connection(&cli1)) {
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
-       
+
        cli_sockopt(cli1, sockops);
 
        /* Test 1 - this should delete the file on close. */
-       
+
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS, FILE_ATTRIBUTE_NORMAL,
                                   0, FILE_OVERWRITE_IF, 
                                   FILE_DELETE_ON_CLOSE, 0);
-       
+
        if (fnum1 == -1) {
                printf("[1] open of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
@@ -2846,36 +3022,36 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        printf("first delete on close test succeeded.\n");
-       
+
        /* Test 2 - this should delete the file on close. */
-       
+
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, GENERIC_ALL_ACCESS,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE, 
                                   FILE_OVERWRITE_IF, 0, 0);
-       
+
        if (fnum1 == -1) {
                printf("[2] open of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_nt_delete_on_close(cli1, fnum1, True)) {
                printf("[2] setting delete_on_close failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("[2] close failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        fnum1 = cli_open(cli1, fname, O_RDONLY, DENY_NONE);
        if (fnum1 != -1) {
                printf("[2] open of %s succeeded should have been deleted on close !\n", fname);
@@ -2887,7 +3063,7 @@ static BOOL run_deletetest(int dummy)
                cli_unlink(cli1, fname);
        } else
                printf("second delete on close test succeeded.\n");
-       
+
        /* Test 3 - ... */
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
@@ -2929,19 +3105,19 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("[3] close 1 failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_close(cli1, fnum2)) {
                printf("[3] close 2 failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        /* This should fail - file should no longer be there. */
 
        fnum1 = cli_open(cli1, fname, O_RDONLY, DENY_NONE);
@@ -2962,7 +3138,7 @@ static BOOL run_deletetest(int dummy)
 
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
                        FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE, FILE_OVERWRITE_IF, 0, 0);
-                                                               
+
        if (fnum1 == -1) {
                printf("[4] open of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
@@ -2977,19 +3153,19 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_close(cli1, fnum2)) {
                printf("[4] close - 1 failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_nt_delete_on_close(cli1, fnum1, True)) {
                printf("[4] setting delete_on_close failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        /* This should fail - no more opens once delete on close set. */
        fnum2 = cli_nt_create_full(cli1, fname, 0, GENERIC_READ_ACCESS,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
@@ -3000,17 +3176,17 @@ static BOOL run_deletetest(int dummy)
                goto fail;
        } else
                printf("fourth delete on close test succeeded.\n");
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("[4] close - 2 failed (%s)\n", cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        /* Test 5 ... */
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        fnum1 = cli_open(cli1, fname, O_RDWR|O_CREAT, DENY_NONE);
        if (fnum1 == -1) {
                printf("[5] open of %s failed (%s)\n", fname, cli_errstr(cli1));
@@ -3031,25 +3207,25 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        printf("fifth delete on close test succeeded.\n");
-       
+
        /* Test 6 ... */
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
                                   FILE_OVERWRITE_IF, 0, 0);
-       
+
        if (fnum1 == -1) {
                printf("[6] open of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
                goto fail;
        }
-       
+
        /* This should fail - only allowed on NT opens with DELETE access. */
-       
+
        if (cli_nt_delete_on_close(cli1, fnum1, True)) {
                printf("[6] setting delete_on_close on file with no delete access succeeded - should fail !\n");
                correct = False;
@@ -3063,14 +3239,14 @@ static BOOL run_deletetest(int dummy)
        }
 
        printf("sixth delete on close test succeeded.\n");
-       
+
        /* Test 7 ... */
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
                                   FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF, 0, 0);
-                                                               
+
        if (fnum1 == -1) {
                printf("[7] open of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
@@ -3082,7 +3258,7 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_nt_delete_on_close(cli1, fnum1, False)) {
                printf("[7] unsetting delete_on_close on file failed !\n");
                correct = False;
@@ -3094,9 +3270,9 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        /* This next open should succeed - we reset the flag. */
-       
+
        fnum1 = cli_open(cli1, fname, O_RDONLY, DENY_NONE);
        if (fnum1 == -1) {
                printf("[5] open of %s failed (%s)\n", fname, cli_errstr(cli1));
@@ -3111,23 +3287,23 @@ static BOOL run_deletetest(int dummy)
        }
 
        printf("seventh delete on close test succeeded.\n");
-       
+
        /* Test 7 ... */
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
-       if (!torture_open_connection(&cli2)) {
+
+       if (!torture_open_connection(&cli2, 1)) {
                printf("[8] failed to open second connection.\n");
                correct = False;
                goto fail;
        }
 
        cli_sockopt(cli1, sockops);
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
                                   FILE_OVERWRITE_IF, 0, 0);
-       
+
        if (fnum1 == -1) {
                printf("[8] open 1 of %s failed (%s)\n", fname, cli_errstr(cli1));
                correct = False;
@@ -3137,7 +3313,7 @@ static BOOL run_deletetest(int dummy)
        fnum2 = cli_nt_create_full(cli2, fname, 0, FILE_READ_DATA|FILE_WRITE_DATA|DELETE_ACCESS,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
                                   FILE_OPEN, 0, 0);
-       
+
        if (fnum2 == -1) {
                printf("[8] open 2 of %s failed (%s)\n", fname, cli_errstr(cli2));
                correct = False;
@@ -3149,7 +3325,7 @@ static BOOL run_deletetest(int dummy)
                correct = False;
                goto fail;
        }
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("[8] close - 1 failed (%s)\n", cli_errstr(cli1));
                correct = False;
@@ -3174,7 +3350,7 @@ static BOOL run_deletetest(int dummy)
        /* This should fail - we need to set DELETE_ACCESS. */
        fnum1 = cli_nt_create_full(cli1, fname, 0,FILE_READ_DATA|FILE_WRITE_DATA,
                                   FILE_ATTRIBUTE_NORMAL, FILE_SHARE_NONE, FILE_OVERWRITE_IF, FILE_DELETE_ON_CLOSE, 0);
-       
+
        if (fnum1 != -1) {
                printf("[9] open of %s succeeded should have failed!\n", fname);
                correct = False;
@@ -3232,7 +3408,7 @@ static BOOL run_deletetest(int dummy)
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_ATTRIBUTES|DELETE_ACCESS,
                                   0, FILE_SHARE_READ|FILE_SHARE_WRITE|FILE_SHARE_DELETE,
                                   FILE_OVERWRITE_IF, 0, 0);
-       
+
        if (fnum1 != -1) {
                printf("[11] open of %s succeeded should have been denied with ACCESS_DENIED!\n", fname);
                cli_close(cli1, fnum1);
@@ -3248,14 +3424,14 @@ static BOOL run_deletetest(int dummy)
                        printf("eleventh delete on close test succeeded.\n");
                }
        }
-       
+
        printf("finished delete test\n");
 
   fail:
        /* FIXME: This will crash if we aborted before cli2 got
         * intialized, because these functions don't handle
         * uninitialized connections. */
-               
+
        if (fnum1 != -1) cli_close(cli1, fnum1);
        if (fnum2 != -1) cli_close(cli1, fnum2);
        cli_setatr(cli1, fname, 0, 0);
@@ -3274,19 +3450,19 @@ static BOOL run_deletetest(int dummy)
 /*
   print out server properties
  */
-static BOOL run_properties(int dummy)
+static bool run_properties(int dummy)
 {
        static struct cli_state *cli;
-       BOOL correct = True;
-       
+       bool correct = True;
+
        printf("starting properties test\n");
-       
+
        ZERO_STRUCT(cli);
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
-       
+
        cli_sockopt(cli, sockops);
 
        d_printf("Capabilities 0x%08x\n", cli->capabilities);
@@ -3322,19 +3498,19 @@ static BOOL run_properties(int dummy)
 /*
   Test ntcreate calls made by xcopy
  */
-static BOOL run_xcopy(int dummy)
+static bool run_xcopy(int dummy)
 {
        static struct cli_state *cli1;
        const char *fname = "\\test.txt";
-       BOOL correct = True;
+       bool correct = True;
        int fnum1, fnum2;
 
        printf("starting xcopy test\n");
-       
-       if (!torture_open_connection(&cli1)) {
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0,
                                   FIRST_DESIRED_ACCESS, FILE_ATTRIBUTE_ARCHIVE,
                                   FILE_SHARE_NONE, FILE_OVERWRITE_IF, 
@@ -3353,31 +3529,31 @@ static BOOL run_xcopy(int dummy)
                printf("second open failed - %s\n", cli_errstr(cli1));
                return False;
        }
-       
+
        if (!torture_close_connection(cli1)) {
                correct = False;
        }
-       
+
        return correct;
 }
 
 /*
   Test rename on files open with share delete and no share delete.
  */
-static BOOL run_rename(int dummy)
+static bool run_rename(int dummy)
 {
        static struct cli_state *cli1;
        const char *fname = "\\test.txt";
        const char *fname1 = "\\test1.txt";
-       BOOL correct = True;
+       bool correct = True;
        int fnum1;
 
        printf("starting rename test\n");
-       
-       if (!torture_open_connection(&cli1)) {
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
-       
+
        cli_unlink(cli1, fname);
        cli_unlink(cli1, fname1);
        fnum1 = cli_nt_create_full(cli1, fname, 0, GENERIC_READ_ACCESS, FILE_ATTRIBUTE_NORMAL,
@@ -3453,7 +3629,7 @@ static BOOL run_rename(int dummy)
                printf("[8] setting delete_on_close on file failed !\n");
                return False;
        }
-       
+
        if (!cli_close(cli1, fnum2)) {
                printf("close - 4 failed (%s)\n", cli_errstr(cli1));
                return False;
@@ -3512,7 +3688,8 @@ static BOOL run_rename(int dummy)
        }
 
        if (!cli_rename(cli1, fname, fname1)) {
-               printf("Fifth rename failed (SHARE_READ | SHARE_WRITE | SHARE_DELETE) - this should have failed ! \n");
+               printf("Fifth rename failed (SHARE_READ | SHARE_WRITE | SHARE_DELETE) - this should have succeeded - %s ! \n",
+                       cli_errstr(cli1));
                correct = False;
        } else {
                printf("Fifth rename succeeded (SHARE_READ | SHARE_WRITE | SHARE_DELETE) (this is correct) - %s\n", cli_errstr(cli1));
@@ -3544,15 +3721,15 @@ static BOOL run_rename(int dummy)
 
        cli_unlink(cli1, fname);
        cli_unlink(cli1, fname1);
-        
+
        if (!torture_close_connection(cli1)) {
                correct = False;
        }
-       
+
        return correct;
 }
 
-static BOOL run_pipe_number(int dummy)
+static bool run_pipe_number(int dummy)
 {
        struct cli_state *cli1;
        const char *pipe_name = "\\SPOOLSS";
@@ -3560,7 +3737,7 @@ static BOOL run_pipe_number(int dummy)
        int num_pipes = 0;
 
        printf("starting pipenumber test\n");
-       if (!torture_open_connection(&cli1)) {
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
 
@@ -3574,6 +3751,7 @@ static BOOL run_pipe_number(int dummy)
                        break;
                }
                num_pipes++;
+               printf("\r%6d", num_pipes);
        }
 
        printf("pipe_number test - we can open %d %s pipes.\n", num_pipes, pipe_name );
@@ -3584,7 +3762,7 @@ static BOOL run_pipe_number(int dummy)
 /*
   Test open mode returns on read-only files.
  */
-static BOOL run_opentest(int dummy)
+static bool run_opentest(int dummy)
 {
        static struct cli_state *cli1;
        static struct cli_state *cli2;
@@ -3592,20 +3770,20 @@ static BOOL run_opentest(int dummy)
        int fnum1, fnum2;
        char buf[20];
        SMB_OFF_T fsize;
-       BOOL correct = True;
+       bool correct = True;
        char *tmp_path;
 
        printf("starting open test\n");
-       
-       if (!torture_open_connection(&cli1)) {
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
-       
+
        cli_setatr(cli1, fname, 0, 0);
        cli_unlink(cli1, fname);
-       
+
        cli_sockopt(cli1, sockops);
-       
+
        fnum1 = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE);
        if (fnum1 == -1) {
                printf("open of %s failed (%s)\n", fname, cli_errstr(cli1));
@@ -3616,67 +3794,67 @@ static BOOL run_opentest(int dummy)
                printf("close2 failed (%s)\n", cli_errstr(cli1));
                return False;
        }
-       
+
        if (!cli_setatr(cli1, fname, aRONLY, 0)) {
                printf("cli_setatr failed (%s)\n", cli_errstr(cli1));
                return False;
        }
-       
+
        fnum1 = cli_open(cli1, fname, O_RDONLY, DENY_WRITE);
        if (fnum1 == -1) {
                printf("open of %s failed (%s)\n", fname, cli_errstr(cli1));
                return False;
        }
-       
+
        /* This will fail - but the error should be ERRnoaccess, not ERRbadshare. */
        fnum2 = cli_open(cli1, fname, O_RDWR, DENY_ALL);
-       
+
         if (check_error(__LINE__, cli1, ERRDOS, ERRnoaccess, 
                        NT_STATUS_ACCESS_DENIED)) {
                printf("correct error code ERRDOS/ERRnoaccess returned\n");
        }
-       
+
        printf("finished open test 1\n");
-       
+
        cli_close(cli1, fnum1);
-       
+
        /* Now try not readonly and ensure ERRbadshare is returned. */
-       
+
        cli_setatr(cli1, fname, 0, 0);
-       
+
        fnum1 = cli_open(cli1, fname, O_RDONLY, DENY_WRITE);
        if (fnum1 == -1) {
                printf("open of %s failed (%s)\n", fname, cli_errstr(cli1));
                return False;
        }
-       
+
        /* This will fail - but the error should be ERRshare. */
        fnum2 = cli_open(cli1, fname, O_RDWR, DENY_ALL);
-       
+
        if (check_error(__LINE__, cli1, ERRDOS, ERRbadshare, 
                        NT_STATUS_SHARING_VIOLATION)) {
                printf("correct error code ERRDOS/ERRbadshare returned\n");
        }
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("close2 failed (%s)\n", cli_errstr(cli1));
                return False;
        }
-       
+
        cli_unlink(cli1, fname);
-       
+
        printf("finished open test 2\n");
-       
+
        /* Test truncate open disposition on file opened for read. */
-       
+
        fnum1 = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE);
        if (fnum1 == -1) {
                printf("(3) open (1) of %s failed (%s)\n", fname, cli_errstr(cli1));
                return False;
        }
-       
+
        /* write 20 bytes. */
-       
+
        memset(buf, '\0', 20);
 
        if (cli_write(cli1, fnum1, 0, buf, 0, 20) != 20) {
@@ -3688,26 +3866,26 @@ static BOOL run_opentest(int dummy)
                printf("(3) close1 failed (%s)\n", cli_errstr(cli1));
                return False;
        }
-       
+
        /* Ensure size == 20. */
        if (!cli_getatr(cli1, fname, NULL, &fsize, NULL)) {
                printf("(3) getatr failed (%s)\n", cli_errstr(cli1));
                return False;
        }
-       
+
        if (fsize != 20) {
                printf("(3) file size != 20\n");
                return False;
        }
 
        /* Now test if we can truncate a file opened for readonly. */
-       
+
        fnum1 = cli_open(cli1, fname, O_RDONLY|O_TRUNC, DENY_NONE);
        if (fnum1 == -1) {
                printf("(3) open (2) of %s failed (%s)\n", fname, cli_errstr(cli1));
                return False;
        }
-       
+
        if (!cli_close(cli1, fnum1)) {
                printf("close2 failed (%s)\n", cli_errstr(cli1));
                return False;
@@ -3724,7 +3902,7 @@ static BOOL run_opentest(int dummy)
                return False;
        }
        printf("finished open test 3\n");
-       
+
        cli_unlink(cli1, fname);
 
 
@@ -3741,20 +3919,20 @@ static BOOL run_opentest(int dummy)
        if (!cli_unlink(cli1, tmp_path)) {
                printf("unlink of temp failed (%s)\n", cli_errstr(cli1));
        }
-       
+
        /* Test the non-io opens... */
 
-       if (!torture_open_connection(&cli2)) {
+       if (!torture_open_connection(&cli2, 1)) {
                return False;
        }
-       
+
        cli_setatr(cli2, fname, 0, 0);
        cli_unlink(cli2, fname);
-       
+
        cli_sockopt(cli2, sockops);
 
        printf("TEST #1 testing 2 non-io opens (no delete)\n");
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_ATTRIBUTES, FILE_ATTRIBUTE_NORMAL,
                                   FILE_SHARE_NONE, FILE_OVERWRITE_IF, 0, 0);
 
@@ -3785,7 +3963,7 @@ static BOOL run_opentest(int dummy)
        cli_unlink(cli1, fname);
 
        printf("TEST #2 testing 2 non-io opens (first with delete)\n");
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, DELETE_ACCESS|FILE_READ_ATTRIBUTES, FILE_ATTRIBUTE_NORMAL,
                                   FILE_SHARE_NONE, FILE_OVERWRITE_IF, 0, 0);
 
@@ -3816,7 +3994,7 @@ static BOOL run_opentest(int dummy)
        cli_unlink(cli1, fname);
 
        printf("TEST #3 testing 2 non-io opens (second with delete)\n");
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_ATTRIBUTES, FILE_ATTRIBUTE_NORMAL,
                                   FILE_SHARE_NONE, FILE_OVERWRITE_IF, 0, 0);
 
@@ -3847,7 +4025,7 @@ static BOOL run_opentest(int dummy)
        cli_unlink(cli1, fname);
 
        printf("TEST #4 testing 2 non-io opens (both with delete)\n");
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, DELETE_ACCESS|FILE_READ_ATTRIBUTES, FILE_ATTRIBUTE_NORMAL,
                                   FILE_SHARE_NONE, FILE_OVERWRITE_IF, 0, 0);
 
@@ -3876,7 +4054,7 @@ static BOOL run_opentest(int dummy)
        cli_unlink(cli1, fname);
 
        printf("TEST #5 testing 2 non-io opens (both with delete - both with file share delete)\n");
-       
+
        fnum1 = cli_nt_create_full(cli1, fname, 0, DELETE_ACCESS|FILE_READ_ATTRIBUTES, FILE_ATTRIBUTE_NORMAL,
                                   FILE_SHARE_DELETE, FILE_OVERWRITE_IF, 0, 0);
 
@@ -3906,7 +4084,7 @@ static BOOL run_opentest(int dummy)
        printf("non-io open test #5 passed.\n");
 
        printf("TEST #6 testing 1 non-io open, one io open\n");
-       
+
        cli_unlink(cli1, fname);
 
        fnum1 = cli_nt_create_full(cli1, fname, 0, FILE_READ_DATA, FILE_ATTRIBUTE_NORMAL,
@@ -3974,50 +4152,163 @@ static BOOL run_opentest(int dummy)
        if (!torture_close_connection(cli2)) {
                correct = False;
        }
-       
+
        return correct;
 }
 
-static uint32 open_attrs_table[] = {
-               FILE_ATTRIBUTE_NORMAL,
-               FILE_ATTRIBUTE_ARCHIVE,
-               FILE_ATTRIBUTE_READONLY,
-               FILE_ATTRIBUTE_HIDDEN,
-               FILE_ATTRIBUTE_SYSTEM,
+/*
+  Test POSIX open /mkdir calls.
+ */
+static bool run_simple_posix_open_test(int dummy)
+{
+       static struct cli_state *cli1;
+       const char *fname = "\\posix:file";
+       const char *dname = "\\posix:dir";
+       uint16 major, minor;
+       uint32 caplow, caphigh;
+       int fnum1 = -1;
+       bool correct = false;
 
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY,
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN,
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM,
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
-               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
+       printf("Starting simple POSIX open test\n");
 
-               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
-               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
-               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
-               FILE_ATTRIBUTE_HIDDEN,FILE_ATTRIBUTE_SYSTEM,
-};
+       if (!torture_open_connection(&cli1, 0)) {
+               return false;
+       }
 
-struct trunc_open_results {
-       unsigned int num;
-       uint32 init_attr;
-       uint32 trunc_attr;
-       uint32 result_attr;
-};
+       cli_sockopt(cli1, sockops);
 
-static struct trunc_open_results attr_results[] = {
-       { 0, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
-       { 1, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
-       { 2, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
-       { 16, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
-       { 17, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
-       { 18, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
-       { 51, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
-       { 54, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
-       { 56, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN },
-       { 68, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
-       { 71, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
-       { 73, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM },
+       if (!SERVER_HAS_UNIX_CIFS(cli1)) {
+               printf("Server doesn't support UNIX CIFS extensions.\n");
+               return false;
+       }
+
+       if (!cli_unix_extensions_version(cli1, &major,
+                       &minor, &caplow, &caphigh)) {
+               printf("Server didn't return UNIX CIFS extensions.\n");
+               return false;
+       }
+
+       if (!cli_set_unix_extensions_capabilities(cli1,
+                       major, minor, caplow, caphigh)) {
+               printf("Server doesn't support setting UNIX CIFS extensions.\n");
+               return false;
+        }
+
+       cli_setatr(cli1, fname, 0, 0);
+       cli_posix_unlink(cli1, fname);
+       cli_setatr(cli1, dname, 0, 0);
+       cli_posix_rmdir(cli1, dname);
+
+       /* Create a directory. */
+       if (cli_posix_mkdir(cli1, dname, 0777) == -1) {
+               printf("Server doesn't support setting UNIX CIFS extensions.\n");
+               goto out;
+       }
+
+       fnum1 = cli_posix_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, 0600);
+       if (fnum1 == -1) {
+               printf("POSIX create of %s failed (%s)\n", fname, cli_errstr(cli1));
+               goto out;
+       }
+
+       if (!cli_close(cli1, fnum1)) {
+               printf("close failed (%s)\n", cli_errstr(cli1));
+               goto out;
+       }
+
+       /* Now open the file again for read only. */
+       fnum1 = cli_posix_open(cli1, fname, O_RDONLY, 0);
+       if (fnum1 == -1) {
+               printf("POSIX open of %s failed (%s)\n", fname, cli_errstr(cli1));
+               goto out;
+       }
+
+       /* Now unlink while open. */
+       if (!cli_posix_unlink(cli1, fname)) {
+               printf("POSIX unlink of %s failed (%s)\n", fname, cli_errstr(cli1));
+               goto out;
+       }
+
+       if (!cli_close(cli1, fnum1)) {
+               printf("close(2) failed (%s)\n", cli_errstr(cli1));
+               goto out;
+       }
+
+       /* Ensure the file has gone. */
+       fnum1 = cli_posix_open(cli1, fname, O_RDONLY, 0);
+       if (fnum1 != -1) {
+               printf("POSIX open of %s succeeded, should have been deleted.\n", fname);
+               goto out;
+       }
+
+       if (!cli_posix_rmdir(cli1, dname)) {
+               printf("POSIX rmdir failed (%s)\n", cli_errstr(cli1));
+               goto out;
+       }
+
+       printf("Simple POSIX open test passed\n");
+       correct = true;
+
+  out:
+
+       if (fnum1 != -1) {
+               cli_close(cli1, fnum1);
+               fnum1 = -1;
+       }
+
+       cli_setatr(cli1, fname, 0, 0);
+       cli_posix_unlink(cli1, fname);
+       cli_setatr(cli1, dname, 0, 0);
+       cli_posix_rmdir(cli1, dname);
+
+       if (!torture_close_connection(cli1)) {
+               correct = false;
+       }
+
+       return correct;
+}
+
+
+static uint32 open_attrs_table[] = {
+               FILE_ATTRIBUTE_NORMAL,
+               FILE_ATTRIBUTE_ARCHIVE,
+               FILE_ATTRIBUTE_READONLY,
+               FILE_ATTRIBUTE_HIDDEN,
+               FILE_ATTRIBUTE_SYSTEM,
+
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY,
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN,
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM,
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
+               FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
+
+               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN,
+               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM,
+               FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN|FILE_ATTRIBUTE_SYSTEM,
+               FILE_ATTRIBUTE_HIDDEN,FILE_ATTRIBUTE_SYSTEM,
+};
+
+struct trunc_open_results {
+       unsigned int num;
+       uint32 init_attr;
+       uint32 trunc_attr;
+       uint32 result_attr;
+};
+
+static struct trunc_open_results attr_results[] = {
+       { 0, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
+       { 1, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
+       { 2, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
+       { 16, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_NORMAL, FILE_ATTRIBUTE_ARCHIVE },
+       { 17, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_ARCHIVE },
+       { 18, FILE_ATTRIBUTE_ARCHIVE, FILE_ATTRIBUTE_READONLY, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY },
+       { 51, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
+       { 54, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
+       { 56, FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_HIDDEN },
+       { 68, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
+       { 71, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_SYSTEM },
+       { 73, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM },
        { 99, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_HIDDEN,FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
        { 102, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_HIDDEN },
        { 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 },
@@ -4034,21 +4325,21 @@ static struct trunc_open_results attr_results[] = {
        { 249, FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM, FILE_ATTRIBUTE_ARCHIVE|FILE_ATTRIBUTE_READONLY|FILE_ATTRIBUTE_SYSTEM }
 };
 
-static BOOL run_openattrtest(int dummy)
+static bool run_openattrtest(int dummy)
 {
        static struct cli_state *cli1;
        const char *fname = "\\openattr.file";
        int fnum1;
-       BOOL correct = True;
+       bool correct = True;
        uint16 attr;
        unsigned int i, j, k, l;
 
        printf("starting open attr test\n");
-       
-       if (!torture_open_connection(&cli1)) {
+
+       if (!torture_open_connection(&cli1, 0)) {
                return False;
        }
-       
+
        cli_sockopt(cli1, sockops);
 
        for (k = 0, i = 0; i < sizeof(open_attrs_table)/sizeof(uint32); i++) {
@@ -4141,23 +4432,23 @@ static BOOL run_openattrtest(int dummy)
 
 static void list_fn(const char *mnt, file_info *finfo, const char *name, void *state)
 {
-       
+
 }
 
 /*
   test directory listing speed
  */
-static BOOL run_dirtest(int dummy)
+static bool run_dirtest(int dummy)
 {
        int i;
        static struct cli_state *cli;
        int fnum;
        double t1;
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting directory test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -4209,7 +4500,7 @@ static void del_fn(const char *mnt, file_info *finfo, const char *mask, void *st
                return;
 
        if (finfo->mode & aDIR) {
-               if (!cli_rmdir(pcli, fname))
+               if (!NT_STATUS_IS_OK(cli_rmdir(pcli, fname)))
                        printf("del_fn: failed to rmdir %s\n,", fname );
        } else {
                if (!cli_unlink(pcli, fname))
@@ -4221,7 +4512,7 @@ static void del_fn(const char *mnt, file_info *finfo, const char *mask, void *st
 /*
   sees what IOCTLs are supported
  */
-BOOL torture_ioctl_test(int dummy)
+bool torture_ioctl_test(int dummy)
 {
        static struct cli_state *cli;
        uint16 device, function;
@@ -4230,7 +4521,7 @@ BOOL torture_ioctl_test(int dummy)
        DATA_BLOB blob;
        NTSTATUS status;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -4258,7 +4549,8 @@ BOOL torture_ioctl_test(int dummy)
                        status = cli_raw_ioctl(cli, fnum, code, &blob);
 
                        if (NT_STATUS_IS_OK(status)) {
-                               printf("ioctl 0x%x OK : %d bytes\n", code, blob.length);
+                               printf("ioctl 0x%x OK : %d bytes\n", (int)code,
+                                      (int)blob.length);
                                data_blob_free(&blob);
                        }
                }
@@ -4275,13 +4567,13 @@ BOOL torture_ioctl_test(int dummy)
 /*
   tries varients of chkpath
  */
-BOOL torture_chkpath_test(int dummy)
+bool torture_chkpath_test(int dummy)
 {
        static struct cli_state *cli;
        int fnum;
-       BOOL ret;
+       bool ret;
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -4292,12 +4584,12 @@ BOOL torture_chkpath_test(int dummy)
        cli_unlink(cli, "\\chkpath.dir\\*");
        cli_rmdir(cli, "\\chkpath.dir");
 
-       if (!cli_mkdir(cli, "\\chkpath.dir")) {
+       if (!NT_STATUS_IS_OK(cli_mkdir(cli, "\\chkpath.dir"))) {
                printf("mkdir1 failed : %s\n", cli_errstr(cli));
                return False;
        }
 
-       if (!cli_mkdir(cli, "\\chkpath.dir\\dir2")) {
+       if (!NT_STATUS_IS_OK(cli_mkdir(cli, "\\chkpath.dir\\dir2"))) {
                printf("mkdir2 failed : %s\n", cli_errstr(cli));
                return False;
        }
@@ -4354,22 +4646,23 @@ BOOL torture_chkpath_test(int dummy)
        return ret;
 }
 
-static BOOL run_eatest(int dummy)
+static bool run_eatest(int dummy)
 {
        static struct cli_state *cli;
        const char *fname = "\\eatest.txt";
-       BOOL correct = True;
+       bool correct = True;
        int fnum, i;
        size_t num_eas;
        struct ea_struct *ea_list = NULL;
        TALLOC_CTX *mem_ctx = talloc_init("eatest");
 
        printf("starting eatest\n");
-       
-       if (!torture_open_connection(&cli)) {
+
+       if (!torture_open_connection(&cli, 0)) {
+               talloc_destroy(mem_ctx);
                return False;
        }
-       
+
        cli_unlink(cli, fname);
        fnum = cli_nt_create_full(cli, fname, 0,
                                   FIRST_DESIRED_ACCESS, FILE_ATTRIBUTE_ARCHIVE,
@@ -4378,6 +4671,7 @@ static BOOL run_eatest(int dummy)
 
        if (fnum == -1) {
                printf("open failed - %s\n", cli_errstr(cli));
+               talloc_destroy(mem_ctx);
                return False;
        }
 
@@ -4388,10 +4682,11 @@ static BOOL run_eatest(int dummy)
                memset(ea_val, (char)i+1, i+1);
                if (!cli_set_ea_fnum(cli, fnum, ea_name, ea_val, i+1)) {
                        printf("ea_set of name %s failed - %s\n", ea_name, cli_errstr(cli));
+                       talloc_destroy(mem_ctx);
                        return False;
                }
        }
-       
+
        cli_close(cli, fnum);
        for (i = 0; i < 10; i++) {
                fstring ea_name, ea_val;
@@ -4400,16 +4695,17 @@ static BOOL run_eatest(int dummy)
                memset(ea_val, (char)i+1, i+1);
                if (!cli_set_ea_path(cli, fname, ea_name, ea_val, i+1)) {
                        printf("ea_set of name %s failed - %s\n", ea_name, cli_errstr(cli));
+                       talloc_destroy(mem_ctx);
                        return False;
                }
        }
-       
+
        if (!cli_get_ea_list_path(cli, fname, mem_ctx, &num_eas, &ea_list)) {
                printf("ea_get list failed - %s\n", cli_errstr(cli));
                correct = False;
        }
 
-       printf("num_eas = %d\n", num_eas);
+       printf("num_eas = %d\n", (int)num_eas);
 
        if (num_eas != 20) {
                printf("Should be 20 EA's stored... failing.\n");
@@ -4418,30 +4714,37 @@ static BOOL run_eatest(int dummy)
 
        for (i = 0; i < num_eas; i++) {
                printf("%d: ea_name = %s. Val = ", i, ea_list[i].name);
-               dump_data(0, ea_list[i].value.data, ea_list[i].value.length);
+               dump_data(0, ea_list[i].value.data,
+                         ea_list[i].value.length);
        }
 
        /* Setting EA's to zero length deletes them. Test this */
        printf("Now deleting all EA's - case indepenent....\n");
 
+#if 1
+       cli_set_ea_path(cli, fname, "", "", 0);
+#else
        for (i = 0; i < 20; i++) {
                fstring ea_name;
                slprintf(ea_name, sizeof(ea_name), "ea_%d", i);
                if (!cli_set_ea_path(cli, fname, ea_name, "", 0)) {
                        printf("ea_set of name %s failed - %s\n", ea_name, cli_errstr(cli));
+                       talloc_destroy(mem_ctx);
                        return False;
                }
        }
-       
+#endif
+
        if (!cli_get_ea_list_path(cli, fname, mem_ctx, &num_eas, &ea_list)) {
                printf("ea_get list failed - %s\n", cli_errstr(cli));
                correct = False;
        }
 
-       printf("num_eas = %d\n", num_eas);
+       printf("num_eas = %d\n", (int)num_eas);
        for (i = 0; i < num_eas; i++) {
                printf("%d: ea_name = %s. Val = ", i, ea_list[i].name);
-               dump_data(0, ea_list[i].value.data, ea_list[i].value.length);
+               dump_data(0, ea_list[i].value.data,
+                         ea_list[i].value.length);
        }
 
        if (num_eas != 0) {
@@ -4459,20 +4762,20 @@ static BOOL run_eatest(int dummy)
        if (!torture_close_connection(cli)) {
                correct = False;
        }
-       
+
        return correct;
 }
 
-static BOOL run_dirtest1(int dummy)
+static bool run_dirtest1(int dummy)
 {
        int i;
        static struct cli_state *cli;
        int fnum, num_seen;
-       BOOL correct = True;
+       bool correct = True;
 
        printf("starting directory test\n");
 
-       if (!torture_open_connection(&cli)) {
+       if (!torture_open_connection(&cli, 0)) {
                return False;
        }
 
@@ -4498,7 +4801,7 @@ static BOOL run_dirtest1(int dummy)
        for (i=0;i<1000;i++) {
                fstring fname;
                slprintf(fname, sizeof(fname), "\\LISTDIR\\d%d", i);
-               if (!cli_mkdir(cli, fname)) {
+               if (!NT_STATUS_IS_OK(cli_mkdir(cli, fname))) {
                        fprintf(stderr,"Failed to open %s\n", fname);
                        return False;
                }
@@ -4544,10 +4847,11 @@ static BOOL run_dirtest1(int dummy)
        return correct;
 }
 
-static BOOL run_error_map_extract(int dummy) {
-       
-       static struct cli_state c_dos;
-       static struct cli_state c_nt;
+static bool run_error_map_extract(int dummy) {
+
+       static struct cli_state *c_dos;
+       static struct cli_state *c_nt;
+       NTSTATUS status;
 
        uint32 error;
 
@@ -4560,81 +4864,86 @@ static BOOL run_error_map_extract(int dummy) {
 
        /* NT-Error connection */
 
-       if (!open_nbt_connection(&c_nt)) {
+       if (!(c_nt = open_nbt_connection())) {
                return False;
        }
 
-       c_nt.use_spnego = False;
+       c_nt->use_spnego = False;
+
+       status = cli_negprot(c_nt);
 
-       if (!cli_negprot(&c_nt)) {
-               printf("%s rejected the NT-error negprot (%s)\n",host, cli_errstr(&c_nt));
-               cli_shutdown(&c_nt);
+       if (!NT_STATUS_IS_OK(status)) {
+               printf("%s rejected the NT-error negprot (%s)\n", host,
+                      nt_errstr(status));
+               cli_shutdown(c_nt);
                return False;
        }
 
-       if (!cli_session_setup(&c_nt, "", "", 0, "", 0,
-                              workgroup)) {
-               printf("%s rejected the NT-error initial session setup (%s)\n",host, cli_errstr(&c_nt));
+       if (!NT_STATUS_IS_OK(cli_session_setup(c_nt, "", "", 0, "", 0,
+                                              workgroup))) {
+               printf("%s rejected the NT-error initial session setup (%s)\n",host, cli_errstr(c_nt));
                return False;
        }
 
        /* DOS-Error connection */
 
-       if (!open_nbt_connection(&c_dos)) {
+       if (!(c_dos = open_nbt_connection())) {
                return False;
        }
 
-       c_dos.use_spnego = False;
-       c_dos.force_dos_errors = True;
+       c_dos->use_spnego = False;
+       c_dos->force_dos_errors = True;
 
-       if (!cli_negprot(&c_dos)) {
-               printf("%s rejected the DOS-error negprot (%s)\n",host, cli_errstr(&c_dos));
-               cli_shutdown(&c_dos);
+       status = cli_negprot(c_dos);
+       if (!NT_STATUS_IS_OK(status)) {
+               printf("%s rejected the DOS-error negprot (%s)\n", host,
+                      nt_errstr(status));
+               cli_shutdown(c_dos);
                return False;
        }
 
-       if (!cli_session_setup(&c_dos, "", "", 0, "", 0,
-                              workgroup)) {
-               printf("%s rejected the DOS-error initial session setup (%s)\n",host, cli_errstr(&c_dos));
+       if (!NT_STATUS_IS_OK(cli_session_setup(c_dos, "", "", 0, "", 0,
+                                              workgroup))) {
+               printf("%s rejected the DOS-error initial session setup (%s)\n",host, cli_errstr(c_dos));
                return False;
        }
 
        for (error=(0xc0000000 | 0x1); error < (0xc0000000| 0xFFF); error++) {
                fstr_sprintf(user, "%X", error);
 
-               if (cli_session_setup(&c_nt, user, 
-                                      password, strlen(password),
-                                      password, strlen(password),
-                                     workgroup)) {
+               if (NT_STATUS_IS_OK(cli_session_setup(c_nt, user, 
+                                                     password, strlen(password),
+                                                     password, strlen(password),
+                                                     workgroup))) {
                        printf("/** Session setup succeeded.  This shouldn't happen...*/\n");
                }
-               
-               flgs2 = SVAL(c_nt.inbuf,smb_flg2);
-               
+
+               flgs2 = SVAL(c_nt->inbuf,smb_flg2);
+
                /* Case #1: 32-bit NT errors */
                if (flgs2 & FLAGS2_32_BIT_ERROR_CODES) {
-                       nt_status = NT_STATUS(IVAL(c_nt.inbuf,smb_rcls));
+                       nt_status = NT_STATUS(IVAL(c_nt->inbuf,smb_rcls));
                } else {
                        printf("/** Dos error on NT connection! (%s) */\n", 
-                              cli_errstr(&c_nt));
+                              cli_errstr(c_nt));
                        nt_status = NT_STATUS(0xc0000000);
                }
 
-               if (cli_session_setup(&c_dos, user, 
-                                      password, strlen(password),
-                                      password, strlen(password),
-                                      workgroup)) {
+               if (NT_STATUS_IS_OK(cli_session_setup(c_dos, user, 
+                                                     password, strlen(password),
+                                                     password, strlen(password),
+                                                     workgroup))) {
                        printf("/** Session setup succeeded.  This shouldn't happen...*/\n");
                }
-               flgs2 = SVAL(c_dos.inbuf,smb_flg2), errnum;
-               
+               flgs2 = SVAL(c_dos->inbuf,smb_flg2), errnum;
+
                /* Case #1: 32-bit NT errors */
                if (flgs2 & FLAGS2_32_BIT_ERROR_CODES) {
                        printf("/** NT error on DOS connection! (%s) */\n", 
-                              cli_errstr(&c_nt));
+                              cli_errstr(c_nt));
                        errnum = errclass = 0;
                } else {
-                       cli_dos_error(&c_dos, &errclass, &errnum);
+                       cli_dos_error(c_dos, &errclass, &errnum);
                }
 
                if (NT_STATUS_V(nt_status) != error) { 
@@ -4642,7 +4951,7 @@ static BOOL run_error_map_extract(int dummy) {
                               get_nt_error_c_code(NT_STATUS(error)), 
                               get_nt_error_c_code(nt_status));
                }
-               
+
                printf("\t{%s,\t%s,\t%s},\n", 
                       smb_dos_err_class(errclass), 
                       smb_dos_err_name(errclass, errnum), 
@@ -4651,11 +4960,795 @@ static BOOL run_error_map_extract(int dummy) {
        return True;
 }
 
-static double create_procs(BOOL (*fn)(int), BOOL *result)
+static bool run_sesssetup_bench(int dummy)
+{
+       static struct cli_state *c;
+       const char *fname = "\\file.dat";
+       int fnum;
+       NTSTATUS status;
+       int i;
+
+       if (!torture_open_connection(&c, 0)) {
+               return false;
+       }
+
+       fnum = cli_nt_create_full(
+               c, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS,
+               FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF,
+               FILE_DELETE_ON_CLOSE, 0);
+       if (fnum == -1) {
+               d_printf("open %s failed: %s\n", fname, cli_errstr(c));
+               return false;
+       }
+
+       for (i=0; i<torture_numops; i++) {
+               status = cli_session_setup(
+                       c, username,
+                       password, strlen(password),
+                       password, strlen(password),
+                       workgroup);
+               if (!NT_STATUS_IS_OK(status)) {
+                       d_printf("(%s) cli_session_setup failed: %s\n",
+                                __location__, nt_errstr(status));
+                       return false;
+               }
+
+               d_printf("\r%d   ", (int)c->vuid);
+
+               if (!cli_ulogoff(c)) {
+                       d_printf("(%s) cli_ulogoff failed: %s\n",
+                                __location__, cli_errstr(c));
+                       return false;
+               }
+               c->vuid = 0;
+       }
+
+       return true;
+}
+
+static bool subst_test(const char *str, const char *user, const char *domain,
+                      uid_t uid, gid_t gid, const char *expected)
+{
+       char *subst;
+       bool result = true;
+
+       subst = talloc_sub_specified(talloc_tos(), str, user, domain, uid, gid);
+
+       if (strcmp(subst, expected) != 0) {
+               printf("sub_specified(%s, %s, %s, %d, %d) returned [%s], expected "
+                      "[%s]\n", str, user, domain, (int)uid, (int)gid, subst,
+                      expected);
+               result = false;
+       }
+
+       TALLOC_FREE(subst);
+       return result;
+}
+
+static void chain1_open_completion(struct tevent_req *req)
+{
+       int fnum;
+       NTSTATUS status;
+       status = cli_open_recv(req, &fnum);
+       TALLOC_FREE(req);
+
+       d_printf("cli_open_recv returned %s: %d\n",
+                nt_errstr(status),
+                NT_STATUS_IS_OK(status) ? fnum : -1);
+}
+
+static void chain1_write_completion(struct tevent_req *req)
+{
+       size_t written;
+       NTSTATUS status;
+       status = cli_write_andx_recv(req, &written);
+       TALLOC_FREE(req);
+
+       d_printf("cli_write_andx_recv returned %s: %d\n",
+                nt_errstr(status),
+                NT_STATUS_IS_OK(status) ? (int)written : -1);
+}
+
+static void chain1_close_completion(struct tevent_req *req)
+{
+       NTSTATUS status;
+       bool *done = (bool *)tevent_req_callback_data_void(req);
+
+       status = cli_close_recv(req);
+       *done = true;
+
+       TALLOC_FREE(req);
+
+       d_printf("cli_close returned %s\n", nt_errstr(status));
+}
+
+static bool run_chain1(int dummy)
+{
+       struct cli_state *cli1;
+       struct event_context *evt = event_context_init(NULL);
+       struct tevent_req *reqs[3], *smbreqs[3];
+       bool done = false;
+       const char *str = "foobar";
+
+       printf("starting chain1 test\n");
+       if (!torture_open_connection(&cli1, 0)) {
+               return False;
+       }
+
+       cli_sockopt(cli1, sockops);
+
+       reqs[0] = cli_open_create(talloc_tos(), evt, cli1, "\\test",
+                                 O_CREAT|O_RDWR, 0, &smbreqs[0]);
+       if (reqs[0] == NULL) return false;
+       tevent_req_set_callback(reqs[0], chain1_open_completion, NULL);
+
+
+       reqs[1] = cli_write_andx_create(talloc_tos(), evt, cli1, 0, 0,
+                                       (uint8_t *)str, 0, strlen(str)+1,
+                                       smbreqs, 1, &smbreqs[1]);
+       if (reqs[1] == NULL) return false;
+       tevent_req_set_callback(reqs[1], chain1_write_completion, NULL);
+
+       reqs[2] = cli_close_create(talloc_tos(), evt, cli1, 0, &smbreqs[2]);
+       if (reqs[2] == NULL) return false;
+       tevent_req_set_callback(reqs[2], chain1_close_completion, &done);
+
+       if (!cli_smb_chain_send(smbreqs, ARRAY_SIZE(smbreqs))) {
+               return false;
+       }
+
+       while (!done) {
+               event_loop_once(evt);
+       }
+
+       torture_close_connection(cli1);
+       return True;
+}
+
+static bool run_mangle1(int dummy)
+{
+       struct cli_state *cli;
+       const char *fname = "this_is_a_long_fname_to_be_mangled.txt";
+       int fnum;
+       fstring alt_name;
+       NTSTATUS status;
+       time_t change_time, access_time, write_time;
+       SMB_OFF_T size;
+       uint16_t mode;
+
+       printf("starting chain1 test\n");
+       if (!torture_open_connection(&cli, 0)) {
+               return False;
+       }
+
+       cli_sockopt(cli, sockops);
+
+       fnum = cli_nt_create_full(
+               cli, fname, 0, GENERIC_ALL_ACCESS|DELETE_ACCESS,
+               FILE_ATTRIBUTE_NORMAL, 0, FILE_OVERWRITE_IF, 0, 0);
+       if (fnum == -1) {
+               d_printf("open %s failed: %s\n", fname, cli_errstr(cli));
+               return false;
+       }
+       cli_close(cli, fnum);
+
+       status = cli_qpathinfo_alt_name(cli, fname, alt_name);
+       if (!NT_STATUS_IS_OK(status)) {
+               d_printf("cli_qpathinfo_alt_name failed: %s\n",
+                        nt_errstr(status));
+               return false;
+       }
+       d_printf("alt_name: %s\n", alt_name);
+
+       fnum = cli_open(cli, alt_name, O_RDONLY, DENY_NONE);
+       if (fnum == -1) {
+               d_printf("cli_open(%s) failed: %s\n", alt_name,
+                        cli_errstr(cli));
+               return false;
+       }
+       cli_close(cli, fnum);
+
+       if (!cli_qpathinfo(cli, alt_name, &change_time, &access_time,
+                          &write_time, &size, &mode)) {
+               d_printf("cli_qpathinfo(%s) failed: %s\n", alt_name,
+                        cli_errstr(cli));
+               return false;
+       }
+
+       return true;
+}
+
+static size_t null_source(uint8_t *buf, size_t n, void *priv)
+{
+       size_t *to_pull = (size_t *)priv;
+       size_t thistime = *to_pull;
+
+       thistime = MIN(thistime, n);
+       if (thistime == 0) {
+               return 0;
+       }
+
+       memset(buf, 0, thistime);
+       *to_pull -= thistime;
+       return thistime;
+}
+
+static bool run_windows_write(int dummy)
+{
+       struct cli_state *cli1;
+       int fnum;
+       int i;
+       bool ret = false;
+       const char *fname = "\\writetest.txt";
+       double seconds;
+       double kbytes;
+
+       printf("starting windows_write test\n");
+       if (!torture_open_connection(&cli1, 0)) {
+               return False;
+       }
+
+       fnum = cli_open(cli1, fname, O_RDWR|O_CREAT|O_EXCL, DENY_NONE);
+       if (fnum == -1) {
+               printf("open failed (%s)\n", cli_errstr(cli1));
+               return False;
+       }
+
+       cli_sockopt(cli1, sockops);
+
+       start_timer();
+
+       for (i=0; i<torture_numops; i++) {
+               char c = 0;
+               off_t start = i * torture_blocksize;
+               NTSTATUS status;
+               size_t to_pull = torture_blocksize - 1;
+
+               if (cli_write(cli1, fnum, 0, &c,
+                             start + torture_blocksize - 1, 1) != 1) {
+                       printf("cli_write failed: %s\n", cli_errstr(cli1));
+                       goto fail;
+               }
+
+               status = cli_push(cli1, fnum, 0, i * torture_blocksize, torture_blocksize,
+                                 null_source, &to_pull);
+               if (!NT_STATUS_IS_OK(status)) {
+                       printf("cli_push returned: %s\n", nt_errstr(status));
+                       goto fail;
+               }
+       }
+
+       seconds = end_timer();
+       kbytes = (double)torture_blocksize * torture_numops;
+       kbytes /= 1024;
+
+       printf("Wrote %d kbytes in %.2f seconds: %d kb/sec\n", (int)kbytes,
+              (double)seconds, (int)(kbytes/seconds));
+
+       ret = true;
+ fail:
+       cli_close(cli1, fnum);
+       cli_unlink(cli1, fname);
+       torture_close_connection(cli1);
+       return ret;
+}
+
+static bool run_cli_echo(int dummy)
+{
+       struct cli_state *cli;
+       NTSTATUS status;
+
+       printf("starting cli_echo test\n");
+       if (!torture_open_connection(&cli, 0)) {
+               return false;
+       }
+       cli_sockopt(cli, sockops);
+
+       status = cli_echo(cli, 5, data_blob_const("hello", 5));
+
+       d_printf("cli_echo returned %s\n", nt_errstr(status));
+
+       torture_close_connection(cli);
+       return NT_STATUS_IS_OK(status);
+}
+
+static bool run_uid_regression_test(int dummy)
+{
+       static struct cli_state *cli;
+       int16_t old_vuid;
+       bool correct = True;
+
+       printf("starting uid regression test\n");
+
+       if (!torture_open_connection(&cli, 0)) {
+               return False;
+       }
+
+       cli_sockopt(cli, sockops);
+
+       /* Ok - now save then logoff our current user. */
+       old_vuid = cli->vuid;
+
+       if (!cli_ulogoff(cli)) {
+               d_printf("(%s) cli_ulogoff failed: %s\n",
+                       __location__, cli_errstr(cli));
+               correct = false;
+               goto out;
+       }
+
+       cli->vuid = old_vuid;
+
+       /* Try an operation. */
+       if (!NT_STATUS_IS_OK(cli_mkdir(cli, "\\uid_reg_test"))) {
+               /* We expect bad uid. */
+               if (!check_error(__LINE__, cli, ERRSRV, ERRbaduid,
+                               NT_STATUS_NO_SUCH_USER)) {
+                       return False;
+               }
+               goto out;
+       }
+
+       cli_rmdir(cli, "\\uid_reg_test");
+
+  out:
+
+       torture_close_connection(cli);
+       return correct;
+}
+
+static bool run_local_substitute(int dummy)
+{
+       bool ok = true;
+
+       ok &= subst_test("%U", "bla", "", -1, -1, "bla");
+       ok &= subst_test("%u%U", "bla", "", -1, -1, "blabla");
+       ok &= subst_test("%g", "", "", -1, -1, "NO_GROUP");
+       ok &= subst_test("%G", "", "", -1, -1, "NO_GROUP");
+       ok &= subst_test("%g", "", "", -1, 0, gidtoname(0));
+       ok &= subst_test("%G", "", "", -1, 0, gidtoname(0));
+       ok &= subst_test("%D%u", "u", "dom", -1, 0, "domu");
+       ok &= subst_test("%i %I", "", "", -1, -1, "0.0.0.0 0.0.0.0");
+
+       /* Different captialization rules in sub_basic... */
+
+       ok &=  (strcmp(talloc_sub_basic(talloc_tos(), "BLA", "dom", "%U%D"),
+                      "blaDOM") == 0);
+
+       return ok;
+}
+
+static bool run_local_gencache(int dummy)
+{
+       char *val;
+       time_t tm;
+       DATA_BLOB blob;
+
+       if (!gencache_init()) {
+               d_printf("%s: gencache_init() failed\n", __location__);
+               return False;
+       }
+
+       if (!gencache_set("foo", "bar", time(NULL) + 1000)) {
+               d_printf("%s: gencache_set() failed\n", __location__);
+               return False;
+       }
+
+       if (!gencache_get("foo", &val, &tm)) {
+               d_printf("%s: gencache_get() failed\n", __location__);
+               return False;
+       }
+
+       if (strcmp(val, "bar") != 0) {
+               d_printf("%s: gencache_get() returned %s, expected %s\n",
+                        __location__, val, "bar");
+               SAFE_FREE(val);
+               return False;
+       }
+
+       SAFE_FREE(val);
+
+       if (!gencache_del("foo")) {
+               d_printf("%s: gencache_del() failed\n", __location__);
+               return False;
+       }
+       if (gencache_del("foo")) {
+               d_printf("%s: second gencache_del() succeeded\n",
+                        __location__);
+               return False;
+       }
+
+       if (gencache_get("foo", &val, &tm)) {
+               d_printf("%s: gencache_get() on deleted entry "
+                        "succeeded\n", __location__);
+               return False;
+       }
+
+       blob = data_blob_string_const_null("bar");
+       tm = time(NULL);
+
+       if (!gencache_set_data_blob("foo", &blob, tm)) {
+               d_printf("%s: gencache_set_data_blob() failed\n", __location__);
+               return False;
+       }
+
+       data_blob_free(&blob);
+
+       if (!gencache_get_data_blob("foo", &blob, NULL)) {
+               d_printf("%s: gencache_get_data_blob() failed\n", __location__);
+               return False;
+       }
+
+       if (strcmp((const char *)blob.data, "bar") != 0) {
+               d_printf("%s: gencache_get_data_blob() returned %s, expected %s\n",
+                        __location__, (const char *)blob.data, "bar");
+               data_blob_free(&blob);
+               return False;
+       }
+
+       data_blob_free(&blob);
+
+       if (!gencache_del("foo")) {
+               d_printf("%s: gencache_del() failed\n", __location__);
+               return False;
+       }
+       if (gencache_del("foo")) {
+               d_printf("%s: second gencache_del() succeeded\n",
+                        __location__);
+               return False;
+       }
+
+       if (gencache_get_data_blob("foo", &blob, NULL)) {
+               d_printf("%s: gencache_get_data_blob() on deleted entry "
+                        "succeeded\n", __location__);
+               return False;
+       }
+
+       if (!gencache_shutdown()) {
+               d_printf("%s: gencache_shutdown() failed\n", __location__);
+               return False;
+       }
+
+       if (gencache_shutdown()) {
+               d_printf("%s: second gencache_shutdown() succeeded\n",
+                        __location__);
+               return False;
+       }
+
+       return True;
+}
+
+static bool rbt_testval(struct db_context *db, const char *key,
+                       const char *value)
+{
+       struct db_record *rec;
+       TDB_DATA data = string_tdb_data(value);
+       bool ret = false;
+       NTSTATUS status;
+
+       rec = db->fetch_locked(db, db, string_tdb_data(key));
+       if (rec == NULL) {
+               d_fprintf(stderr, "fetch_locked failed\n");
+               goto done;
+       }
+       status = rec->store(rec, data, 0);
+       if (!NT_STATUS_IS_OK(status)) {
+               d_fprintf(stderr, "store failed: %s\n", nt_errstr(status));
+               goto done;
+       }
+       TALLOC_FREE(rec);
+
+       rec = db->fetch_locked(db, db, string_tdb_data(key));
+       if (rec == NULL) {
+               d_fprintf(stderr, "second fetch_locked failed\n");
+               goto done;
+       }
+       if ((rec->value.dsize != data.dsize)
+           || (memcmp(rec->value.dptr, data.dptr, data.dsize) != 0)) {
+               d_fprintf(stderr, "Got wrong data back\n");
+               goto done;
+       }
+
+       ret = true;
+ done:
+       TALLOC_FREE(rec);
+       return ret;
+}
+
+static bool run_local_rbtree(int dummy)
+{
+       struct db_context *db;
+       bool ret = false;
+       int i;
+
+       db = db_open_rbt(NULL);
+
+       if (db == NULL) {
+               d_fprintf(stderr, "db_open_rbt failed\n");
+               return false;
+       }
+
+       for (i=0; i<1000; i++) {
+               char *key, *value;
+
+               if (asprintf(&key, "key%ld", random()) == -1) {
+                       goto done;
+               }
+               if (asprintf(&value, "value%ld", random()) == -1) {
+                       SAFE_FREE(key);
+                       goto done;
+               }
+
+               if (!rbt_testval(db, key, value)) {
+                       SAFE_FREE(key);
+                       SAFE_FREE(value);
+                       goto done;
+               }
+
+               SAFE_FREE(value);
+               if (asprintf(&value, "value%ld", random()) == -1) {
+                       SAFE_FREE(key);
+                       goto done;
+               }
+
+               if (!rbt_testval(db, key, value)) {
+                       SAFE_FREE(key);
+                       SAFE_FREE(value);
+                       goto done;
+               }
+
+               SAFE_FREE(key);
+               SAFE_FREE(value);
+       }
+
+       ret = true;
+
+ done:
+       TALLOC_FREE(db);
+       return ret;
+}
+
+static bool test_stream_name(const char *fname, const char *expected_base,
+                            const char *expected_stream,
+                            NTSTATUS expected_status)
+{
+       NTSTATUS status;
+       char *base = NULL;
+       char *stream = NULL;
+
+       status = split_ntfs_stream_name(talloc_tos(), fname, &base, &stream);
+       if (!NT_STATUS_EQUAL(status, expected_status)) {
+               goto error;
+       }
+
+       if (!NT_STATUS_IS_OK(status)) {
+               return true;
+       }
+
+       if (base == NULL) goto error;
+
+       if (strcmp(expected_base, base) != 0) goto error;
+
+       if ((expected_stream != NULL) && (stream == NULL)) goto error;
+       if ((expected_stream == NULL) && (stream != NULL)) goto error;
+
+       if ((stream != NULL) && (strcmp(expected_stream, stream) != 0))
+               goto error;
+
+       TALLOC_FREE(base);
+       TALLOC_FREE(stream);
+       return true;
+
+ error:
+       d_fprintf(stderr, "test_stream(%s, %s, %s, %s)\n",
+                 fname, expected_base ? expected_base : "<NULL>",
+                 expected_stream ? expected_stream : "<NULL>",
+                 nt_errstr(expected_status));
+       d_fprintf(stderr, "-> base=%s, stream=%s, status=%s\n",
+                 base ? base : "<NULL>", stream ? stream : "<NULL>",
+                 nt_errstr(status));
+       TALLOC_FREE(base);
+       TALLOC_FREE(stream);
+       return false;
+}
+
+static bool run_local_stream_name(int dummy)
+{
+       bool ret = true;
+
+       ret &= test_stream_name(
+               "bla", "bla", NULL, NT_STATUS_OK);
+       ret &= test_stream_name(
+               "bla::$DATA", "bla", NULL, NT_STATUS_OK);
+       ret &= test_stream_name(
+               "bla:blub:", "bla", NULL, NT_STATUS_OBJECT_NAME_INVALID);
+       ret &= test_stream_name(
+               "bla::", NULL, NULL, NT_STATUS_OBJECT_NAME_INVALID);
+       ret &= test_stream_name(
+               "bla::123", "bla", NULL, NT_STATUS_OBJECT_NAME_INVALID);
+       ret &= test_stream_name(
+               "bla:$DATA", "bla", "$DATA:$DATA", NT_STATUS_OK);
+       ret &= test_stream_name(
+               "bla:x:$DATA", "bla", "x:$DATA", NT_STATUS_OK);
+       ret &= test_stream_name(
+               "bla:x", "bla", "x:$DATA", NT_STATUS_OK);
+
+       return ret;
+}
+
+static bool data_blob_equal(DATA_BLOB a, DATA_BLOB b)
+{
+       if (a.length != b.length) {
+               printf("a.length=%d != b.length=%d\n",
+                      (int)a.length, (int)b.length);
+               return false;
+       }
+       if (memcmp(a.data, b.data, a.length) != 0) {
+               printf("a.data and b.data differ\n");
+               return false;
+       }
+       return true;
+}
+
+static bool run_local_memcache(int dummy)
+{
+       struct memcache *cache;
+       DATA_BLOB k1, k2;
+       DATA_BLOB d1, d2, d3;
+       DATA_BLOB v1, v2, v3;
+
+       TALLOC_CTX *mem_ctx;
+       char *str1, *str2;
+       size_t size1, size2;
+       bool ret = false;
+
+       cache = memcache_init(NULL, 100);
+
+       if (cache == NULL) {
+               printf("memcache_init failed\n");
+               return false;
+       }
+
+       d1 = data_blob_const("d1", 2);
+       d2 = data_blob_const("d2", 2);
+       d3 = data_blob_const("d3", 2);
+
+       k1 = data_blob_const("d1", 2);
+       k2 = data_blob_const("d2", 2);
+
+       memcache_add(cache, STAT_CACHE, k1, d1);
+       memcache_add(cache, GETWD_CACHE, k2, d2);
+
+       if (!memcache_lookup(cache, STAT_CACHE, k1, &v1)) {
+               printf("could not find k1\n");
+               return false;
+       }
+       if (!data_blob_equal(d1, v1)) {
+               return false;
+       }
+
+       if (!memcache_lookup(cache, GETWD_CACHE, k2, &v2)) {
+               printf("could not find k2\n");
+               return false;
+       }
+       if (!data_blob_equal(d2, v2)) {
+               return false;
+       }
+
+       memcache_add(cache, STAT_CACHE, k1, d3);
+
+       if (!memcache_lookup(cache, STAT_CACHE, k1, &v3)) {
+               printf("could not find replaced k1\n");
+               return false;
+       }
+       if (!data_blob_equal(d3, v3)) {
+               return false;
+       }
+
+       memcache_add(cache, GETWD_CACHE, k1, d1);
+
+       if (memcache_lookup(cache, GETWD_CACHE, k2, &v2)) {
+               printf("Did find k2, should have been purged\n");
+               return false;
+       }
+
+       TALLOC_FREE(cache);
+
+       cache = memcache_init(NULL, 0);
+
+       mem_ctx = talloc_init("foo");
+
+       str1 = talloc_strdup(mem_ctx, "string1");
+       str2 = talloc_strdup(mem_ctx, "string2");
+
+       memcache_add_talloc(cache, SINGLETON_CACHE_TALLOC,
+                           data_blob_string_const("torture"), &str1);
+       size1 = talloc_total_size(cache);
+
+       memcache_add_talloc(cache, SINGLETON_CACHE_TALLOC,
+                           data_blob_string_const("torture"), &str2);
+       size2 = talloc_total_size(cache);
+
+       printf("size1=%d, size2=%d\n", (int)size1, (int)size2);
+
+       if (size2 > size1) {
+               printf("memcache leaks memory!\n");
+               goto fail;
+       }
+
+       ret = true;
+ fail:
+       TALLOC_FREE(cache);
+       return ret;
+}
+
+static void wbclient_done(struct tevent_req *req)
+{
+       wbcErr wbc_err;
+       struct winbindd_response *wb_resp;
+       int *i = (int *)tevent_req_callback_data_void(req);
+
+       wbc_err = wb_trans_recv(req, req, &wb_resp);
+       TALLOC_FREE(req);
+       *i += 1;
+       d_printf("wb_trans_recv %d returned %s\n", *i, wbcErrorString(wbc_err));
+}
+
+static bool run_local_wbclient(int dummy)
+{
+       struct event_context *ev;
+       struct wb_context **wb_ctx;
+       struct winbindd_request wb_req;
+       bool result = false;
+       int i, j;
+
+       BlockSignals(True, SIGPIPE);
+
+       ev = event_context_init(talloc_tos());
+       if (ev == NULL) {
+               goto fail;
+       }
+
+       wb_ctx = TALLOC_ARRAY(ev, struct wb_context *, torture_numops);
+       if (wb_ctx == NULL) {
+               goto fail;
+       }
+
+       ZERO_STRUCT(wb_req);
+       wb_req.cmd = WINBINDD_PING;
+
+       for (i=0; i<torture_numops; i++) {
+               wb_ctx[i] = wb_context_init(ev);
+               if (wb_ctx[i] == NULL) {
+                       goto fail;
+               }
+               for (j=0; j<5; j++) {
+                       struct tevent_req *req;
+                       req = wb_trans_send(ev, ev, wb_ctx[i],
+                                           (j % 2) == 0, &wb_req);
+                       if (req == NULL) {
+                               goto fail;
+                       }
+                       tevent_req_set_callback(req, wbclient_done, &i);
+               }
+       }
+
+       i = 0;
+
+       while (i < 5 * torture_numops) {
+               event_loop_once(ev);
+       }
+
+       result = true;
+ fail:
+       TALLOC_FREE(ev);
+       return result;
+}
+
+static double create_procs(bool (*fn)(int), bool *result)
 {
        int i, status;
        volatile pid_t *child_status;
-       volatile BOOL *child_status_out;
+       volatile bool *child_status_out;
        int synccount;
        int tries = 8;
 
@@ -4667,7 +5760,7 @@ static double create_procs(BOOL (*fn)(int), BOOL *result)
                return -1;
        }
 
-       child_status_out = (volatile BOOL *)shm_setup(sizeof(BOOL)*nprocs);
+       child_status_out = (volatile bool *)shm_setup(sizeof(bool)*nprocs);
        if (!child_status_out) {
                printf("Failed to setup result status shared memory\n");
                return -1;
@@ -4689,7 +5782,7 @@ static double create_procs(BOOL (*fn)(int), BOOL *result)
                        slprintf(myname,sizeof(myname),"CLIENT%d", i);
 
                        while (1) {
-                               if (torture_open_connection(&current_cli)) break;
+                               if (torture_open_connection(&current_cli, i)) break;
                                if (tries-- == 0) {
                                        printf("pid %d failed to start\n", (int)getpid());
                                        _exit(1);
@@ -4735,7 +5828,7 @@ static double create_procs(BOOL (*fn)(int), BOOL *result)
        }
 
        printf("\n");
-       
+
        for (i=0;i<nprocs;i++) {
                if (!child_status_out[i]) {
                        *result = False;
@@ -4748,7 +5841,7 @@ static double create_procs(BOOL (*fn)(int), BOOL *result)
 
 static struct {
        const char *name;
-       BOOL (*fn)(int);
+       bool (*fn)(int);
        unsigned flags;
 } torture_ops[] = {
        {"FDPASS", run_fdpasstest, 0},
@@ -4781,6 +5874,8 @@ static struct {
        {"RW2",  run_readwritemulti, FLAG_MULTIPROC},
        {"RW3",  run_readwritelarge, 0},
        {"OPEN", run_opentest, 0},
+       {"POSIX", run_simple_posix_open_test, 0},
+       { "UID-REGRESSION-TEST", run_uid_regression_test, 0},
 #if 1
        {"OPENATTR", run_openattrtest, 0},
 #endif
@@ -4789,6 +5884,7 @@ static struct {
        {"DELETE", run_deletetest, 0},
        {"PROPERTIES", run_properties, 0},
        {"MANGLE", torture_mangle, 0},
+       {"MANGLE1", run_mangle1, 0},
        {"W2K", run_w2ktest, 0},
        {"TRANS2SCAN", torture_trans2_scan, 0},
        {"NTTRANSSCAN", torture_nttrans_scan, 0},
@@ -4801,6 +5897,16 @@ static struct {
        {"CHKPATH",  torture_chkpath_test, 0},
        {"FDSESS", run_fdsesstest, 0},
        { "EATEST", run_eatest, 0},
+       { "SESSSETUP_BENCH", run_sesssetup_bench, 0},
+       { "CHAIN1", run_chain1, 0},
+       { "WINDOWS-WRITE", run_windows_write, 0},
+       { "CLI_ECHO", run_cli_echo, 0},
+       { "LOCAL-SUBSTITUTE", run_local_substitute, 0},
+       { "LOCAL-GENCACHE", run_local_gencache, 0},
+       { "LOCAL-RBTREE", run_local_rbtree, 0},
+       { "LOCAL-MEMCACHE", run_local_memcache, 0},
+       { "LOCAL-STREAM-NAME", run_local_stream_name, 0},
+       { "LOCAL-WBCLIENT", run_local_wbclient, 0},
        {NULL, NULL, 0}};
 
 
@@ -4808,11 +5914,11 @@ static struct {
 /****************************************************************************
 run a specified test or "ALL"
 ****************************************************************************/
-static BOOL run_test(const char *name)
+static bool run_test(const char *name)
 {
-       BOOL ret = True;
-       BOOL result = True;
-       BOOL found = False;
+       bool ret = True;
+       bool result = True;
+       bool found = False;
        int i;
        double t;
        if (strequal(name,"ALL")) {
@@ -4821,7 +5927,7 @@ static BOOL run_test(const char *name)
                }
                found = True;
        }
-       
+
        for (i=0;torture_ops[i].name;i++) {
                fstr_sprintf(randomfname, "\\XX%x", 
                         (unsigned)random());
@@ -4835,7 +5941,6 @@ static BOOL run_test(const char *name)
                                        ret = False;
                                        printf("TEST %s FAILED!\n", name);
                                }
-                                        
                        } else {
                                start_timer();
                                if (!torture_ops[i].fn(0)) {
@@ -4861,6 +5966,9 @@ static void usage(void)
 {
        int i;
 
+       printf("WARNING samba4 test suite is much more complete nowadays.\n");
+       printf("Please use samba4 torture.\n\n");
+
        printf("Usage: smbtorture //server/share <options> TEST1 TEST2 ...\n");
 
        printf("\t-d debuglevel\n");
@@ -4877,6 +5985,7 @@ static void usage(void)
        printf("\t-A showall\n");
        printf("\t-p port\n");
        printf("\t-s seed\n");
+       printf("\t-b unclist_filename   specify multiple shares for multiple connections\n");
        printf("\n\n");
 
        printf("tests are:");
@@ -4886,7 +5995,7 @@ static void usage(void)
        printf("\n");
 
        printf("default test is ALL\n");
-       
+
        exit(1);
 }
 
@@ -4899,9 +6008,9 @@ static void usage(void)
        char *p;
        int gotuser = 0;
        int gotpass = 0;
-       extern char *optarg;
-       extern int optind;
-       BOOL correct = True;
+       bool correct = True;
+       TALLOC_CTX *frame = talloc_stackframe();
+       int seed = time(NULL);
 
        dbf = x_stdout;
 
@@ -4909,7 +6018,14 @@ static void usage(void)
        setbuffer(stdout, NULL, 0);
 #endif
 
-       lp_load(dyn_CONFIGFILE,True,False,False);
+       load_case_tables();
+
+       if (is_default_dyn_CONFIGFILE()) {
+               if(getenv("SMB_CONF_PATH")) {
+                       set_dyn_CONFIGFILE(getenv("SMB_CONF_PATH"));
+               }
+       }
+       lp_load(get_dyn_CONFIGFILE(),True,False,False,True);
        load_interfaces();
 
        if (argc < 2) {
@@ -4919,7 +6035,7 @@ static void usage(void)
         for(p = argv[1]; *p; p++)
           if(*p == '\\')
             *p = '/';
+
        if (strncmp(argv[1], "//", 2)) {
                usage();
        }
@@ -4932,7 +6048,11 @@ static void usage(void)
        *p = 0;
        fstrcpy(share, p+1);
 
-       get_myname(myname);
+       fstrcpy(myname, get_myname(talloc_tos()));
+       if (!*myname) {
+               fprintf(stderr, "Failed to get my hostname.\n");
+               return 1;
+       }
 
        if (*username == 0 && getenv("LOGNAME")) {
          fstrcpy(username,getenv("LOGNAME"));
@@ -4941,17 +6061,15 @@ static void usage(void)
        argc--;
        argv++;
 
-       srandom(time(NULL));
-
        fstrcpy(workgroup, lp_workgroup());
 
-       while ((opt = getopt(argc, argv, "p:hW:U:n:N:O:o:m:Ld:Ac:ks:")) != EOF) {
+       while ((opt = getopt(argc, argv, "p:hW:U:n:N:O:o:m:Ld:Aec:ks:b:B:")) != EOF) {
                switch (opt) {
                case 'p':
                        port_to_use = atoi(optarg);
                        break;
                case 's':
-                       srandom(atoi(optarg));
+                       seed = atoi(optarg);
                        break;
                case 'W':
                        fstrcpy(workgroup,optarg);
@@ -4983,6 +6101,9 @@ static void usage(void)
                case 'c':
                        client_txt = optarg;
                        break;
+               case 'e':
+                       do_encrypt = true;
+                       break;
                case 'k':
 #ifdef HAVE_KRB5
                        use_kerberos = True;
@@ -5001,12 +6122,23 @@ static void usage(void)
                                gotpass = 1;
                        }
                        break;
+               case 'b':
+                       fstrcpy(multishare_conn_fname, optarg);
+                       use_multishare_conn = True;
+                       break;
+               case 'B':
+                       torture_blocksize = atoi(optarg);
+                       break;
                default:
                        printf("Unknown option %c (%d)\n", (char)opt, opt);
                        usage();
                }
        }
 
+       d_printf("using seed %d\n", seed);
+
+       srandom(seed);
+
        if(use_kerberos && !gotuser) gotpass = True;
 
        while (!gotpass) {
@@ -5030,6 +6162,8 @@ static void usage(void)
                }
        }
 
+       TALLOC_FREE(frame);
+
        if (correct) {
                return(0);
        } else {