Blob Blame Raw
From b63830b142053f99bfe954d4be5a2b0f68ce3a93 Mon Sep 17 00:00:00 2001
From: Jakub Hrozek <jhrozek@redhat.com>
Date: Fri, 22 Feb 2013 11:01:38 +0100
Subject: [PATCH 1/4] Provide a be_get_account_info_send function

In order to resolve group names in the simple access provider we need to
contact the Data Provider in a generic fashion from the access provider.
We can't call any particular implementation (like sdap_generic_send())
because we have no idea what kind of provider is configured as the
id_provider.

This patch splits introduces the be_file_account_request() function into
the data_provider_be module and makes it public.

A future patch should make the be_get_account_info function use the
be_get_account_info_send function.
---
 src/providers/data_provider_be.c | 153 ++++++++++++++++++++++++++++++++++-----
 src/providers/dp_backend.h       |  15 ++++
 2 files changed, 149 insertions(+), 19 deletions(-)

diff --git a/src/providers/data_provider_be.c b/src/providers/data_provider_be.c
index b261bf8d456829a513ec352c8290d2011bd3526a..f85a04d09b5b41b17be611c333324f7207242979 100644
--- a/src/providers/data_provider_be.c
+++ b/src/providers/data_provider_be.c
@@ -717,6 +717,34 @@ static errno_t be_initgroups_prereq(struct be_req *be_req)
 }
 
 static errno_t
+be_file_account_request(struct be_req *be_req, struct be_acct_req *ar)
+{
+    errno_t ret;
+    struct be_ctx *be_ctx = be_req->be_ctx;
+
+    be_req->req_data = ar;
+
+    /* see if we need a pre request call, only done for initgroups for now */
+    if ((ar->entry_type & 0xFF) == BE_REQ_INITGROUPS) {
+        ret = be_initgroups_prereq(be_req);
+        if (ret) {
+            DEBUG(SSSDBG_CRIT_FAILURE, ("Prerequest failed"));
+            return ret;
+        }
+    }
+
+    /* process request */
+    ret = be_file_request(be_ctx, be_req,
+                          be_ctx->bet_info[BET_ID].bet_ops->handler);
+    if (ret != EOK) {
+        DEBUG(SSSDBG_CRIT_FAILURE, ("Failed to file request"));
+        return ret;
+    }
+
+    return EOK;
+}
+
+static errno_t
 split_name_extended(TALLOC_CTX *mem_ctx,
                     const char *filter,
                     char **name,
@@ -742,6 +770,110 @@ split_name_extended(TALLOC_CTX *mem_ctx,
     return EOK;
 }
 
+static void
+be_get_account_info_done(struct be_req *be_req,
+                         int dp_err, int dp_ret,
+                         const char *errstr);
+
+struct be_get_account_info_state {
+    int err_maj;
+    int err_min;
+    const char *err_msg;
+};
+
+struct tevent_req *
+be_get_account_info_send(TALLOC_CTX *mem_ctx,
+                         struct tevent_context *ev,
+                         struct be_client *becli,
+                         struct be_ctx *be_ctx,
+                         struct be_acct_req *ar)
+{
+    struct tevent_req *req;
+    struct be_get_account_info_state *state;
+    struct be_req *be_req;
+    errno_t ret;
+
+    req = tevent_req_create(mem_ctx, &state,
+                            struct be_get_account_info_state);
+    if (!req) return NULL;
+
+    be_req = talloc_zero(mem_ctx, struct be_req);
+    if (be_req == NULL) {
+        ret = ENOMEM;
+        goto done;
+    }
+
+    be_req->becli = becli;
+    be_req->be_ctx = be_ctx;
+    be_req->fn = be_get_account_info_done;
+    be_req->pvt = req;
+
+    ret = be_file_account_request(be_req, ar);
+    if (ret != EOK) {
+        goto done;
+    }
+
+    return req;
+
+done:
+    tevent_req_error(req, ret);
+    tevent_req_post(req, ev);
+    return req;
+}
+
+static void
+be_get_account_info_done(struct be_req *be_req,
+                         int dp_err, int dp_ret,
+                         const char *errstr)
+{
+    struct tevent_req *req;
+    struct be_get_account_info_state *state;
+
+    req = talloc_get_type(be_req->pvt, struct tevent_req);
+    state = tevent_req_data(req, struct be_get_account_info_state);
+
+    state->err_maj = dp_err;
+    state->err_min = dp_ret;
+    if (errstr) {
+        state->err_msg = talloc_strdup(state, errstr);
+        if (state->err_msg == NULL) {
+            talloc_free(be_req);
+            tevent_req_error(req, ENOMEM);
+            return;
+        }
+    }
+
+    talloc_free(be_req);
+    tevent_req_done(req);
+}
+
+errno_t be_get_account_info_recv(struct tevent_req *req,
+                                 TALLOC_CTX *mem_ctx,
+                                 int *_err_maj,
+                                 int *_err_min,
+                                 const char **_err_msg)
+{
+    struct be_get_account_info_state *state;
+
+    state = tevent_req_data(req, struct be_get_account_info_state);
+
+    TEVENT_REQ_RETURN_ON_ERROR(req);
+
+    if (_err_maj) {
+        *_err_maj = state->err_maj;
+    }
+
+    if (_err_min) {
+        *_err_min = state->err_min;
+    }
+
+    if (_err_msg) {
+        *_err_msg = talloc_steal(mem_ctx, state->err_msg);
+    }
+
+    return EOK;
+}
+
 static int be_get_account_info(DBusMessage *message, struct sbus_connection *conn)
 {
     struct be_acct_req *req;
@@ -845,8 +977,6 @@ static int be_get_account_info(DBusMessage *message, struct sbus_connection *con
         goto done;
     }
 
-    be_req->req_data = req;
-
     if ((attr_type != BE_ATTR_CORE) &&
         (attr_type != BE_ATTR_MEM) &&
         (attr_type != BE_ATTR_ALL)) {
@@ -893,26 +1023,11 @@ static int be_get_account_info(DBusMessage *message, struct sbus_connection *con
         goto done;
     }
 
-    /* see if we need a pre request call, only done for initgroups for now */
-    if ((type & 0xFF) == BE_REQ_INITGROUPS) {
-        ret = be_initgroups_prereq(be_req);
-        if (ret) {
-            err_maj = DP_ERR_FATAL;
-            err_min = ret;
-            err_msg = "Prerequest failed";
-            goto done;
-        }
-    }
-
-    /* process request */
-
-    ret = be_file_request(becli->bectx->bet_info[BET_ID].pvt_bet_data,
-                          be_req,
-                          becli->bectx->bet_info[BET_ID].bet_ops->handler);
+    ret = be_file_account_request(be_req, req);
     if (ret != EOK) {
         err_maj = DP_ERR_FATAL;
         err_min = ret;
-        err_msg = "Failed to file request";
+        err_msg = "Cannot file account request";
         goto done;
     }
 
diff --git a/src/providers/dp_backend.h b/src/providers/dp_backend.h
index 58a9b7490df8aab06a2a15f8c0fed9ac5ed33600..743b6f4ffe73fe9ec7404218184a7133aba054c6 100644
--- a/src/providers/dp_backend.h
+++ b/src/providers/dp_backend.h
@@ -258,4 +258,19 @@ int be_fo_run_callbacks_at_next_request(struct be_ctx *ctx,
                                         const char *service_name);
 
 void reset_fo(struct be_ctx *be_ctx);
+
+/* Request account information */
+struct tevent_req *
+be_get_account_info_send(TALLOC_CTX *mem_ctx,
+                         struct tevent_context *ev,
+                         struct be_client *becli,
+                         struct be_ctx *be_ctx,
+                         struct be_acct_req *ar);
+
+errno_t be_get_account_info_recv(struct tevent_req *req,
+                                 TALLOC_CTX *mem_ctx,
+                                 int *_err_maj,
+                                 int *_err_min,
+                                 const char **_err_msg);
+
 #endif /* __DP_BACKEND_H___ */
-- 
1.8.1.4