dpward / rpms / sssd

Forked from rpms/sssd 3 years ago
Clone

Blame SOURCES/0075-RESP-Expose-DP-method-getAccountDomain-to-responders.patch

ced1f5
From cac78825ba2fcb2efcd7ff2e58b562b370bbb28c Mon Sep 17 00:00:00 2001
ced1f5
From: Jakub Hrozek <jhrozek@redhat.com>
ced1f5
Date: Mon, 30 Oct 2017 20:51:40 +0100
ced1f5
Subject: [PATCH 75/83] RESP: Expose DP method getAccountDomain() to responders
ced1f5
MIME-Version: 1.0
ced1f5
Content-Type: text/plain; charset=UTF-8
ced1f5
Content-Transfer-Encoding: 8bit
ced1f5
ced1f5
Adds a tevent request that calls the getAccountDomain DP method.
ced1f5
This request will be used by responders to locate an object's domain.
ced1f5
ced1f5
At the moment, only looking up UIDs and GIDs is supported.
ced1f5
ced1f5
Internally, until we switch to the rdp_ interface everywhere, this
ced1f5
interface hooks into the sss_dp_issue_request(). When we switch to
ced1f5
the rdp_ interface, we'll be able to provide a nicer method parameters
ced1f5
as well.
ced1f5
ced1f5
Reviewed-by: Pavel Březina <pbrezina@redhat.com>
ced1f5
Reviewed-by: Sumit Bose <sbose@redhat.com>
ced1f5
(cherry picked from commit 95fd82a4d7b50e64fed6906bc5345f271e8247d9)
ced1f5
---
ced1f5
 src/responder/common/responder.h             |  36 +++++++
ced1f5
 src/responder/common/responder_get_domains.c | 155 +++++++++++++++++++++++++++
ced1f5
 2 files changed, 191 insertions(+)
ced1f5
ced1f5
diff --git a/src/responder/common/responder.h b/src/responder/common/responder.h
ced1f5
index 9a57df558994c418d440eabf4a29f69c4a47faa5..9400e4b60d9fc77c23710174e4c00a83f6395985 100644
ced1f5
--- a/src/responder/common/responder.h
ced1f5
+++ b/src/responder/common/responder.h
ced1f5
@@ -375,6 +375,42 @@ struct tevent_req *sss_dp_get_domains_send(TALLOC_CTX *mem_ctx,
ced1f5
 
ced1f5
 errno_t sss_dp_get_domains_recv(struct tevent_req *req);
ced1f5
 
ced1f5
+/*
ced1f5
+ * Call a getAccountDomain request
ced1f5
+ *
ced1f5
+ * Only requests by ID are supported.
ced1f5
+ *
ced1f5
+ * @param   mem_ctx     Parent memory context
ced1f5
+ * @param   rctx        Responder context
ced1f5
+ * @param   domain      The SSSD domain we're querying. The response can
ced1f5
+ *                      be either NULL or come from any of domain's subdomains
ced1f5
+ *                      or domain itself
ced1f5
+ * @param   type        Either SSS_DP_USER or SSS_DP_GROUP, other types
ced1f5
+ *                      are not supported at the moment
ced1f5
+ * @param   opt_id      The ID number we're trying to locate
ced1f5
+ *
ced1f5
+ * @return  A tevent request or NULL if allocating the request fails.
ced1f5
+ */
ced1f5
+struct tevent_req *sss_dp_get_account_domain_send(TALLOC_CTX *mem_ctx,
ced1f5
+                                                  struct resp_ctx *rctx,
ced1f5
+                                                  struct sss_domain_info *domain,
ced1f5
+                                                  enum sss_dp_acct_type type,
ced1f5
+                                                  uint32_t opt_id);
ced1f5
+
ced1f5
+/* Receive a getAccountDomain request result
ced1f5
+ *
ced1f5
+ * @param   mem_ctx     The memory context that will own the contents of _domain
ced1f5
+ * @param   req         The request that had finished
ced1f5
+ * @para    _domain     Either NULL (the request did not match any domain) or
ced1f5
+ *                      a string that corresponds to either the input domain
ced1f5
+ *                      or any of its subdomains
ced1f5
+ *
ced1f5
+ * @return EOK on success, errno otherwise
ced1f5
+ */
ced1f5
+errno_t sss_dp_get_account_domain_recv(TALLOC_CTX *mem_ctx,
ced1f5
+                                       struct tevent_req *req,
ced1f5
+                                       char **_domain);
ced1f5
+
ced1f5
 errno_t schedule_get_domains_task(TALLOC_CTX *mem_ctx,
ced1f5
                                   struct tevent_context *ev,
ced1f5
                                   struct resp_ctx *rctx,
ced1f5
diff --git a/src/responder/common/responder_get_domains.c b/src/responder/common/responder_get_domains.c
ced1f5
index 4955af064040e03372e9a47fb264499d9a23b828..d69bce2300580beb42d3af8e66ff467db890f284 100644
ced1f5
--- a/src/responder/common/responder_get_domains.c
ced1f5
+++ b/src/responder/common/responder_get_domains.c
ced1f5
@@ -642,3 +642,158 @@ errno_t sss_parse_inp_recv(struct tevent_req *req, TALLOC_CTX *mem_ctx,
ced1f5
 
ced1f5
     return state->error;
ced1f5
 }
ced1f5
+
ced1f5
+/* ========== Get domain of an ccount ================= */
ced1f5
+struct sss_dp_get_account_domain_info {
ced1f5
+    struct sss_domain_info *dom;
ced1f5
+    enum sss_dp_acct_type type;
ced1f5
+    uint32_t opt_id;
ced1f5
+};
ced1f5
+
ced1f5
+static DBusMessage *sss_dp_get_account_domain_msg(void *pvt);
ced1f5
+
ced1f5
+struct tevent_req *sss_dp_get_account_domain_send(TALLOC_CTX *mem_ctx,
ced1f5
+                                                  struct resp_ctx *rctx,
ced1f5
+                                                  struct sss_domain_info *dom,
ced1f5
+                                                  enum sss_dp_acct_type type,
ced1f5
+                                                  uint32_t opt_id)
ced1f5
+{
ced1f5
+    struct tevent_req *req;
ced1f5
+    struct sss_dp_get_account_domain_info *info;
ced1f5
+    struct sss_dp_req_state *state;
ced1f5
+    char *key;
ced1f5
+    errno_t ret;
ced1f5
+
ced1f5
+    req = tevent_req_create(mem_ctx, &state, struct sss_dp_req_state);
ced1f5
+    if (!req) {
ced1f5
+        return NULL;
ced1f5
+    }
ced1f5
+
ced1f5
+    info = talloc_zero(state, struct sss_dp_get_account_domain_info);
ced1f5
+    if (info == NULL) {
ced1f5
+        ret = ENOMEM;
ced1f5
+        goto immediately;
ced1f5
+    }
ced1f5
+    info->type = type;
ced1f5
+    info->opt_id = opt_id;
ced1f5
+    info->dom = dom;
ced1f5
+
ced1f5
+    key = talloc_asprintf(state, "%d: %"SPRIuid"@%s", type, opt_id, dom->name);
ced1f5
+    if (key == NULL) {
ced1f5
+        ret = ENOMEM;
ced1f5
+        goto immediately;
ced1f5
+    }
ced1f5
+
ced1f5
+    ret = sss_dp_issue_request(state, rctx, key, dom,
ced1f5
+                               sss_dp_get_account_domain_msg,
ced1f5
+                               info, req);
ced1f5
+    talloc_free(key);
ced1f5
+    if (ret != EOK) {
ced1f5
+        DEBUG(SSSDBG_OP_FAILURE,
ced1f5
+              "Could not issue DP request [%d]: %s\n",
ced1f5
+              ret, sss_strerror(ret));
ced1f5
+        goto immediately;
ced1f5
+    }
ced1f5
+
ced1f5
+    return req;
ced1f5
+
ced1f5
+immediately:
ced1f5
+    if (ret == EOK) {
ced1f5
+        tevent_req_done(req);
ced1f5
+    } else {
ced1f5
+        tevent_req_error(req, ret);
ced1f5
+    }
ced1f5
+    tevent_req_post(req, rctx->ev);
ced1f5
+    return req;
ced1f5
+}
ced1f5
+
ced1f5
+static DBusMessage *
ced1f5
+sss_dp_get_account_domain_msg(void *pvt)
ced1f5
+{
ced1f5
+    DBusMessage *msg;
ced1f5
+    dbus_bool_t dbret;
ced1f5
+    struct sss_dp_get_account_domain_info *info;
ced1f5
+    uint32_t entry_type;
ced1f5
+    char *filter;
ced1f5
+
ced1f5
+    info = talloc_get_type(pvt, struct sss_dp_get_account_domain_info);
ced1f5
+
ced1f5
+    switch (info->type) {
ced1f5
+    case SSS_DP_USER:
ced1f5
+        entry_type = BE_REQ_USER;
ced1f5
+        break;
ced1f5
+    case SSS_DP_GROUP:
ced1f5
+        entry_type = BE_REQ_GROUP;
ced1f5
+        break;
ced1f5
+    case SSS_DP_USER_AND_GROUP:
ced1f5
+        entry_type = BE_REQ_USER_AND_GROUP;
ced1f5
+        break;
ced1f5
+    default:
ced1f5
+        DEBUG(SSSDBG_OP_FAILURE,
ced1f5
+              "Unsupported lookup type %X for this request\n", info->type);
ced1f5
+        return NULL;
ced1f5
+    }
ced1f5
+
ced1f5
+    filter = talloc_asprintf(info, "idnumber=%u", info->opt_id);
ced1f5
+    if (!filter) {
ced1f5
+        DEBUG(SSSDBG_CRIT_FAILURE, "Out of memory?!\n");
ced1f5
+        return NULL;
ced1f5
+    }
ced1f5
+
ced1f5
+    msg = dbus_message_new_method_call(NULL,
ced1f5
+                                       DP_PATH,
ced1f5
+                                       IFACE_DP,
ced1f5
+                                       IFACE_DP_GETACCOUNTDOMAIN);
ced1f5
+    if (msg == NULL) {
ced1f5
+        talloc_free(filter);
ced1f5
+        DEBUG(SSSDBG_CRIT_FAILURE, "Out of memory?!\n");
ced1f5
+        return NULL;
ced1f5
+    }
ced1f5
+
ced1f5
+    /* create the message */
ced1f5
+    DEBUG(SSSDBG_TRACE_FUNC,
ced1f5
+          "Creating request for [%s][%#x][%s][%s:-]\n",
ced1f5
+          info->dom->name, entry_type, be_req2str(entry_type), filter);
ced1f5
+
ced1f5
+    dbret = dbus_message_append_args(msg,
ced1f5
+                                     DBUS_TYPE_UINT32, &entry_type,
ced1f5
+                                     DBUS_TYPE_STRING, &filter,
ced1f5
+                                     DBUS_TYPE_INVALID);
ced1f5
+    talloc_free(filter);
ced1f5
+    if (!dbret) {
ced1f5
+        DEBUG(SSSDBG_CRIT_FAILURE, "Failed to build message\n");
ced1f5
+        dbus_message_unref(msg);
ced1f5
+        return NULL;
ced1f5
+    }
ced1f5
+
ced1f5
+    return msg;
ced1f5
+}
ced1f5
+
ced1f5
+errno_t sss_dp_get_account_domain_recv(TALLOC_CTX *mem_ctx,
ced1f5
+                                       struct tevent_req *req,
ced1f5
+                                       char **_domain)
ced1f5
+{
ced1f5
+    errno_t ret;
ced1f5
+    dbus_uint16_t err_maj;
ced1f5
+    dbus_uint32_t err_min;
ced1f5
+    char *msg;
ced1f5
+
ced1f5
+    ret = sss_dp_req_recv(mem_ctx, req, &err_maj, &err_min, &msg;;
ced1f5
+    if (ret != EOK) {
ced1f5
+        DEBUG(SSSDBG_OP_FAILURE,
ced1f5
+              "Could not get account info [%d]: %s\n",
ced1f5
+              ret, sss_strerror(ret));
ced1f5
+        return ret;
ced1f5
+    }
ced1f5
+
ced1f5
+    if (err_maj != DP_ERR_OK) {
ced1f5
+        DEBUG(SSSDBG_OP_FAILURE,
ced1f5
+              "Data Provider Error: %u, %u\n",
ced1f5
+              (unsigned int)err_maj, (unsigned int)err_min);
ced1f5
+        talloc_free(msg);
ced1f5
+        return err_min ? err_min : EIO;
ced1f5
+    }
ced1f5
+
ced1f5
+    *_domain = msg;
ced1f5
+    return EOK;
ced1f5
+}
ced1f5
-- 
ced1f5
2.14.3
ced1f5