/* Copyright (C) 2000,2001,2002 Manuel Amador (Rudd-O)
This file is part of Directory administrator.
Directory administrator is free software; you can redistribute it
and/or modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2.1 of
the License, or (at your option) any later version.
Directory administrator is distributed in the hope that it will be
useful, but WITHOUT ANY WARRANTY; without even the implied warranty
of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License along
with Directory administrator; if not, send e-mail to amador@alomega.com
*/
#include <glib.h>
#include <gnome.h>
#include "appsupport.h"
#include "appglobals.h"
#include "groups.h"
#include "users.h"
#include "charset.h"
#include "mkntpwd.h"
#ifdef FREEBSD
#include <des.h>
#else
#include <crypt.h>
#endif /* FREEBSD */
#include <sys/time.h>
#include <unistd.h>
#include "md5.h"
//standard attributes to check on creation/modification
gchar *attrs2chk[] = { "uid", "uidnumber", "gidnumber", "givenname",
"initials", "sn", "cn", "homedirectory",
"loginshell", "mail", "maillocaladdress",
"mailroutingaddress", "mailhost",
"gecos", "userPassword", "authPassword", "shadowLastChange",
"shadowmin", "shadowmax", "shadowwarning", "shadowinactive",
"shadowexpire", "title", "physicaldeliveryofficename",
"ou", "l",
"telephonenumber", "facsimiletelephonenumber", "o", "homephone",
"mobile", "smbHome", "homeDrive", "profilePath", "scriptPath", "lmPassword",
"ntPassword", "rid", "objectclass", "host","employeeNumber",
NULL
};
gchar *posixlist[] = {
"uid", "uidnumber", "gidnumber", "homedirectory",
"loginshell", "gecos", "userPassword", "authPassword",
"shadowLastChange", "shadowmin", "shadowmax", "shadowwarning",
"shadowinactive", "shadowexpire", NULL
};
gchar *sambalist[] = {
"smbHome", "homeDrive", "profilePath", "scriptPath", "lmPassword",
"ntPassword", "rid", NULL
};
gchar *maillist[] = {
"maillocaladdress", "mailroutingaddress", "mailhost", NULL
};
gchar *accountlist[] = {
"host", NULL
};
gchar *personlist[] = { "givenname", "initials", "sn", "cn",
"mail", "title", "physicaldeliveryofficename", "ou", "l",
"telephonenumber", "facsimiletelephonenumber", "o", "homephone",
"mobile","employeenumber", NULL
};
gchar *handled_objectclasses[] = {
/*"person",*/"organizationalPerson","inetOrgPerson","account","posixAccount",
"shadowAccount","sambaAccount","inetLocalMailRecipient","top", NULL
};
/* This is from 'pam_ldap.c' by Luke Howard, <lukeh@padl.com>
Used without explicit permission. */
/* i64c - convert an integer to a radix 64 character */
static int
i64c (int i)
{
const char *base64 =
"./01234567890ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz";
if (i < 0)
i = 0;
else if (i > 63)
i = 63;
return base64[i];
}
/* This is from 'pam_ldap.c' by Luke Howard, <lukeh@padl.com>
Used with permission granted in the 'GNU Library General Public License'.
THANKS, Luke! */
static char *
_get_salt (char salt[3])
{
int i;
int j;
srand (time (NULL));
for (j = 0; j < 2; j++)
{
i = rand () % 3;
switch (i)
{
case 0:
i = (rand () % (57 - 46)) + 46;
break;
case 1:
i = (rand () % (90 - 65)) + 65;
break;
case 2:
i = (rand () % (122 - 97)) + 97;
break;
}
salt[j] = i;
}
salt[2] = '\0';
return (salt);
}
static char *
_get_md5_salt (char saltbuf[16])
{
md5_state_t state;
md5_byte_t digest[16];
struct timeval tv;
int i;
md5_init (&state);
gettimeofday (&tv, NULL);
md5_append (&state, (unsigned char *) &tv, sizeof (tv));
i = getpid ();
md5_append (&state, (unsigned char *) &i, sizeof (i));
i = clock ();
md5_append (&state, (unsigned char *) &i, sizeof (i));
md5_append (&state, (unsigned char *) saltbuf, sizeof (saltbuf));
md5_finish (&state, digest);
strcpy (saltbuf, "$1$");
for (i = 0; i < 8; i++)
saltbuf[i + 3] = i64c (digest[i] & 0x3f);
saltbuf[i + 3] = '\0';
return saltbuf;
}
diradmin_user *
diradmin_user_new (gchar * dn, GList * allowed)
{
diradmin_user *conn = g_new (diradmin_user, 1);
conn->diradmin_user_data = NULL;
conn->diradmin_user_allowedservers = NULL;
conn->diradmin_user_objectclasses = NULL;
conn->diradmin_user_data =
pairs_list_set_attribute (conn->diradmin_user_data, "dn", dn);
diradmin_user_revokeallservers (conn);
diradmin_user_set_allowedservers (conn, allowed);
return conn;
}
diradmin_user *
diradmin_user_duplicate (diradmin_user * tobeduped)
{
diradmin_user *conn = g_new (diradmin_user, 1);
conn->diradmin_user_data = NULL;
conn->diradmin_user_allowedservers = NULL;
conn->diradmin_user_objectclasses = NULL;
conn->diradmin_user_data =
pairs_list_duplicate (tobeduped->diradmin_user_data);
diradmin_user_set_allowedservers (conn,
tobeduped->diradmin_user_allowedservers);
diradmin_user_set_objectclasses (conn,
tobeduped->diradmin_user_objectclasses);
conn->allserversallowed = tobeduped->allserversallowed;
return conn;
}
//these three functions receive pointers to pointers as arguments for the datalist
void
diradmin_user_destroy (diradmin_user * todestroy)
{
if (todestroy)
{
pairs_list_destroy (todestroy->diradmin_user_data);
diradmin_user_set_allowedservers (todestroy, NULL);
diradmin_user_set_objectclasses (todestroy, NULL);
g_free (todestroy);
}
}
gchar *
diradmin_user_get_attribute (diradmin_user * conn, gchar * attr)
{
// g_print("getting attribute "); g_print(attr);
// g_print(" to "); g_print(to); g_print("\n");
g_assert (conn);
g_assert (attr);
return pairs_list_get_attribute (conn->diradmin_user_data, attr);
}
void
diradmin_user_set_attribute (diradmin_user * conn, gchar * attr, gchar * to)
{
int i;
g_assert (conn);
g_assert (attr);
// g_print("setting attribute "); g_print(attr);
// g_print(" to "); g_print(to); g_print("\n");
conn->diradmin_user_data =
pairs_list_set_attribute (conn->diradmin_user_data, attr, to);
diradmin_user_add_objectclass (conn, "top");
for (i = 0; posixlist[i] != NULL; i++)
if (g_strcasecmp (posixlist[i], attr) == 0)
{
diradmin_user_add_objectclass (conn, "posixAccount");
diradmin_user_add_objectclass (conn, "shadowAccount");
}
for (i = 0; sambalist[i] != NULL; i++)
if (g_strcasecmp (sambalist[i], attr) == 0)
{
diradmin_user_add_objectclass (conn, "sambaAccount");
}
for (i = 0; maillist[i] != NULL; i++)
if (g_strcasecmp (maillist[i], attr) == 0)
{
diradmin_user_add_objectclass (conn, "inetLocalMailRecipient");
}
for (i = 0; accountlist[i] != NULL; i++)
if (g_strcasecmp (accountlist[i], attr) == 0)
{
diradmin_user_add_objectclass (conn, "account");
}
for (i = 0; personlist[i] != NULL; i++)
if (g_strcasecmp (personlist[i], attr) == 0)
{
// diradmin_user_add_objectclass (conn, "person");
diradmin_user_add_objectclass (conn, "organizationalPerson");
diradmin_user_add_objectclass (conn, "inetOrgPerson");
}
}
void
diradmin_user_tighten_objectclasses (diradmin_user * u)
{
int isneeded, i;
/* para cada lista de atributos
si el user no tiene ninguno
remover esos object classes*/
isneeded = FALSE;
for (i = 0; posixlist[i] != NULL; i++)
if (diradmin_user_get_attribute (u, posixlist[i]))
isneeded = TRUE;
if (isneeded == FALSE)
{
// g_print("\nTighten objectclasses: removing account classes");
diradmin_user_remove_objectclass (u, "posixAccount");
diradmin_user_remove_objectclass (u, "shadowAccount");
}
isneeded = FALSE;
for (i = 0; sambalist[i] != NULL; i++)
if (diradmin_user_get_attribute (u, sambalist[i]))
isneeded = TRUE;
if (isneeded == FALSE)
{
// g_print("\nTighten objectclasses: removing samba classes");
diradmin_user_remove_objectclass (u, "sambaAccount");
}
isneeded = FALSE;
for (i = 0; personlist[i] != NULL; i++)
if (diradmin_user_get_attribute (u, personlist[i]))
isneeded = TRUE;
if (isneeded == FALSE)
{
//g_print("\nTighten objectclasses: removing person classes");
//diradmin_user_remove_objectclass (u, "person");
diradmin_user_remove_objectclass (u, "organizationalPerson");
diradmin_user_remove_objectclass (u, "inetOrgPerson");
}
isneeded = FALSE;
for (i = 0; maillist[i] != NULL; i++)
if (diradmin_user_get_attribute (u, maillist[i]))
isneeded = TRUE;
if (isneeded == FALSE)
{
//g_print("\nTighten objectclasses: removing mail classes");
diradmin_user_remove_objectclass (u, "inetLocalMailRecipient");
}
}
void
diradmin_user_remove_attribute (diradmin_user * conn, gchar * attr)
{
g_assert (conn);
g_assert (attr);
conn->diradmin_user_data =
pairs_list_remove_attribute (conn->diradmin_user_data, attr);
}
void
diradmin_user_set_password (diradmin_user * conn, gchar * to)
{
char seed[2], buf[96],buf2[96], saltbuf[16], md5crypt[64];
g_print ("set password called with password: %s\n", to);
if (preferences.passwordcrypttype == CRYPT)
{
snprintf (buf, sizeof buf, "{crypt}%s", crypt (to, _get_salt (seed)));
snprintf (buf2, sizeof buf2, "CRYPT$%s", crypt (to, _get_salt (seed)));
}
else if (preferences.passwordcrypttype == MD5)
{
// Due to the way that md5 crypt (shadow) format works, we want
// the prepend to be {crypt} instead of {md5}
strncpy (md5crypt, to, sizeof (md5crypt) - 1);
_get_md5_salt (saltbuf);
g_print (crypt (md5crypt, saltbuf));
snprintf (buf, sizeof buf, "{crypt}%s", crypt (md5crypt, saltbuf));
snprintf (buf2, sizeof buf2, "MD5$%s", crypt (md5crypt, saltbuf));
}
else
{
snprintf (buf, sizeof buf, "%s", to);
snprintf (buf2, sizeof buf2, "%s", to);
}
if (diradmin_user_has_objectclass(conn,"sambaaccount"))
{
char hash[17], hexstr[33];
mklmhash(to, hash);
to_hexstr(hash, hexstr);
diradmin_user_set_attribute (conn, "lmPassword", hexstr);
mknthash(to, hash);
to_hexstr(hash, hexstr);
diradmin_user_set_attribute (conn, "ntPassword", hexstr);
}
diradmin_user_set_attribute (conn, "userPassword", buf);
if (preferences.rfc2307bis == TRUE)
diradmin_user_set_attribute (conn, "authPassword", buf2);
//this line of code is taken from pam_ldap.c
snprintf (buf, sizeof buf, "%ld", time (NULL) / (60 * 60 * 24));
diradmin_user_set_attribute (conn, "shadowLastChange", buf);
g_print ("set password set attribute: %s\n",
diradmin_user_get_attribute (conn, "userPassword"));
}
diradmin_user *
diradmin_user_new_from_ldap (connection_profile * usethisone, char *userdn)
{
//conn should already be connected, or else undefined behaviour!!!
diradmin_user *user = NULL;
int ldap_errors;
GList* ocs = NULL;
LDAP *h;
LDAPMessage *searchresults = NULL;
LDAPMessage *entry = NULL;
char **value_collection = NULL;
gchar *attribute;
BerElement *attributehandler;
gchar *localed_attr;
int i = 0;
int ocnum = 0;
g_print ("\nFetching %s from directory\n", userdn);
//check 4 connection
h = connection_profile_get_ldap_handler (usethisone);
g_assert (h);
//look data up
ldap_errors =
ldap_search_s (h, userdn, LDAP_SCOPE_BASE, "(objectclass=*)", NULL, 0,
&searchresults);
if (ldap_errors)
{
//any error?
g_print ("LDAP error while creating a diradmin_user structure for ");
g_print (userdn);
g_print (": ");
g_print (ldap_err2string (ldap_errors));
g_print ("\n");
//ldap_msgfree (searchresults);
if (ldap_errors == LDAP_SERVER_DOWN) {
connection_profile_invalidate(usethisone);
}
return NULL;
}
else
{
//rock on dude, let's go ahead
user = diradmin_user_new (userdn, NULL);
//get only first entry
entry = ldap_first_entry (h, searchresults);
// loop thru attribute values
attribute = ldap_first_attribute (h, entry, &attributehandler);
g_assert (attribute);
while (attribute)
{
value_collection = ldap_get_values (h, entry, attribute);
g_assert (value_collection);
if (g_strcasecmp (attribute, "host") == 0)
{
for (i = 0; value_collection[i]; i++)
{
//g_print ("\nServer: %s", value_collection[i]);
if (g_strcasecmp(value_collection[i],"*")==0)
diradmin_user_allowallservers(user);
else
diradmin_user_add_allowedserver (user, value_collection[i]);
}
}
else if (g_strcasecmp (attribute, "objectclass") == 0)
{
for (i = 0; value_collection[i]; i++)
{
/*diradmin_user_dump(user);*/
diradmin_user_set_objectclasses (user,NULL);
/* changed to bring only the USEFUL object classes that I know about */
for (ocnum=0;handled_objectclasses[ocnum];ocnum++)
if (g_strcasecmp(value_collection[i],handled_objectclasses[ocnum])==0)
{
//g_print ("\nRecognized object class: %s", value_collection[i]);
ocs = g_list_append(ocs,g_strdup(value_collection[i]));
// COMMENTED to track bug diradmin_user_add_objectclass (user, value_collection[i]);
}
/* end change */
}
}
else
{
g_assert (value_collection[0]);
//detect if gecos
if (g_strcasecmp (attribute, "gecos") == 0)
localed_attr = convert_from_ascii(value_collection[0]);
else
localed_attr = convert_from_utf8(value_collection[0]);
diradmin_user_set_attribute (user, attribute,
localed_attr);
g_free (localed_attr);
//g_print ("\n%s: %s", attribute, value_collection[0]);
}
ldap_value_free (value_collection);
attribute = ldap_next_attribute (h, entry, attributehandler);
}
ldap_msgfree (searchresults);
}
diradmin_user_set_objectclasses (user, ocs);
/*g_print ("\n\n************STRAIGHT FROM THE DIRECTORY***********:");
diradmin_user_dump(user);
g_print ("\n\n************END FROM THE DIRECTORY***********:");*/
return (user);
}
GList *
diradmin_user_get_allowedservers (diradmin_user * conn)
{
//return a reference to the allowedservers list. shouldnt be manipulated outside.
return g_list_first (conn->diradmin_user_allowedservers);
}
void
diradmin_user_add_allowedserver (diradmin_user * conn, gchar * allowedserver)
{
diradmin_user_remove_allowedserver (conn, allowedserver);
conn->diradmin_user_allowedservers =
g_list_append (conn->diradmin_user_allowedservers,
g_strdup (allowedserver));
//g_print ("\nAdding object class Account\n");
diradmin_user_add_objectclass (conn, "account");
conn->allserversallowed =FALSE;
}
void
diradmin_user_revokeallservers(diradmin_user*c) {
//g_print("Se revocaron todos los servers");
diradmin_user_set_allowedservers(c,NULL);
diradmin_user_remove_objectclass(c,"account");
c->allserversallowed = FALSE;
}
void
diradmin_user_allowallservers (diradmin_user * conn)
{
diradmin_user_revokeallservers(conn);
diradmin_user_add_objectclass(conn,"account");
conn->allserversallowed=TRUE;
}
gboolean
diradmin_user_has_allservers (diradmin_user * conn) {
return conn->allserversallowed;
}
void
diradmin_user_remove_allowedserver (diradmin_user * conn, gchar
* allowedserver)
{
GList *iterator = NULL;
iterator = g_list_find_custom (conn->diradmin_user_allowedservers,
allowedserver, (GCompareFunc) g_strcasecmp);
if (iterator)
{
conn->diradmin_user_allowedservers =
g_list_remove_link (conn->diradmin_user_allowedservers, iterator);
g_free (iterator->data);
g_list_free_1 (iterator);
}
if (g_list_length (conn->diradmin_user_allowedservers) == 0)
g_print ("\nRemoving object class Account\n");
diradmin_user_remove_objectclass (conn, "account");
}
gboolean
diradmin_user_has_allowedserver (diradmin_user * conn, gchar * allowedserver)
{
gchar *data;
GList *iterator = NULL;
iterator = g_list_first (conn->diradmin_user_allowedservers);
while (iterator)
{
data = iterator->data;
if (g_strcasecmp (allowedserver, iterator->data) == 0)
{
return (TRUE);
}
iterator = g_list_next (iterator);
}
return (FALSE);
}
void
diradmin_user_set_allowedservers (diradmin_user * conn, GList
* allowedserverlist)
{
//removes all allowedservers in the list. that means frees its allocated storage.
GList *newallowedservers = NULL;
GList *allowedservers = NULL;
//free the old allowedservers list
allowedservers = g_list_first (diradmin_user_get_allowedservers (conn));
while (allowedservers)
{
g_free (allowedservers->data);
allowedservers = g_list_next (allowedservers);
}
g_list_free (g_list_first (diradmin_user_get_allowedservers (conn)));
//make a copy of the passed allowedservers list into newallowedservers
allowedservers = g_list_first (allowedserverlist);
while (allowedservers)
{
newallowedservers =
g_list_append (newallowedservers, g_strdup (allowedservers->data));
allowedservers = g_list_next (allowedservers);
}
conn->diradmin_user_allowedservers = newallowedservers;
}
//objectclasses
GList *
diradmin_user_get_objectclasses (diradmin_user * conn)
{
//return a reference to the allowedservers list. shouldnt be manipulated outside.
return g_list_first (conn->diradmin_user_objectclasses);
}
void
diradmin_user_add_objectclass (diradmin_user * conn, gchar * allowedserver)
{
g_assert(conn);
g_assert(allowedserver);
diradmin_user_remove_objectclass (conn, allowedserver);
conn->diradmin_user_objectclasses =
g_list_append (conn->diradmin_user_objectclasses,
g_strdup (allowedserver));
//g_print("\nAdd objectclass: adding %s class", allowedserver);
}
void
diradmin_user_remove_objectclass (diradmin_user * conn, gchar * allowedserver)
{
GList *iterator = NULL;
iterator = g_list_find_custom (conn->diradmin_user_objectclasses,
allowedserver, (GCompareFunc) g_strcasecmp);
if (iterator)
{
conn->diradmin_user_objectclasses =
g_list_remove_link (conn->diradmin_user_objectclasses, iterator);
g_free (iterator->data);
g_list_free_1 (iterator);
}
}
gboolean
diradmin_user_has_objectclass (diradmin_user * conn, gchar * allowedserver)
{
gchar *data;
GList *iterator = NULL;
iterator = g_list_first (conn->diradmin_user_objectclasses);
while (iterator)
{
data = iterator->data;
if (g_strcasecmp (allowedserver, iterator->data) == 0)
{
return (TRUE);
}
iterator = g_list_next (iterator);
}
return (FALSE);
}
void
diradmin_user_set_objectclasses (diradmin_user * conn, GList
* allowedserverlist)
{
//removes all allowedservers in the list. that means frees its allocated storage.
GList *newallowedservers = NULL;
GList *allowedservers = NULL;
//free the old allowedservers list
allowedservers = g_list_first (diradmin_user_get_objectclasses (conn));
while (allowedservers)
{
g_free (allowedservers->data);
allowedservers = g_list_next (allowedservers);
}
g_list_free (g_list_first (conn->diradmin_user_objectclasses));
//make a copy of the passed allowedservers list into newallowedservers
allowedservers = g_list_first (allowedserverlist);
while (allowedservers)
{
newallowedservers =
g_list_append (newallowedservers, g_strdup (allowedservers->data));
allowedservers = g_list_next (allowedservers);
}
conn->diradmin_user_objectclasses = newallowedservers;
}
void
diradmin_user_dump (diradmin_user * conn)
{
GList *objectclasses = NULL;
g_print("\nDump for user %s:", diradmin_user_get_attribute (conn,"dn"));
objectclasses = g_list_first(diradmin_user_get_objectclasses (conn));
while (objectclasses)
{
g_print("\n Object class: %s" ,(char*)objectclasses->data);
objectclasses = g_list_next (objectclasses);
}
}
ldaptransaction *
diradmin_user_generate_ldapdiff (diradmin_user * oldone,
diradmin_user * newone)
{
ldaptransaction *t;
gchar **vals = NULL;
GList *l = NULL;
gint acnt = 0;
gchar *oldattr = NULL;
gchar *newattr = NULL;
// gboolean samba_user = 0;
gboolean holder;
diradmin_user*m; gchar*n;
gboolean ispassword;
g_assert (oldone);
g_assert (newone);
/*g_print ("\n\nOld user dump:");
diradmin_user_dump(oldone);
g_print ("\n\nNew user dump:");
diradmin_user_dump(newone);*/
diradmin_user_tighten_objectclasses (newone);
// samba_user = diradmin_user_has_objectclass (newone, "sambaaccount");
t = ldaptransaction_new ();
// veremos con objectclasses. poner los que no, quitar los que si
acnt = 0;
l = diradmin_user_get_objectclasses (oldone);
vals = g_new0 (gchar *, g_list_length(l) + 1);
for (l = g_list_first(l); l; l = g_list_next (l))
if (diradmin_user_has_objectclass (newone, l->data) == FALSE)
{
vals[acnt] = g_strdup (l->data); acnt++;
}
if (acnt)
ldaptransaction_delete (t, "objectclass", vals);
else
g_free(vals);
acnt = 0;
l = diradmin_user_get_objectclasses (newone);
vals = g_new0 (gchar *, g_list_length(l) + 11);
for (l = g_list_first(l); l; l = g_list_next (l)) {
//g_print ("\nChecking if we need to add %s (%d)... ",(char*)l->data,g_list_length(l));
m = oldone;
n = l->data;
holder = diradmin_user_has_objectclass (m,n);
if (holder == FALSE)
{
//g_print ("YES");
vals[acnt] = g_strdup (l->data); acnt++;
}
}
if (acnt)
ldaptransaction_add (t, "objectclass", vals);
else
g_free(vals);
// veremos con servers. poner los que no, quitar los que si
if (diradmin_user_has_allservers(newone))
if (!diradmin_user_has_allservers(oldone)) {
vals = g_new0 (gchar *, 2);
vals[0] = g_strdup ("*");
ldaptransaction_add (t, "host", vals); }
if (diradmin_user_has_allservers(oldone))
if (!diradmin_user_has_allservers(newone)) {
vals = g_new0 (gchar *, 2);
vals[0] = g_strdup ("*");
ldaptransaction_delete (t, "host", vals);}
acnt = 0;
l = diradmin_user_get_allowedservers (oldone);
vals = g_new0 (gchar *, g_list_length(l) + 1);
for (l = g_list_first(l); l; l = g_list_next (l))
if (diradmin_user_has_allowedserver (newone, l->data) == FALSE)
{
vals[acnt] = g_strdup (l->data); acnt++;
}
if (acnt)
ldaptransaction_delete (t, "host", vals);
else
g_free(vals);
acnt = 0;
l = diradmin_user_get_allowedservers (newone);
vals = g_new0 (gchar *, g_list_length(l) + 1);
for (l = g_list_first(l); l; l = g_list_next (l))
if (diradmin_user_has_allowedserver (oldone, l->data) == FALSE)
{
vals[acnt] = g_strdup (l->data); acnt++;
}
if (acnt)
ldaptransaction_add (t, "host", vals);
else
g_free(vals);
//chequeo de los atributos
for (acnt = 0; attrs2chk[acnt]; acnt++)
{
oldattr = diradmin_user_get_attribute (oldone, attrs2chk[acnt]);
newattr = diradmin_user_get_attribute (newone, attrs2chk[acnt]);
ispassword = g_strcasecmp (attrs2chk[acnt], "userPassword") == 0 || g_strcasecmp (attrs2chk[acnt], "authPassword") == 0 || g_strcasecmp (attrs2chk[acnt], "ntPassword") == 0 || g_strcasecmp (attrs2chk[acnt], "lmPassword") == 0;
// if any attribute isn't empty
if (oldattr || newattr) {
//g_print ("\nattribute %s:\n old %s\n new %s",
// attrs2chk[acnt], oldattr, newattr);
// if the attribute isn't a password or the date of last change, and the old attribute existed but the new one doesn't
if (!ispassword && g_strcasecmp (attrs2chk[acnt], "shadowLastChange") != 0 && oldattr != NULL && newattr == NULL) {
vals = g_new0 (gchar *, 2);
if (g_strcasecmp (attrs2chk[acnt], "gecos") == 0) {
vals[0] = convert_to_ascii(oldattr);
}
else {
vals[0] = convert_to_utf8(oldattr);
}
ldaptransaction_delete (t, attrs2chk[acnt], vals);
}
// else if the old attribute didn't exist but was added
else if (oldattr == NULL && newattr != NULL)
{
vals = g_new0 (gchar *, 2);
//if it's the gecos, please convert to ascii first
if (g_strcasecmp (attrs2chk[acnt], "gecos") == 0) {
vals[0] = convert_to_ascii(newattr);
}
else {
vals[0] = convert_to_utf8(newattr);
}
ldaptransaction_replace (t, attrs2chk[acnt], vals);
}
// else if both existed but are different (excluding the case that the attribute we're checking is the DN)
else if (oldattr && newattr && strcmp (oldattr, newattr) != 0 && strcmp (oldattr, "dn") != 0)
{
vals = g_new0 (gchar *, 2);
//if it's the gecos, please convert to ascii first
if (g_strcasecmp (attrs2chk[acnt], "gecos") == 0) {
vals[0] = convert_to_ascii(newattr);
}
else {
vals[0] = convert_to_utf8(newattr);
}
ldaptransaction_replace (t, attrs2chk[acnt], vals);
}
}
}
return (t);
}
diradmin_user *
create_user_struct_from_dialogbox (connection_profile * conn,
GtkWidget * dialogbox, gchar * dn)
{
diradmin_user *newuser;
gint iterator;
gchar *uid = NULL;
gchar *uidnumber = NULL;
gchar *gidnumber = NULL;
gchar *givenname = NULL;
gchar *sn = NULL;
gchar *cn = NULL;
gchar *homedirectory = NULL;
gchar *loginshell = NULL;
gchar *userpassword = NULL;
gchar *gecos = NULL;
gchar *mail = NULL;
gchar *mailhost = NULL;
gchar *mailroutingaddress = NULL;
gchar *shadowmin = NULL;
gchar *shadowmax = NULL;
gchar *shadowwarning = NULL;
gchar *smbHome = NULL;
gchar *homeDrive = NULL;
gchar *profilePath = NULL;
gchar *scriptPath = NULL;
gchar *lmPassword = NULL;
gchar *ntPassword = NULL;
gchar *shadowinactive = NULL;
char buf[32];
time_t shadowexpiretime;
GtkCList *allowedservers = NULL;
gchar *allowedserver = NULL;
allowedservers = (GtkCList *) lookup_widget (dialogbox, "allowedservers");
uid = gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "uid")));
uidnumber =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "uidnumber")));
gidnumber =
cn_to_gidnumber (conn,
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "gidnumber"))));
sn = gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "sn")));
cn = gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "cn")));
givenname =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "givenname")));
homedirectory =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "homedirectory")));
loginshell =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "loginshell")));
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "loginshell")));
mail = gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "mail")));
mailhost =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "mailhost")));
mailroutingaddress =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "mailroutingaddress")));
userpassword =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "userpassword")));
lmPassword =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "userpassword")));
ntPassword =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "userpassword")));
gecos = gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "cn")));
newuser = diradmin_user_new (dn, NULL);
diradmin_user_set_attribute (newuser, "uid", uid);
diradmin_user_set_attribute (newuser, "uidnumber", uidnumber);
diradmin_user_set_attribute (newuser, "gidnumber", gidnumber);
diradmin_user_set_attribute (newuser, "givenname", givenname);
diradmin_user_set_attribute (newuser, "sn", sn);
diradmin_user_set_attribute (newuser, "cn", cn);
diradmin_user_set_attribute (newuser, "homedirectory", homedirectory);
diradmin_user_set_attribute (newuser, "loginshell", loginshell);
diradmin_user_set_attribute (newuser, "gecos", gecos);
diradmin_user_set_attribute (newuser, "mail", mail);
g_free (gidnumber); //mallocced by the function
//shadow password setting attributes
shadowmin =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "shadowmin")));
shadowmax =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "shadowmax")));
shadowwarning =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "shadowwarning")));
shadowinactive =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "shadowinactive")));
diradmin_user_set_attribute (newuser, "shadowmin", shadowmin);
diradmin_user_set_attribute (newuser, "shadowmax", shadowmax);
diradmin_user_set_attribute (newuser, "shadowwarning", shadowwarning);
diradmin_user_set_attribute (newuser, "shadowinactive", shadowinactive);
//organizationalperson
diradmin_user_set_attribute (newuser, "initials",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox,
"initials"))));
diradmin_user_set_attribute (newuser, "title",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "title"))));
diradmin_user_set_attribute (newuser, "physicaldeliveryofficename",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox,
"physicaldeliveryofficename"))));
diradmin_user_set_attribute (newuser, "ou",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "ou"))));
diradmin_user_set_attribute (newuser, "l",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "l"))));
diradmin_user_set_attribute (newuser, "employeenumber",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "employeenumber"))));
diradmin_user_set_attribute (newuser, "telephonenumber",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox,
"telephonenumber"))));
diradmin_user_set_attribute (newuser, "facsimiletelephonenumber",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox,
"facsimiletelephonenumber"))));
diradmin_user_set_attribute (newuser, "o",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "o"))));
diradmin_user_set_attribute (newuser, "homephone",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox,
"homephone"))));
diradmin_user_set_attribute (newuser, "mobile",
gtk_entry_get_text (GTK_ENTRY
(lookup_widget
(dialogbox, "mobile"))));
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "shadowexpirecheck"))->active)
{
shadowexpiretime =
gnome_date_edit_get_date ((GnomeDateEdit *)
lookup_widget (dialogbox, "shadowexpire"));
snprintf (buf, sizeof buf, "%ld", shadowexpiretime / (60 * 60 * 24 ) + 1);
diradmin_user_set_attribute (newuser, "shadowexpire", buf);
}
//g_print ("constatando servers logontoallservers");
if (!GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "logontoallservers"))->active)
{
//g_print("\n****Se desactiv todos los servers para este user\n");
diradmin_user_revokeallservers (newuser);
}
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "logontoallservers"))->active)
{
//g_print("\n****Se activ todos los servers para este user\n");
diradmin_user_allowallservers (newuser);
}
else {
for (iterator = 0; iterator < allowedservers->rows; iterator++)
{
gtk_clist_get_text (allowedservers, iterator, 0, &allowedserver);
diradmin_user_add_allowedserver (newuser, allowedserver);
}
}
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "enablemailpolicycontrol"))->active)
{
diradmin_user_set_attribute (newuser, "maillocaladdress", mail);
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "mailroutingaddressset"))->active)
diradmin_user_set_attribute (newuser, "mailroutingaddress",
mailroutingaddress);
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "mailhostset"))->active)
diradmin_user_set_attribute (newuser, "mailhost", mailhost);
}
if (GTK_TOGGLE_BUTTON
(lookup_widget (dialogbox, "enablesambaobjectclass"))->active)
{
char rid[11];
smbHome =
gtk_entry_get_text (GTK_ENTRY (lookup_widget (dialogbox, "smbHome")));
homeDrive =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "homeDrive")));
profilePath =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "profilePath")));
scriptPath =
gtk_entry_get_text (GTK_ENTRY
(lookup_widget (dialogbox, "scriptPath")));
diradmin_user_set_attribute (newuser, "smbHome", smbHome);
diradmin_user_set_attribute (newuser, "homeDrive", homeDrive);
diradmin_user_set_attribute (newuser, "profilePath", profilePath);
diradmin_user_set_attribute (newuser, "scriptPath", scriptPath);
sprintf(rid, "%d", 2*atoi(uidnumber) + 1000);
diradmin_user_set_attribute (newuser, "rid", rid);
}
if (strlen (userpassword) > 0)
diradmin_user_set_password (newuser, userpassword);
return (newuser);
}
ldaptransaction *
diradmin_user_create_ldapdiff (diradmin_user * newone)
{
ldaptransaction *t = NULL;
gchar **values;
GList *l = NULL;
gint acnt = 0;
g_assert (newone);
t = ldaptransaction_new ();
/* l = diradmin_user_get_objectclasses (newone);
for (l = diradmin_user_get_objectclasses (newone); l; l = g_list_next (l))
{
values = g_new0 (gchar *, 2);
values[0] = g_strdup (l->data);
ldaptransaction_add (t, "objectclass", values);
}
for (l = diradmin_user_get_allowedservers (newone); l; l = g_list_next (l))
{
values = g_new0 (gchar *, 2);
values[0] = g_strdup (l->data);
ldaptransaction_add (t, "host", values);
}*/
/* THIS GOT CHANGED!!! -Rudd-O */
l = diradmin_user_get_objectclasses (newone);
values = g_new0(gchar*,g_list_length(l)+1);
acnt = 0;
for (l = g_list_first(l); l; l = g_list_next (l))
{
values[acnt] = g_strdup (l->data); acnt++;
}
ldaptransaction_add (t, "objectclass", values);
if (diradmin_user_has_allservers(newone)) {
values = g_new0 (gchar *, 2);
values[0] = g_strdup ("*");
ldaptransaction_add (t, "host", values);
}
l = diradmin_user_get_allowedservers (newone);
if (g_list_length(l)) {
values = g_new0(gchar*,g_list_length(l)+1);
acnt = 0;
for (l = g_list_first(l); l; l = g_list_next (l))
{
values[acnt] = g_strdup (l->data); acnt++;
}
ldaptransaction_add (t, "host", values);
}
/* change is up to here */
for (acnt = 0; attrs2chk[acnt]; acnt++)
if (diradmin_user_get_attribute (newone, attrs2chk[acnt]) != NULL)
{
values = g_new0 (gchar *, 2);
if (g_strcasecmp (attrs2chk[acnt], "gecos") == 0)
values[0] = convert_to_ascii(diradmin_user_get_attribute
(newone, attrs2chk[acnt]));
else
values[0] = convert_to_utf8(diradmin_user_get_attribute (newone, attrs2chk[acnt]));
//g_print("Attribute %s value %s\n",attrs2chk[acnt],values[0]);
ldaptransaction_add (t, attrs2chk[acnt], values);
}
ldaptransaction_dump (t);
return t;
}
syntax highlighted by Code2HTML, v. 0.9.1