From 9cfa2f6d7f7438d76b2aea242bc4b39e1ad9d4df Mon Sep 17 00:00:00 2001
From: Stephen Gallagher <sgallagh@redhat.com>
Date: Thu, 7 Oct 2010 19:51:26 -0400
Subject: [PATCH 2/3] Modify sysdb_add_group_member_send to accept users and groups

Previously, it assumed that all members were users. This changes
the interface so that either a user or a group can be specified.
---
 src/db/sysdb.h                           |   26 +++++++++-----
 src/db/sysdb_ops.c                       |   56 +++++++++++++++++++++--------
 src/providers/ldap/sdap_async_accounts.c |    2 +
 src/tests/sysdb-tests.c                  |    9 ++++-
 4 files changed, 66 insertions(+), 27 deletions(-)

diff --git a/src/db/sysdb.h b/src/db/sysdb.h
index 1c8d848b78726d23803846e8dce748be4c01bf4a..0ae26ac9ed943dc6ed73c3ba42f186ecc59b04e4 100644
--- a/src/db/sysdb.h
+++ b/src/db/sysdb.h
@@ -529,12 +529,18 @@ struct tevent_req *sysdb_store_group_send(TALLOC_CTX *mem_ctx,
                                           uint64_t cache_timeout);
 int sysdb_store_group_recv(struct tevent_req *req);
 
+enum sysdb_member_type {
+    SYSDB_MEMBER_USER,
+    SYSDB_MEMBER_GROUP
+};
+
 struct tevent_req *sysdb_add_group_member_send(TALLOC_CTX *mem_ctx,
                                                struct tevent_context *ev,
                                                struct sysdb_handle *handle,
                                                struct sss_domain_info *domain,
                                                const char *group,
-                                               const char *member);
+                                               const char *member,
+                                               enum sysdb_member_type type);
 int sysdb_add_group_member_recv(struct tevent_req *req);
 
 struct tevent_req *sysdb_remove_group_member_send(TALLOC_CTX *mem_ctx,
@@ -542,17 +548,19 @@ struct tevent_req *sysdb_remove_group_member_send(TALLOC_CTX *mem_ctx,
                                                   struct sysdb_handle *handle,
                                                   struct sss_domain_info *domain,
                                                   const char *group,
-                                                  const char *member);
+                                                  const char *member,
+                                                  enum sysdb_member_type type);
 int sysdb_remove_group_member_recv(struct tevent_req *req);
 
 
-struct tevent_req * sysdb_update_members_send(TALLOC_CTX *mem_ctx,
-                                              struct tevent_context *ev,
-                                              struct sysdb_handle *handle,
-                                              struct sss_domain_info *domain,
-                                              const char *user,
-                                              char **add_groups,
-                                              char **del_groups);
+struct tevent_req *sysdb_update_members_send(TALLOC_CTX *mem_ctx,
+                                             struct tevent_context *ev,
+                                             struct sysdb_handle *handle,
+                                             struct sss_domain_info *domain,
+                                             const char *member,
+                                             enum sysdb_member_type type,
+                                             char **add_groups,
+                                             char **del_groups);
 errno_t sysdb_update_members_recv(struct tevent_req *req);
 
 /* Password caching function.
diff --git a/src/db/sysdb_ops.c b/src/db/sysdb_ops.c
index 19f8176d58fa90944291dcb05125bbf86841e2c0..6a696b73ef61a393bd54c455c258f19e3ad67a4b 100644
--- a/src/db/sysdb_ops.c
+++ b/src/db/sysdb_ops.c
@@ -3142,11 +3142,12 @@ struct tevent_req *sysdb_add_group_member_send(TALLOC_CTX *mem_ctx,
                                                struct sysdb_handle *handle,
                                                struct sss_domain_info *domain,
                                                const char *group,
-                                               const char *user)
+                                               const char *member,
+                                               enum sysdb_member_type type)
 {
     struct tevent_req *req, *subreq;
     struct sysdb_op_state *state;
-    struct ldb_dn *group_dn, *user_dn;
+    struct ldb_dn *group_dn, *member_dn;
     int ret;
 
     req = tevent_req_create(mem_ctx, &state, struct sysdb_op_state);
@@ -3162,13 +3163,24 @@ struct tevent_req *sysdb_add_group_member_send(TALLOC_CTX *mem_ctx,
         ERROR_OUT(ret, ENOMEM, fail);
     }
 
-    user_dn = sysdb_user_dn(handle->ctx, state, domain->name, user);
-    if (!user_dn) {
+    if (type == SYSDB_MEMBER_USER) {
+        member_dn = sysdb_user_dn(handle->ctx, state,
+                                  domain->name,
+                                  member);
+    } else if (type == SYSDB_MEMBER_GROUP) {
+        member_dn = sysdb_group_dn(handle->ctx, state,
+                                   domain->name,
+                                   member);
+    } else {
+        ERROR_OUT(ret, EINVAL, fail);
+    }
+
+    if (!member_dn) {
         ERROR_OUT(ret, ENOMEM, fail);
     }
 
     subreq = sysdb_mod_group_member_send(state, ev, handle,
-                                         user_dn, group_dn,
+                                         member_dn, group_dn,
                                          SYSDB_MOD_ADD);
     if (!subreq) {
         ERROR_OUT(ret, ENOMEM, fail);
@@ -3216,11 +3228,12 @@ struct tevent_req *sysdb_remove_group_member_send(TALLOC_CTX *mem_ctx,
                                                   struct sysdb_handle *handle,
                                                   struct sss_domain_info *domain,
                                                   const char *group,
-                                                  const char *user)
+                                                  const char *member,
+                                                  enum sysdb_member_type type)
 {
     struct tevent_req *req, *subreq;
     struct sysdb_op_state *state;
-    struct ldb_dn *group_dn, *user_dn;
+    struct ldb_dn *group_dn, *member_dn;
     int ret;
 
     req = tevent_req_create(mem_ctx, &state, struct sysdb_op_state);
@@ -3236,13 +3249,20 @@ struct tevent_req *sysdb_remove_group_member_send(TALLOC_CTX *mem_ctx,
         ERROR_OUT(ret, ENOMEM, fail);
     }
 
-    user_dn = sysdb_user_dn(handle->ctx, state, domain->name, user);
-    if (!user_dn) {
+    if (type == SYSDB_MEMBER_USER) {
+        member_dn = sysdb_user_dn(handle->ctx, state, domain->name, member);
+    } else if (type == SYSDB_MEMBER_GROUP) {
+        member_dn = sysdb_group_dn(handle->ctx, state, domain->name, member);
+    } else {
+        ERROR_OUT(ret, EINVAL, fail);
+    }
+
+    if (!member_dn) {
         ERROR_OUT(ret, ENOMEM, fail);
     }
 
     subreq = sysdb_mod_group_member_send(state, ev, handle,
-                                         user_dn, group_dn,
+                                         member_dn, group_dn,
                                          SYSDB_MOD_DEL);
     if (!subreq) {
         ERROR_OUT(ret, ENOMEM, fail);
@@ -5242,11 +5262,13 @@ int sysdb_cache_auth_recv(struct tevent_req *req, time_t *expire_date,
 }
 
 struct sysdb_update_members_ctx {
-    char *user;
+    char *member;
     struct sss_domain_info *domain;
     struct tevent_context *ev;
     struct sysdb_handle *handle;
 
+    enum sysdb_member_type membertype;
+
     char **add_groups;
     int add_group_iter;
 
@@ -5274,7 +5296,8 @@ struct tevent_req *sysdb_update_members_send(TALLOC_CTX *mem_ctx,
                                              struct tevent_context *ev,
                                              struct sysdb_handle *handle,
                                              struct sss_domain_info *domain,
-                                             const char *user,
+                                             const char *member,
+                                             enum sysdb_member_type type,
                                              char **add_groups,
                                              char **del_groups)
 {
@@ -5287,14 +5310,15 @@ struct tevent_req *sysdb_update_members_send(TALLOC_CTX *mem_ctx,
         return NULL;
     }
 
-    state->user = talloc_strdup(state, user);
-    if (!state->user) {
+    state->member = talloc_strdup(state, member);
+    if (!state->member) {
         goto error;
     }
 
     state->domain = domain;
     state->ev = ev;
     state->handle = handle;
+    state->membertype = type;
 
     if (add_groups) {
         state->add_groups = dup_string_list(state, (const char**)add_groups);
@@ -5358,7 +5382,7 @@ sysdb_update_members_step(struct tevent_req *req)
                 state, state->ev, state->handle,
                 state->domain,
                 state->add_groups[state->add_group_iter],
-                state->user);
+                state->member, state->membertype);
         if (!subreq) {
             return EIO;
         }
@@ -5372,7 +5396,7 @@ sysdb_update_members_step(struct tevent_req *req)
                 state, state->ev,
                 state->handle, state->domain,
                 state->del_groups[state->del_group_iter],
-                state->user);
+                state->member, state->membertype);
         if (!subreq) {
             return EIO;
         }
diff --git a/src/providers/ldap/sdap_async_accounts.c b/src/providers/ldap/sdap_async_accounts.c
index 967697f7291aa2595e6e6f121de7c3bcd2da8be5..68cd589ba4d0f08242cf7242f53411e15e6be754 100644
--- a/src/providers/ldap/sdap_async_accounts.c
+++ b/src/providers/ldap/sdap_async_accounts.c
@@ -2088,6 +2088,7 @@ static void sdap_initgr_rfc2307_update_sysdb_groups(struct tevent_req *subreq)
 
     subreq = sysdb_update_members_send(state, state->ev, state->handle,
                                        state->dom, state->name,
+                                       SYSDB_MEMBER_USER,
                                        state->add_groups, state->del_groups);
     if (!subreq) {
         tevent_req_error(req, EIO);
@@ -2118,6 +2119,7 @@ sdap_initgr_rfc2307_update_sysdb_groups_step(struct tevent_req *subreq)
 
     updatereq = sysdb_update_members_send(state, state->ev, state->handle,
                                        state->dom, state->name,
+                                       SYSDB_MEMBER_USER,
                                        state->add_groups, state->del_groups);
     if (!updatereq) {
         tevent_req_error(req, EIO);
diff --git a/src/tests/sysdb-tests.c b/src/tests/sysdb-tests.c
index d4d031b98843b36e4ac8b5d94ee54f70b7dc0a80..24347014bb34a52c6e4b61f23df7d47e39d62f6d 100644
--- a/src/tests/sysdb-tests.c
+++ b/src/tests/sysdb-tests.c
@@ -831,7 +831,8 @@ static void test_add_group_member(struct tevent_req *req)
 
     subreq = sysdb_add_group_member_send(data, data->ev,
                                          data->handle, data->ctx->domain,
-                                         data->groupname, username);
+                                         data->groupname, username,
+                                         SYSDB_MEMBER_USER);
     if (!subreq) {
         test_return(data, ENOMEM);
     }
@@ -869,7 +870,8 @@ static void test_remove_group_member(struct tevent_req *req)
 
     subreq = sysdb_remove_group_member_send(data, data->ev,
                                             data->handle, data->ctx->domain,
-                                            data->groupname, username);
+                                            data->groupname, username,
+                                            SYSDB_MEMBER_USER);
     if (!subreq) {
         test_return(data, ENOMEM);
     }
@@ -3283,6 +3285,7 @@ static void test_sysdb_update_members_add(struct tevent_req *req)
 
     req = sysdb_update_members_send(data, data->ev, data->handle,
                                     data->ctx->domain, user,
+                                    SYSDB_MEMBER_USER,
                                     add_groups, NULL);
     talloc_free(add_groups);
     talloc_free(user);
@@ -3323,6 +3326,7 @@ static void test_sysdb_update_members_add_del(struct tevent_req *req)
 
     req = sysdb_update_members_send(data, data->ev, data->handle,
                                     data->ctx->domain, user,
+                                    SYSDB_MEMBER_USER,
                                     add_groups, del_groups);
     talloc_free(add_groups);
     talloc_free(del_groups);
@@ -3361,6 +3365,7 @@ static void test_sysdb_update_members_del(struct tevent_req *req)
 
     req = sysdb_update_members_send(data, data->ev, data->handle,
                                     data->ctx->domain, user,
+                                    SYSDB_MEMBER_USER,
                                     NULL, del_groups);
     talloc_free(del_groups);
     talloc_free(user);
-- 
1.7.2.3

