s3: libsmb: Correctly save and restore connection tcon in smbclient, smbcacls and...
authorJeremy Allison <jra@samba.org>
Tue, 13 Jun 2017 23:56:48 +0000 (16:56 -0700)
committerJeremy Allison <jra@samba.org>
Sat, 17 Jun 2017 04:39:20 +0000 (06:39 +0200)
BUG: https://bugzilla.samba.org/show_bug.cgi?id=12831

Signed-off-by: Jeremy Allison <jra@samba.org>
Reviewed-by: Richard Sharpe <realrichardsharpe@gmail.com>
source3/lib/util_sd.c
source3/libsmb/clidfs.c
source3/torture/torture.c
source3/utils/net_rpc.c
source3/utils/smbcacls.c

index a95cafd5f7afe925f6d509c4bb8fed0f9cb264e4..aa6d4809fc8b7ed5ee98a439e39f2236cc13e7d2 100644 (file)
@@ -84,7 +84,7 @@ static NTSTATUS cli_lsa_lookup_sid(struct cli_state *cli,
                                   enum lsa_SidType *type,
                                   char **domain, char **name)
 {
-       uint32_t orig_cnum = cli_state_get_tid(cli);
+       struct smbXcli_tcon *orig_tcon = NULL;
        struct rpc_pipe_client *p = NULL;
        struct policy_handle handle;
        NTSTATUS status;
@@ -93,6 +93,14 @@ static NTSTATUS cli_lsa_lookup_sid(struct cli_state *cli,
        char **domains;
        char **names;
 
+       if (cli_state_has_tcon(cli)) {
+               orig_tcon = cli_state_save_tcon(cli);
+               if (orig_tcon == NULL) {
+                       status = NT_STATUS_NO_MEMORY;
+                       goto tcon_fail;
+               }
+       }
+
        status = cli_tree_connect(cli, "IPC$", "?????", NULL);
        if (!NT_STATUS_IS_OK(status)) {
                goto tcon_fail;
@@ -125,7 +133,7 @@ static NTSTATUS cli_lsa_lookup_sid(struct cli_state *cli,
        TALLOC_FREE(p);
        cli_tdis(cli);
  tcon_fail:
-       cli_state_set_tid(cli, orig_cnum);
+       cli_state_restore_tcon(cli, orig_tcon);
        TALLOC_FREE(frame);
        return status;
 }
@@ -165,7 +173,7 @@ static NTSTATUS cli_lsa_lookup_name(struct cli_state *cli,
                                    enum lsa_SidType *type,
                                    struct dom_sid *sid)
 {
-       uint32_t orig_cnum = cli_state_get_tid(cli);
+       struct smbXcli_tcon *orig_tcon = NULL;
        struct rpc_pipe_client *p;
        struct policy_handle handle;
        NTSTATUS status;
@@ -173,6 +181,14 @@ static NTSTATUS cli_lsa_lookup_name(struct cli_state *cli,
        struct dom_sid *sids;
        enum lsa_SidType *types;
 
+       if (cli_state_has_tcon(cli)) {
+               orig_tcon = cli_state_save_tcon(cli);
+               if (orig_tcon == NULL) {
+                       status = NT_STATUS_NO_MEMORY;
+                       goto tcon_fail;
+               }
+       }
+
        status = cli_tree_connect(cli, "IPC$", "?????", NULL);
        if (!NT_STATUS_IS_OK(status)) {
                goto tcon_fail;
@@ -204,7 +220,7 @@ static NTSTATUS cli_lsa_lookup_name(struct cli_state *cli,
        TALLOC_FREE(p);
        cli_tdis(cli);
  tcon_fail:
-       cli_state_set_tid(cli, orig_cnum);
+       cli_state_restore_tcon(cli, orig_tcon);
        TALLOC_FREE(frame);
        return status;
 }
index 1010e1b5c280f6c095ef77656ab0d82fbf37497f..75012b28e875ee30d73bd8f873b69596c3ea808b 100644 (file)
@@ -1205,7 +1205,7 @@ bool cli_check_msdfs_proxy(TALLOC_CTX *ctx,
        size_t consumed = 0;
        char *fullpath = NULL;
        bool res;
-       uint32_t cnum;
+       struct smbXcli_tcon *orig_tcon = NULL;
        char *newextrapath = NULL;
        NTSTATUS status;
        const char *remote_name;
@@ -1215,7 +1215,6 @@ bool cli_check_msdfs_proxy(TALLOC_CTX *ctx,
        }
 
        remote_name = smbXcli_conn_remote_name(cli->conn);
-       cnum = cli_state_get_tid(cli);
 
        /* special case.  never check for a referral on the IPC$ share */
 
@@ -1230,15 +1229,25 @@ bool cli_check_msdfs_proxy(TALLOC_CTX *ctx,
                return false;
        }
 
+       /* Store tcon state. */
+       if (cli_state_has_tcon(cli)) {
+               orig_tcon = cli_state_save_tcon(cli);
+               if (orig_tcon == NULL) {
+                       return false;
+               }
+       }
+
        /* check for the referral */
 
        if (!NT_STATUS_IS_OK(cli_tree_connect(cli, "IPC$", "IPC", NULL))) {
+               cli_state_restore_tcon(cli, orig_tcon);
                return false;
        }
 
        if (force_encrypt) {
                status = cli_cm_force_encryption_creds(cli, creds, "IPC$");
                if (!NT_STATUS_IS_OK(status)) {
+                       cli_state_restore_tcon(cli, orig_tcon);
                        return false;
                }
        }
@@ -1248,12 +1257,13 @@ bool cli_check_msdfs_proxy(TALLOC_CTX *ctx,
        res = NT_STATUS_IS_OK(status);
 
        status = cli_tdis(cli);
+
+       cli_state_restore_tcon(cli, orig_tcon);
+
        if (!NT_STATUS_IS_OK(status)) {
                return false;
        }
 
-       cli_state_set_tid(cli, cnum);
-
        if (!res || !num_refs) {
                return false;
        }
index d7daffa20bcefe5e0936deb84e3f7ade61ec619e..6b6dbdf1f09a35771bafb64dbb01d63f87e66153 100644 (file)
@@ -1302,6 +1302,7 @@ static bool run_tcon_test(int dummy)
        const char *fname = "\\tcontest.tmp";
        uint16_t fnum1;
        uint32_t cnum1, cnum2, cnum3;
+       struct smbXcli_tcon *orig_tcon = NULL;
        uint16_t vuid1, vuid2;
        char buf[4];
        bool ret = True;
@@ -1333,6 +1334,11 @@ static bool run_tcon_test(int dummy)
                return False;
        }
 
+       orig_tcon = cli_state_save_tcon(cli);
+       if (orig_tcon == NULL) {
+               return false;
+       }
+
        status = cli_tree_connect_creds(cli, share, "?????", torture_creds);
        if (!NT_STATUS_IS_OK(status)) {
                printf("%s refused 2nd tree connect (%s)\n", host,
@@ -1400,6 +1406,8 @@ static bool run_tcon_test(int dummy)
                return False;
        }
 
+       cli_state_restore_tcon(cli, orig_tcon);
+
        cli_state_set_tid(cli, cnum1);
 
        if (!torture_close_connection(cli)) {
@@ -9017,6 +9025,7 @@ static bool run_uid_regression_test(int dummy)
        int16_t old_vuid;
        int32_t old_cnum;
        bool correct = True;
+       struct smbXcli_tcon *orig_tcon = NULL;
        NTSTATUS status;
 
        printf("starting uid regression test\n");
@@ -9057,6 +9066,11 @@ static bool run_uid_regression_test(int dummy)
        }
 
        old_cnum = cli_state_get_tid(cli);
+       orig_tcon = cli_state_save_tcon(cli);
+       if (orig_tcon == NULL) {
+               correct = false;
+               goto out;
+       }
 
        /* Now try a SMBtdis with the invald vuid set to zero. */
        cli_state_set_uid(cli, 0);
@@ -9069,9 +9083,11 @@ static bool run_uid_regression_test(int dummy)
        } else {
                d_printf("First tdis failed (%s)\n", nt_errstr(status));
                correct = false;
+               cli_state_restore_tcon(cli, orig_tcon);
                goto out;
        }
 
+       cli_state_restore_tcon(cli, orig_tcon);
        cli_state_set_uid(cli, old_vuid);
        cli_state_set_tid(cli, old_cnum);
 
index e98f65a3158ffe3a884addfeefcaf14f0e644147..7059ebde3cab3ad4f28dd6c16fa871da6acc90bc 100644 (file)
@@ -5101,7 +5101,7 @@ static void show_userlist(struct rpc_pipe_client *pipe_hnd,
        union srvsvc_NetShareInfo info;
        WERROR result;
        NTSTATUS status;
-       uint16_t cnum;
+       struct smbXcli_tcon *orig_tcon = NULL;
        struct dcerpc_binding_handle *b = pipe_hnd->binding_handle;
 
        status = dcerpc_srvsvc_NetShareGetInfo(b, mem_ctx,
@@ -5123,9 +5123,15 @@ static void show_userlist(struct rpc_pipe_client *pipe_hnd,
                          netname));
        }
 
-       cnum = cli_state_get_tid(cli);
+       if (cli_state_has_tcon(cli)) {
+               orig_tcon = cli_state_save_tcon(cli);
+               if (orig_tcon == NULL) {
+                       return;
+               }
+       }
 
        if (!NT_STATUS_IS_OK(cli_tree_connect(cli, netname, "A:", NULL))) {
+               cli_state_restore_tcon(cli, orig_tcon);
                return;
        }
 
@@ -5168,7 +5174,7 @@ static void show_userlist(struct rpc_pipe_client *pipe_hnd,
        if (fnum != (uint16_t)-1)
                cli_close(cli, fnum);
        cli_tdis(cli);
-       cli_state_set_tid(cli, cnum);
+       cli_state_restore_tcon(cli, orig_tcon);
 
        return;
 }
index 11289e69e4368dddf98b27d3ce181e58e2eb5226..86b4591d3650900ec7fb1d1e7529dee2858eaffd 100644 (file)
@@ -51,12 +51,20 @@ static NTSTATUS cli_lsa_lookup_domain_sid(struct cli_state *cli,
                                          struct dom_sid *sid)
 {
        union lsa_PolicyInformation *info = NULL;
-       uint16_t orig_cnum = cli_state_get_tid(cli);
+       struct smbXcli_tcon *orig_tcon = NULL;
        struct rpc_pipe_client *rpc_pipe = NULL;
        struct policy_handle handle;
        NTSTATUS status, result;
        TALLOC_CTX *frame = talloc_stackframe();
 
+       if (cli_state_has_tcon(cli)) {
+               orig_tcon = cli_state_save_tcon(cli);
+               if (orig_tcon == NULL) {
+                       status = NT_STATUS_NO_MEMORY;
+                       goto done;
+               }
+       }
+
        status = cli_tree_connect(cli, "IPC$", "?????", NULL);
        if (!NT_STATUS_IS_OK(status)) {
                goto done;
@@ -88,7 +96,7 @@ tdis:
        TALLOC_FREE(rpc_pipe);
        cli_tdis(cli);
 done:
-       cli_state_set_tid(cli, orig_cnum);
+       cli_state_restore_tcon(cli, orig_tcon);
        TALLOC_FREE(frame);
        return status;
 }