]> git.ipfire.org Git - thirdparty/samba.git/commitdiff
librpc/rpc: implement dcesrv_mgmt_inq_princ_name infrastructure
authorStefan Metzmacher <metze@samba.org>
Wed, 9 Aug 2023 11:26:31 +0000 (13:26 +0200)
committerAndrew Bartlett <abartlet@samba.org>
Tue, 17 Oct 2023 19:20:38 +0000 (19:20 +0000)
Signed-off-by: Stefan Metzmacher <metze@samba.org>
Reviewed-by: Andrew Bartlett <abartlet@samba.org>
librpc/rpc/dcesrv_core.c
librpc/rpc/dcesrv_core.h
librpc/rpc/dcesrv_mgmt.c

index 35fb7aa853dacaf1a249999b2501d166c55c6b96..8a2707912c5277ae71772ac6b10d835eafbfb6cf 100644 (file)
@@ -165,6 +165,54 @@ static struct dcesrv_call_state *dcesrv_find_fragmented_call(struct dcesrv_conne
        return NULL;
 }
 
+/*
+ * register a principal for an auth_type
+ *
+ * In order to get used in dcesrv_mgmt_inq_princ_name()
+ */
+_PUBLIC_ NTSTATUS dcesrv_auth_type_principal_register(struct dcesrv_context *dce_ctx,
+                                                     enum dcerpc_AuthType auth_type,
+                                                     const char *principal_name)
+{
+       const char *existing = NULL;
+       struct dcesrv_ctx_principal *p = NULL;
+
+       existing = dcesrv_auth_type_principal_find(dce_ctx, auth_type);
+       if (existing != NULL) {
+               DBG_ERR("auth_type[%u] already registered with principal_name[%s]\n",
+                       auth_type, existing);
+               return NT_STATUS_ALREADY_REGISTERED;
+       }
+
+       p = talloc_zero(dce_ctx, struct dcesrv_ctx_principal);
+       if (p == NULL) {
+               return NT_STATUS_NO_MEMORY;
+       }
+       p->auth_type = auth_type;
+       p->principal_name = talloc_strdup(p, principal_name);
+       if (p->principal_name == NULL) {
+               TALLOC_FREE(p);
+               return NT_STATUS_NO_MEMORY;
+       }
+
+       DLIST_ADD_END(dce_ctx->principal_list, p);
+       return NT_STATUS_OK;
+}
+
+_PUBLIC_ const char *dcesrv_auth_type_principal_find(struct dcesrv_context *dce_ctx,
+                                                    enum dcerpc_AuthType auth_type)
+{
+       struct dcesrv_ctx_principal *p = NULL;
+
+       for (p = dce_ctx->principal_list; p != NULL; p = p->next) {
+               if (p->auth_type == auth_type) {
+                       return p->principal_name;
+               }
+       }
+
+       return NULL;
+}
+
 /*
   register an interface on an endpoint
 
index aefb3f127322b4d637494d45592fce907c5c15c5..3ec9f32c93d8228e4e1ed66d1bdd4265d5c6af0e 100644 (file)
@@ -436,6 +436,16 @@ struct dcesrv_context {
                bool use_single_process;
        } *endpoint_list;
 
+       /*
+        * registered auth_type/principals
+        * for dcesrv_mgmt_inq_princ_name()
+        */
+       struct dcesrv_ctx_principal {
+               struct dcesrv_ctx_principal *next, *prev;
+               enum dcerpc_AuthType auth_type;
+               const char *principal_name;
+       } *principal_list;
+
        /* loadparm context to use for this connection */
        struct loadparm_context *lp_ctx;
 
@@ -460,6 +470,11 @@ struct dcesrv_critical_sizes {
        int sizeof_dcesrv_handle;
 };
 
+NTSTATUS dcesrv_auth_type_principal_register(struct dcesrv_context *dce_ctx,
+                                            enum dcerpc_AuthType auth_type,
+                                            const char *principal_name);
+const char *dcesrv_auth_type_principal_find(struct dcesrv_context *dce_ctx,
+                                           enum dcerpc_AuthType auth_type);
 NTSTATUS dcesrv_interface_register(struct dcesrv_context *dce_ctx,
                                   const char *ep_name,
                                   const char *ncacn_np_secondary_endpoint,
index ceb55e1507d5faae88287199f2b46a6e650f7c51..8f00e91930159d8a5ea2ee36b1e6d1c298e134f1 100644 (file)
@@ -137,7 +137,26 @@ static WERROR dcesrv_mgmt_stop_server_listening(struct dcesrv_call_state *dce_ca
 static WERROR dcesrv_mgmt_inq_princ_name(struct dcesrv_call_state *dce_call, TALLOC_CTX *mem_ctx,
                       struct mgmt_inq_princ_name *r)
 {
-       DCESRV_FAULT(DCERPC_FAULT_OP_RNG_ERROR);
+       const char *principal = NULL;
+
+       if (r->in.princ_name_size < 1) {
+               DCESRV_FAULT(DCERPC_FAULT_BAD_STUB_DATA);
+       }
+
+       r->out.princ_name = "";
+
+       principal = dcesrv_auth_type_principal_find(dce_call->conn->dce_ctx,
+                                                   r->in.authn_proto);
+       if (principal == NULL) {
+               return WERR_RPC_S_UNKNOWN_AUTHN_SERVICE;
+       }
+
+       if (strlen(principal) + 1 > r->in.princ_name_size) {
+               return WERR_INSUFFICIENT_BUFFER;
+       }
+
+       r->out.princ_name = principal;
+       return WERR_OK;
 }