]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
s3:rpc_client: Add cli_rpc_pipe_reopen_np_noauth()
authorStefan Metzmacher <metze@samba.org>
Wed, 12 Feb 2025 11:35:20 +0000 (12:35 +0100)
committerJule Anger <janger@samba.org>
Thu, 12 Jun 2025 11:27:15 +0000 (11:27 +0000)
BUG: https://bugzilla.samba.org/show_bug.cgi?id=15680

Signed-off-by: Stefan Metzmacher <metze@samba.org>
Reviewed-by: Andreas Schneider <asn@samba.org>
(cherry picked from commit d2ac6221db48b93581d7ce48d31f8851c88b77bc)
(cherry picked from commit 60dc107d2a6154bf3254218e10b91c2a91ee88d9)

source3/rpc_client/cli_pipe.c
source3/rpc_client/cli_pipe.h

index 4c70c406dbdeb70901ee22a38b030f269c1501e2..46cd8390a28e3b7dcc2549025d918437bdc6e6ae 100644 (file)
@@ -4254,6 +4254,94 @@ NTSTATUS cli_rpc_pipe_open_noauth(struct cli_state *cli,
                                                  presult);
 }
 
+/****************************************************************************
+ * Reopen a connection with the same parameters.
+ *
+ * This is useful if we try an RPC function the server doesn't know about and
+ * disconnects us.
+ ****************************************************************************/
+NTSTATUS cli_rpc_pipe_reopen_np_noauth(struct rpc_pipe_client *rpccli)
+{
+       TALLOC_CTX *frame = talloc_stackframe();
+       enum dcerpc_transport_t transport;
+       struct cli_state *cli = NULL;
+       struct rpc_client_association *assoc = NULL;
+       struct rpc_client_connection *new_conn = NULL;
+       struct pipe_auth_data *new_auth = NULL;
+       NTSTATUS status;
+
+       if (rpccli->assoc == NULL) {
+               TALLOC_FREE(frame);
+               return NT_STATUS_INVALID_PARAMETER_MIX;
+       }
+
+       transport = dcerpc_binding_get_transport(rpccli->assoc->binding);
+       if (transport != NCACN_NP) {
+               TALLOC_FREE(frame);
+               return NT_STATUS_INVALID_PARAMETER_MIX;
+       }
+
+       if (rpccli->np_cli == NULL) {
+               TALLOC_FREE(frame);
+               return NT_STATUS_INVALID_PARAMETER_MIX;
+       }
+       cli = rpccli->np_cli;
+
+       /*
+        * close the old connection
+        */
+       TALLOC_FREE(rpccli->conn);
+
+       /*
+        * Free the auth context
+        */
+       TALLOC_FREE(rpccli->auth);
+
+       /*
+        * Reset the association
+        */
+       assoc = talloc_move(frame, &rpccli->assoc);
+       status = dcerpc_binding_set_assoc_group_id(assoc->binding, 0);
+       if (!NT_STATUS_IS_OK(status)) {
+               return status;
+       }
+       assoc->features.negotiated = 0;
+       if (assoc->features.client != 0) {
+               assoc->features.negotiation_done = false;
+       }
+       assoc->next_call_id = 0;
+
+       status = rpc_client_connection_np(cli,
+                                         assoc,
+                                         &new_conn);
+       if (!NT_STATUS_IS_OK(status)) {
+               TALLOC_FREE(frame);
+               return status;
+       }
+
+       rpccli->assoc = talloc_move(rpccli, &assoc);
+       rpccli->conn = talloc_move(rpccli, &new_conn);
+
+       /* rpc_pipe_bind_send should allocate an id... */
+       rpccli->pres_context_id = UINT16_MAX;
+       rpccli->verified_pcontext = false;
+
+       status = rpccli_anon_bind_data(rpccli, &new_auth);
+       if (!NT_STATUS_IS_OK(status)) {
+               TALLOC_FREE(frame);
+               return status;
+       }
+
+       status = rpc_pipe_bind(rpccli, new_auth);
+       if (!NT_STATUS_IS_OK(status)) {
+               TALLOC_FREE(frame);
+               return status;
+       }
+
+       TALLOC_FREE(frame);
+       return NT_STATUS_OK;
+}
+
 /****************************************************************************
  Open a named pipe to an SMB server and bind using the mech specified
 
index d6e472afcf6db7650eb6ed433eade4e641608e25..e90dd3b944671fd26f740e2a12dc994c79a657d4 100644 (file)
@@ -81,6 +81,8 @@ NTSTATUS cli_rpc_pipe_open_noauth(struct cli_state *cli,
                                  const struct ndr_interface_table *table,
                                  struct rpc_pipe_client **presult);
 
+NTSTATUS cli_rpc_pipe_reopen_np_noauth(struct rpc_pipe_client *rpccli);
+
 NTSTATUS cli_rpc_pipe_client_prepare_alter(struct rpc_pipe_client *p,
                                           bool new_auth_context,
                                           const struct ndr_interface_table *table,