|
|
dc8c34 |
From eb10a9e242264fe94098743e048bfbba4fc9a422 Mon Sep 17 00:00:00 2001
|
|
|
dc8c34 |
From: Noriko Hosoi <nhosoi@totoro.usersys.redhat.com>
|
|
|
dc8c34 |
Date: Tue, 13 Nov 2012 11:21:26 -0800
|
|
|
dc8c34 |
Subject: [PATCH 12/16] Trac Ticket #500 - Newly created users with
|
|
|
dc8c34 |
organizationalPerson objectClass fails to sync from
|
|
|
dc8c34 |
AD to DS with missing attribute error
|
|
|
dc8c34 |
|
|
|
dc8c34 |
https://fedorahosted.org/389/ticket/500
|
|
|
dc8c34 |
|
|
|
dc8c34 |
Bug description: Posix Account objectclass requires homeDirectory,
|
|
|
dc8c34 |
uidNumber, and gidNumber. When an AD entry has just some of these
|
|
|
dc8c34 |
attributes or other allow-to-have attributes, i.e., loginShell or
|
|
|
dc8c34 |
gecos, the entry is incompletely converted to Posix Account entry
|
|
|
dc8c34 |
and fails to be added due to the missing attribute error.
|
|
|
dc8c34 |
|
|
|
dc8c34 |
Fix description: Before transforming the AD entry to the DS posix
|
|
|
dc8c34 |
account entry, check the required attributes first. If any of the
|
|
|
dc8c34 |
above 3 attributes is missing, all of the posix account related
|
|
|
dc8c34 |
attributes are dropped and added to the DS as a non-posix account
|
|
|
dc8c34 |
entry. If the PLUGIN log level is set, this type of message is
|
|
|
dc8c34 |
logged in the error log.
|
|
|
dc8c34 |
[] posix-winsync - AD entry CN=<CN>,OU=<OU>,DC=<DC>,DC=<COM> does
|
|
|
dc8c34 |
not have required attribute uidNumber for posixAccount objectclass.
|
|
|
dc8c34 |
(cherry picked from commit 19e49e69124ff19530a584f90808aa652a4c686f)
|
|
|
dc8c34 |
(cherry picked from commit f95bc254e3019727123068af5612058be05fb6be)
|
|
|
dc8c34 |
---
|
|
|
dc8c34 |
ldap/servers/plugins/posix-winsync/posix-winsync.c | 129 ++++++++++++++-------
|
|
|
dc8c34 |
ldap/servers/slapd/mapping_tree.c | 2 +-
|
|
|
dc8c34 |
2 files changed, 91 insertions(+), 40 deletions(-)
|
|
|
dc8c34 |
|
|
|
dc8c34 |
diff --git a/ldap/servers/plugins/posix-winsync/posix-winsync.c b/ldap/servers/plugins/posix-winsync/posix-winsync.c
|
|
|
dc8c34 |
index aa292c3..92a3a79 100644
|
|
|
dc8c34 |
--- a/ldap/servers/plugins/posix-winsync/posix-winsync.c
|
|
|
dc8c34 |
+++ b/ldap/servers/plugins/posix-winsync/posix-winsync.c
|
|
|
dc8c34 |
@@ -86,14 +86,17 @@ typedef struct _windows_attr_map
|
|
|
dc8c34 |
{
|
|
|
dc8c34 |
char *windows_attribute_name;
|
|
|
dc8c34 |
char *ldap_attribute_name;
|
|
|
dc8c34 |
+ int isMUST; /* schema: required attribute */
|
|
|
dc8c34 |
} windows_attribute_map;
|
|
|
dc8c34 |
|
|
|
dc8c34 |
-static windows_attribute_map user_attribute_map[] = { { "unixHomeDirectory", "homeDirectory" },
|
|
|
dc8c34 |
- { "loginShell", "loginShell" },
|
|
|
dc8c34 |
- { "uidNumber", "uidNumber" },
|
|
|
dc8c34 |
- { "gidNumber", "gidNumber" },
|
|
|
dc8c34 |
- { "gecos", "gecos" },
|
|
|
dc8c34 |
- { NULL, NULL } };
|
|
|
dc8c34 |
+static windows_attribute_map user_attribute_map[] = {
|
|
|
dc8c34 |
+ { "unixHomeDirectory", "homeDirectory", 1 },
|
|
|
dc8c34 |
+ { "loginShell", "loginShell", 0 },
|
|
|
dc8c34 |
+ { "uidNumber", "uidNumber", 1 },
|
|
|
dc8c34 |
+ { "gidNumber", "gidNumber", 1 },
|
|
|
dc8c34 |
+ { "gecos", "gecos", 0 },
|
|
|
dc8c34 |
+ { NULL, NULL, 0 }
|
|
|
dc8c34 |
+};
|
|
|
dc8c34 |
|
|
|
dc8c34 |
static windows_attribute_map user_mssfu_attribute_map[] =
|
|
|
dc8c34 |
{ { "msSFU30homedirectory", "homeDirectory" },
|
|
|
dc8c34 |
@@ -751,7 +754,9 @@ posix_winsync_pre_ds_mod_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
int is_present_local = 0;
|
|
|
dc8c34 |
int do_modify_local = 0;
|
|
|
dc8c34 |
int rc;
|
|
|
dc8c34 |
+ int i;
|
|
|
dc8c34 |
windows_attribute_map *attr_map = user_attribute_map;
|
|
|
dc8c34 |
+ PRBool posixval = PR_TRUE;
|
|
|
dc8c34 |
|
|
|
dc8c34 |
if (posix_winsync_config_get_msSFUSchema())
|
|
|
dc8c34 |
attr_map = user_mssfu_attribute_map;
|
|
|
dc8c34 |
@@ -759,15 +764,33 @@ posix_winsync_pre_ds_mod_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
"--> _pre_ds_mod_user_cb -- begin\n");
|
|
|
dc8c34 |
|
|
|
dc8c34 |
+ /* check all of the required attributes are in the ad_entry:
|
|
|
dc8c34 |
+ * MUST (cn $ uid $ uidNumber $ gidNumber $ homeDirectory).
|
|
|
dc8c34 |
+ * If any of the required attributes are missing, drop them before adding
|
|
|
dc8c34 |
+ * the entry to the DS. */
|
|
|
dc8c34 |
+ for (i = 0; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
+ Slapi_Attr *pa_attr;
|
|
|
dc8c34 |
+ if (attr_map[i].isMUST &&
|
|
|
dc8c34 |
+ slapi_entry_attr_find(ad_entry,
|
|
|
dc8c34 |
+ attr_map[i].windows_attribute_name,
|
|
|
dc8c34 |
+ &pa_attr)) {
|
|
|
dc8c34 |
+ /* required attribute does not exist */
|
|
|
dc8c34 |
+ posixval = PR_FALSE;
|
|
|
dc8c34 |
+ slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
+ "AD entry %s does not have required attribute %s for posixAccount objectclass.\n",
|
|
|
dc8c34 |
+ slapi_entry_get_dn_const(ad_entry),
|
|
|
dc8c34 |
+ attr_map[i].ldap_attribute_name);
|
|
|
dc8c34 |
+ }
|
|
|
dc8c34 |
+ }
|
|
|
dc8c34 |
+
|
|
|
dc8c34 |
/* add objectclass: posixAccount, uidnumber ,gidnumber ,homeDirectory, loginshell */
|
|
|
dc8c34 |
/* in the ad to ds case we have no changelog, so we have to compare the entries */
|
|
|
dc8c34 |
for (rc = slapi_entry_first_attr(ad_entry, &attr); rc == 0;
|
|
|
dc8c34 |
rc = slapi_entry_next_attr(ad_entry, attr, &attr)) {
|
|
|
dc8c34 |
char *type = NULL;
|
|
|
dc8c34 |
- size_t i = 0;
|
|
|
dc8c34 |
|
|
|
dc8c34 |
slapi_attr_get_type(attr, &type);
|
|
|
dc8c34 |
- for (; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
+ for (i = 0; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
if (0 == slapi_attr_type_cmp(type, attr_map[i].windows_attribute_name,
|
|
|
dc8c34 |
SLAPI_TYPE_CMP_SUBTYPE)) {
|
|
|
dc8c34 |
Slapi_Attr *local_attr = NULL;
|
|
|
dc8c34 |
@@ -779,7 +802,10 @@ posix_winsync_pre_ds_mod_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
slapi_entry_attr_find(ds_entry, local_type, &local_attr);
|
|
|
dc8c34 |
is_present_local = (NULL == local_attr) ? 0 : 1;
|
|
|
dc8c34 |
if (is_present_local) {
|
|
|
dc8c34 |
+ /* DS entry has the posix attrs.
|
|
|
dc8c34 |
+ * I.e., it is a posix account*/
|
|
|
dc8c34 |
int values_equal = 0;
|
|
|
dc8c34 |
+ posixval = PR_TRUE;
|
|
|
dc8c34 |
values_equal = attr_compare_equal(attr, local_attr);
|
|
|
dc8c34 |
if (!values_equal) {
|
|
|
dc8c34 |
slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
@@ -791,8 +817,8 @@ posix_winsync_pre_ds_mod_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
valueset_get_valuearray(vs));
|
|
|
dc8c34 |
*do_modify = 1;
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
- } else {
|
|
|
dc8c34 |
-
|
|
|
dc8c34 |
+ } else if (posixval) {
|
|
|
dc8c34 |
+ /* only if AD provides the all necessary attributes */
|
|
|
dc8c34 |
slapi_mods_add_mod_values(smods, LDAP_MOD_ADD, local_type,
|
|
|
dc8c34 |
valueset_get_valuearray(vs));
|
|
|
dc8c34 |
*do_modify = do_modify_local = 1;
|
|
|
dc8c34 |
@@ -804,10 +830,11 @@ posix_winsync_pre_ds_mod_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
- "<-- _pre_ds_mod_user_cb present %d modify %d\n", is_present_local,
|
|
|
dc8c34 |
- do_modify_local);
|
|
|
dc8c34 |
+ "<-- _pre_ds_mod_user_cb present %d modify %d isPosixaccount %s\n",
|
|
|
dc8c34 |
+ is_present_local, do_modify_local,
|
|
|
dc8c34 |
+ posixval?"yes":"no");
|
|
|
dc8c34 |
|
|
|
dc8c34 |
- if (!is_present_local && do_modify_local) {
|
|
|
dc8c34 |
+ if (!is_present_local && do_modify_local && posixval) {
|
|
|
dc8c34 |
Slapi_Attr *oc_attr = NULL;
|
|
|
dc8c34 |
Slapi_Value *voc = slapi_value_new();
|
|
|
dc8c34 |
|
|
|
dc8c34 |
@@ -988,8 +1015,9 @@ posix_winsync_pre_ds_add_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
{
|
|
|
dc8c34 |
Slapi_Attr *attr = NULL;
|
|
|
dc8c34 |
char *type = NULL;
|
|
|
dc8c34 |
- PRBool posixval = PR_FALSE;
|
|
|
dc8c34 |
+ PRBool posixval = PR_TRUE;
|
|
|
dc8c34 |
windows_attribute_map *attr_map = user_attribute_map;
|
|
|
dc8c34 |
+ int i = 0;
|
|
|
dc8c34 |
|
|
|
dc8c34 |
if (posix_winsync_config_get_msSFUSchema())
|
|
|
dc8c34 |
attr_map = user_mssfu_attribute_map;
|
|
|
dc8c34 |
@@ -998,42 +1026,65 @@ posix_winsync_pre_ds_add_user_cb(void *cbdata, const Slapi_Entry *rawentry, Slap
|
|
|
dc8c34 |
slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
"--> _pre_ds_add_user_cb -- begin\n");
|
|
|
dc8c34 |
|
|
|
dc8c34 |
- for (slapi_entry_first_attr(ad_entry, &attr); attr; slapi_entry_next_attr(ad_entry, attr, &attr)) {
|
|
|
dc8c34 |
- size_t i = 0;
|
|
|
dc8c34 |
-
|
|
|
dc8c34 |
- slapi_attr_get_type(attr, &type);
|
|
|
dc8c34 |
- if (!type) {
|
|
|
dc8c34 |
- continue;
|
|
|
dc8c34 |
+ /* check all of the required attributes are in the ad_entry:
|
|
|
dc8c34 |
+ * MUST (cn $ uid $ uidNumber $ gidNumber $ homeDirectory).
|
|
|
dc8c34 |
+ * If any of the required attributes are missing, drop them before adding
|
|
|
dc8c34 |
+ * the entry to the DS. */
|
|
|
dc8c34 |
+ for (i = 0; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
+ Slapi_Attr *pa_attr;
|
|
|
dc8c34 |
+ if (attr_map[i].isMUST &&
|
|
|
dc8c34 |
+ slapi_entry_attr_find(ad_entry,
|
|
|
dc8c34 |
+ attr_map[i].windows_attribute_name,
|
|
|
dc8c34 |
+ &pa_attr)) {
|
|
|
dc8c34 |
+ /* required attribute does not exist */
|
|
|
dc8c34 |
+ posixval = PR_FALSE;
|
|
|
dc8c34 |
+ slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
+ "AD entry %s does not have required attribute %s for posixAccount objectclass.\n",
|
|
|
dc8c34 |
+ slapi_entry_get_dn_const(ad_entry),
|
|
|
dc8c34 |
+ attr_map[i].ldap_attribute_name);
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
+ }
|
|
|
dc8c34 |
|
|
|
dc8c34 |
- slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name, "--> _pre_ds_add_user_cb -- "
|
|
|
dc8c34 |
- "look for [%s] to new entry [%s]\n", type, slapi_entry_get_dn_const(ds_entry));
|
|
|
dc8c34 |
- for (; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
- if (slapi_attr_type_cmp(attr_map[i].windows_attribute_name, type,
|
|
|
dc8c34 |
- SLAPI_TYPE_CMP_SUBTYPE) == 0) {
|
|
|
dc8c34 |
- Slapi_ValueSet *svs = NULL;
|
|
|
dc8c34 |
- slapi_attr_get_valueset(attr, &svs);
|
|
|
dc8c34 |
- slapi_entry_add_valueset(ds_entry, attr_map[i].ldap_attribute_name, svs);
|
|
|
dc8c34 |
- slapi_valueset_free(svs);
|
|
|
dc8c34 |
+ /* converts the AD attributes to DS posix attribute if all the posix
|
|
|
dc8c34 |
+ * required attributes are available */
|
|
|
dc8c34 |
+ if (posixval) {
|
|
|
dc8c34 |
+ int rc;
|
|
|
dc8c34 |
+ for (slapi_entry_first_attr(ad_entry, &attr); attr;
|
|
|
dc8c34 |
+ slapi_entry_next_attr(ad_entry, attr, &attr)) {
|
|
|
dc8c34 |
|
|
|
dc8c34 |
- slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
- "--> _pre_ds_add_user_cb -- "
|
|
|
dc8c34 |
- "adding val for [%s] to new entry [%s]\n", type,
|
|
|
dc8c34 |
- slapi_entry_get_dn_const(ds_entry));
|
|
|
dc8c34 |
- posixval = PR_TRUE;
|
|
|
dc8c34 |
+ slapi_attr_get_type(attr, &type);
|
|
|
dc8c34 |
+ if (!type) {
|
|
|
dc8c34 |
+ continue;
|
|
|
dc8c34 |
+ }
|
|
|
dc8c34 |
+
|
|
|
dc8c34 |
+ slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
+ "--> _pre_ds_add_user_cb -- "
|
|
|
dc8c34 |
+ "look for [%s] to new entry [%s]\n",
|
|
|
dc8c34 |
+ type, slapi_entry_get_dn_const(ds_entry));
|
|
|
dc8c34 |
+ for (i = 0; attr_map[i].windows_attribute_name != NULL; i++) {
|
|
|
dc8c34 |
+ if (slapi_attr_type_cmp(attr_map[i].windows_attribute_name,
|
|
|
dc8c34 |
+ type, SLAPI_TYPE_CMP_SUBTYPE) == 0) {
|
|
|
dc8c34 |
+ Slapi_ValueSet *svs = NULL;
|
|
|
dc8c34 |
+ slapi_attr_get_valueset(attr, &svs);
|
|
|
dc8c34 |
+ slapi_entry_add_valueset(ds_entry,
|
|
|
dc8c34 |
+ attr_map[i].ldap_attribute_name, svs);
|
|
|
dc8c34 |
+ slapi_valueset_free(svs);
|
|
|
dc8c34 |
+
|
|
|
dc8c34 |
+ slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
+ "--> _pre_ds_add_user_cb -- "
|
|
|
dc8c34 |
+ "adding val for [%s] to new entry [%s]\n",
|
|
|
dc8c34 |
+ type, slapi_entry_get_dn_const(ds_entry));
|
|
|
dc8c34 |
+ }
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
- }
|
|
|
dc8c34 |
- if (posixval) {
|
|
|
dc8c34 |
- int rc;
|
|
|
dc8c34 |
rc = slapi_entry_add_string(ds_entry, "objectClass", "posixAccount");
|
|
|
dc8c34 |
rc |= slapi_entry_add_string(ds_entry, "objectClass", "shadowAccount");
|
|
|
dc8c34 |
rc |= slapi_entry_add_string(ds_entry, "objectClass", "inetUser");
|
|
|
dc8c34 |
- if (rc != 0)
|
|
|
dc8c34 |
+ if (rc != 0) {
|
|
|
dc8c34 |
slapi_log_error(SLAPI_LOG_PLUGIN, posix_winsync_plugin_name,
|
|
|
dc8c34 |
"<-- _pre_ds_add_user_cb -- adding objectclass for new entry failed %d\n",
|
|
|
dc8c34 |
rc);
|
|
|
dc8c34 |
- else {
|
|
|
dc8c34 |
+ } else {
|
|
|
dc8c34 |
if (posix_winsync_config_get_mapNestedGrouping()) {
|
|
|
dc8c34 |
memberUidLock();
|
|
|
dc8c34 |
addUserToGroupMembership(ds_entry);
|
|
|
dc8c34 |
diff --git a/ldap/servers/slapd/mapping_tree.c b/ldap/servers/slapd/mapping_tree.c
|
|
|
dc8c34 |
index e8e414f..da8e4f3 100644
|
|
|
dc8c34 |
--- a/ldap/servers/slapd/mapping_tree.c
|
|
|
dc8c34 |
+++ b/ldap/servers/slapd/mapping_tree.c
|
|
|
dc8c34 |
@@ -2451,7 +2451,7 @@ int slapi_mapping_tree_select_and_check(Slapi_PBlock *pb,char *newdn, Slapi_Back
|
|
|
dc8c34 |
{
|
|
|
dc8c34 |
ret = LDAP_AFFECTS_MULTIPLE_DSAS;
|
|
|
dc8c34 |
PR_snprintf(errorbuf, BUFSIZ,
|
|
|
dc8c34 |
- "Cannot move entries accross backends\n");
|
|
|
dc8c34 |
+ "Cannot move entries across backends\n");
|
|
|
dc8c34 |
goto unlock_and_return;
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
}
|
|
|
dc8c34 |
--
|
|
|
dc8c34 |
1.7.11.7
|
|
|
dc8c34 |
|