2 /* ldap.incr arguments example
4 * arguments when moira creates the account - ignored by ldap.incr since the
5 * account is unusable. users 0 11 #45198 45198 /bin/cmd cmd Last First Middle
6 * 0 950000001 2000 121049
8 * login, unix_uid, shell, winconsoleshell, last,
9 * first, middle, status, mitid, type, moiraid
11 * arguments for creating or updating a user account
12 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF
13 * 121058 PathToHomeDir PathToProfileDir username 45206 /bin/cmd cmd Last
14 * First Middle 1 950000001 STAFF 121058 PathToHomeDir PathToProfileDir
15 * users 11 11 #45206 45206 /bin/cmd cmd Last First Middle 0 950000001 STAFF
16 * 121058 PathToHomeDir PathToProfileDir newuser 45206 /bin/cmd cmd Last
17 * First Middle 2 950000001 STAFF 121058 PathToHomeDir PathToProfileDir
19 * login, unix_uid, shell, winconsoleshell, last, first, middle, status,
20 * mitid, type, moiraid
22 * arguments for deactivating/deleting a user account
23 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF
24 * 121058 PathToHomeDir PathToProfileDir username 45206 /bin/cmd cmd Last
25 * First Middle 3 950000001 STAFF 121058 PathToHomeDir PathToProfileDir
26 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF
27 * 121058 PathToHomeDir PathToProfileDir username 45206 /bin/cmd cmd Last
28 * First Middle 3 950000001 STAFF 121058 PathToHomeDir PathToProfileDir
30 * login, unix_uid, shell, winconsoleshell, last, first, middle, status,
31 * mitid, type, moiraid
33 * arguments for reactivating a user account
34 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF
35 * 121058 username 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF
37 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF
38 * 121058 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF 12105
40 * login, unix_uid, shell, winconsoleshell, last, first, middle, status,
41 * mitid, type, moiraid
43 * arguments for changing user name
44 * users 11 11 oldusername 45206 /bin/cmd cmd Last First Middle 1 950000001
45 * STAFF 121058 PathToHomeDir PathToProfileDir newusername 45206 /bin/cmd cmd
46 * Last First Middle 1 950000001 STAFF 121058 PathToHomeDir PathToProfileDir
48 * login, unix_uid, shell, winconsoleshell, last, first, middle, status,
49 * mitid, type, moiraid
51 * arguments for expunging a user
52 * users 11 0 username 45198 /bin/cmd cmd Last First Middle 0 950000001 2000
55 * login, unix_uid, shell, winconsoleshell, last, first, middle, status,
56 * mitid, type, moiraid
58 * arguments for creating a "special" group/list
59 * list 0 11 listname 1 1 0 0 0 -1 NONE 0 description 92616
61 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
62 * acl_id, description, moiraid
64 * arguments for creating a "mail" group/list
65 * list 0 11 listname 1 1 0 1 0 -1 NONE 0 description 92616
67 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
68 * acl_id, description, moiraid
70 * arguments for creating a "group" group/list
71 * list 0 11 listname 1 1 0 0 1 -1 NONE 0 description 92616
73 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
74 * acl_id, description, moiraid
76 * arguments for creating a "group/mail" group/list
77 * list 0 11 listname 1 1 0 1 1 -1 NONE 0 description 92616
79 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
80 * acl_id, description, moiraid
82 * arguments to add a USER member to group/list
83 * imembers 0 12 listname USER userName 1 1 0 0 0 -1 1 92616 121047
85 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist,
86 * gid, userStatus, moiraListId, moiraUserId
88 * arguments to add a STRING or KERBEROS member to group/list
89 * imembers 0 10 listname STRING stringName 1 1 0 0 0 -1 92616
90 * imembers 0 10 listlistnameName KERBEROS kerberosName 1 1 0 0 0 -1 92616
92 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist,
95 * NOTE: group members of type LIST are ignored.
97 * arguments to remove a USER member to group/list
98 * imembers 12 0 listname USER userName 1 1 0 0 0 -1 1 92616 121047
100 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist,
101 * gid, userStatus, moiraListId, moiraUserId
103 * arguments to remove a STRING or KERBEROS member to group/list
104 * imembers 10 0 listname STRING stringName 1 1 0 0 0 -1 92616
105 * imembers 10 0 listname KERBEROS kerberosName 1 1 0 0 0 -1 92616
107 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist,
110 * NOTE: group members of type LIST are ignored.
112 * arguments for renaming a group/list
113 * list 11 11 oldlistname 1 1 0 0 0 -1 NONE 0 description 92616 newlistname 1
114 * 1 0 0 0 -1 description 0 92616
116 * name, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
117 * acl_id, description, moiraListId
119 * arguments for deleting a group/list
120 * list 11 0 listname 1 1 0 0 0 -1 NONE 0 description 92616
122 * name, active, publicflg, hidden, maillist, grouplist, gid, acl_type,
123 * acl_id, description, moiraListId
125 * arguments for adding a file system
126 * filesys 0 12 username AFS ATHENA.MIT.EDU
127 * /afs/athena.mit.edu/user/n/e/username /mit/username w descripton username
128 * wheel 1 HOMEDIR 101727
130 * arguments for deleting a file system
131 * filesys 12 0 username AFS ATHENA.MIT.EDU
132 * /afs/athena.mit.edu/user/n/e/username /mit/username w descripton username
133 * wheel 1 HOMEDIR 101727
135 * arguments when moira creates a container (OU).
136 * containers 0 8 machines/test/bottom description location contact USER
139 * arguments when moira deletes a container (OU).
140 * containers 8 0 machines/test/bottom description location contact USER
141 * 105316 2222 groupname
143 * arguments when moira modifies a container information (OU).
144 * containers 8 8 machines/test/bottom description location contact USER
145 * 105316 2222 groupname machines/test/bottom description1 location contact
146 * USER 105316 2222 groupname
148 * arguments when moira adds a machine from an OU
149 * table name, beforec, afterc, machine_name, container_name, mach_id, cnt_id
150 * mcntmap 0 5 DAVIDT.MIT.EDU dttest/dttest1 76767 46 groupname
152 * arguments when moira removes a machine from an OU
153 * table name, beforec, afterc, machine_name, container_name, mach_id, cnt_id
154 * mcntmap 0 5 DAVIDT.MIT.EDU dttest/dttest1 76767 46 groupname
158 #include <mit-copyright.h>
161 #include <winsock2.h>
165 #include <lmaccess.h>
173 #include <moira_site.h>
174 #include <mrclient.h>
182 #define ECONNABORTED WSAECONNABORTED
185 #define ECONNREFUSED WSAECONNREFUSED
188 #define EHOSTUNREACH WSAEHOSTUNREACH
190 #define krb5_xfree free
192 #define sleep(A) Sleep(A * 1000);
196 #include <sys/types.h>
197 #include <netinet/in.h>
198 #include <arpa/nameser.h>
200 #include <sys/utsname.h>
203 #define CFG_PATH "/moira/ldap/"
204 #define WINADCFG "ldap.cfg"
205 #define strnicmp(A,B,C) strncasecmp(A,B,C)
206 #define UCHAR unsigned char
208 #define UF_SCRIPT 0x0001
209 #define UF_ACCOUNTDISABLE 0x0002
210 #define UF_HOMEDIR_REQUIRED 0x0008
211 #define UF_LOCKOUT 0x0010
212 #define UF_PASSWD_NOTREQD 0x0020
213 #define UF_PASSWD_CANT_CHANGE 0x0040
214 #define UF_DONT_EXPIRE_PASSWD 0x10000
216 #define UF_TEMP_DUPLICATE_ACCOUNT 0x0100
217 #define UF_NORMAL_ACCOUNT 0x0200
218 #define UF_INTERDOMAIN_TRUST_ACCOUNT 0x0800
219 #define UF_WORKSTATION_TRUST_ACCOUNT 0x1000
220 #define UF_SERVER_TRUST_ACCOUNT 0x2000
222 #define OWNER_SECURITY_INFORMATION (0x00000001L)
223 #define GROUP_SECURITY_INFORMATION (0x00000002L)
224 #define DACL_SECURITY_INFORMATION (0x00000004L)
225 #define SACL_SECURITY_INFORMATION (0x00000008L)
228 #define BYTE unsigned char
230 typedef unsigned int DWORD;
231 typedef unsigned long ULONG;
236 unsigned short Data2;
237 unsigned short Data3;
238 unsigned char Data4[8];
241 typedef struct _SID_IDENTIFIER_AUTHORITY {
243 } SID_IDENTIFIER_AUTHORITY, *PSID_IDENTIFIER_AUTHORITY;
245 typedef struct _SID {
247 BYTE SubAuthorityCount;
248 SID_IDENTIFIER_AUTHORITY IdentifierAuthority;
249 DWORD SubAuthority[512];
254 #define WINADCFG "ldap.cfg"
262 #define WINAFS "\\\\afs\\all\\"
264 #define ADS_GROUP_TYPE_GLOBAL_GROUP 0x00000002
265 #define ADS_GROUP_TYPE_DOMAIN_LOCAL_GROUP 0x00000004
266 #define ADS_GROUP_TYPE_LOCAL_GROUP 0x00000004
267 #define ADS_GROUP_TYPE_UNIVERSAL_GROUP 0x00000008
268 #define ADS_GROUP_TYPE_SECURITY_ENABLED 0x80000000
270 #define QUERY_VERSION -1
271 #define PRIMARY_REALM "ATHENA.MIT.EDU"
272 #define PRIMARY_DOMAIN "win.mit.edu"
273 #define PRODUCTION_PRINCIPAL "sms"
274 #define TEST_PRINCIPAL "smstest"
283 #define MEMBER_REMOVE 2
284 #define MEMBER_CHANGE_NAME 3
285 #define MEMBER_ACTIVATE 4
286 #define MEMBER_DEACTIVATE 5
287 #define MEMBER_CREATE 6
289 #define MOIRA_ALL 0x0
290 #define MOIRA_USERS 0x1
291 #define MOIRA_KERBEROS 0x2
292 #define MOIRA_STRINGS 0x4
293 #define MOIRA_LISTS 0x8
294 #define MOIRA_MACHINE 0x16
296 #define CHECK_GROUPS 1
297 #define CLEANUP_GROUPS 2
299 #define AD_NO_GROUPS_FOUND -1
300 #define AD_WRONG_GROUP_DN_FOUND -2
301 #define AD_MULTIPLE_GROUPS_FOUND -3
302 #define AD_INVALID_NAME -4
303 #define AD_LDAP_FAILURE -5
304 #define AD_INVALID_FILESYS -6
305 #define AD_NO_ATTRIBUTE_FOUND -7
306 #define AD_NO_OU_FOUND -8
307 #define AD_NO_USER_FOUND -9
309 /* container arguments */
310 #define CONTAINER_NAME 0
311 #define CONTAINER_DESC 1
312 #define CONTAINER_LOCATION 2
313 #define CONTAINER_CONTACT 3
314 #define CONTAINER_TYPE 4
315 #define CONTAINER_ID 5
316 #define CONTAINER_ROWID 6
317 #define CONTAINER_GROUP_NAME 7
319 /*mcntmap arguments*/
320 #define OU_MACHINE_NAME 0
321 #define OU_CONTAINER_NAME 1
322 #define OU_MACHINE_ID 2
323 #define OU_CONTAINER_ID 3
324 #define OU_CONTAINER_GROUP 4
326 typedef struct lk_entry {
336 struct lk_entry *next;
339 #define STOP_FILE "/moira/ldap/noldap"
340 #define file_exists(file) (access((file), F_OK) == 0)
342 #define N_SD_BER_BYTES 5
343 #define LDAP_BERVAL struct berval
344 #define MAX_SERVER_NAMES 32
346 #define HIDDEN_GROUP "HiddenGroup.g"
347 #define HIDDEN_GROUP_WITH_ADMIN "HiddenGroupWithAdmin.g"
348 #define NOT_HIDDEN_GROUP "NotHiddenGroup.g"
349 #define NOT_HIDDEN_GROUP_WITH_ADMIN "NotHiddenGroupWithAdmin.g"
351 #define ADDRESS_LIST_PREFIX "CN=MIT Directory,CN=All Address Lists,\
352 CN=Address Lists Container,CN=Massachusetts Institute of Technology,\
353 CN=Microsoft Exchange,CN=Services,CN=Configuration,"
355 #define ADD_ATTR(t, v, o) \
356 mods[n] = malloc(sizeof(LDAPMod)); \
357 mods[n]->mod_op = o; \
358 mods[n]->mod_type = t; \
359 mods[n++]->mod_values = v
361 #define DEL_ATTR(t, o) \
362 DelMods[i] = malloc(sizeof(LDAPMod)); \
363 DelMods[i]->mod_op = o; \
364 DelMods[i]->mod_type = t; \
365 DelMods[i++]->mod_values = NULL
367 #define DOMAIN_SUFFIX "MIT.EDU"
368 #define DOMAIN "DOMAIN:"
369 #define PRINCIPALNAME "PRINCIPAL:"
370 #define SERVER "SERVER:"
373 #define GROUP_SUFFIX "GROUP_SUFFIX:"
374 #define GROUP_TYPE "GROUP_TYPE:"
375 #define SET_GROUP_ACE "SET_GROUP_ACE:"
376 #define SET_PASSWORD "SET_PASSWORD:"
377 #define EXCHANGE "EXCHANGE:"
378 #define REALM "REALM:"
379 #define ACTIVE_DIRECTORY "ACTIVE_DIRECTORY:"
381 #define PROCESS_MACHINE_CONTAINER "PROCESS_MACHINE_CONTAINER:"
382 #define GROUP_POPULATE_MEMBERS "GROUP_POPULATE_MEMBERS:"
383 #define MAX_DOMAINS 10
384 char DomainNames[MAX_DOMAINS][128];
386 LK_ENTRY *member_base = NULL;
388 char PrincipalName[128];
389 static char tbl_buf[1024];
390 char kerberos_ou[] = "OU=kerberos,OU=moira";
391 char contact_ou[] = "OU=strings,OU=moira";
392 char user_ou[] = "OU=users,OU=moira";
393 char group_ou_distribution[1024];
394 char group_ou_root[1024];
395 char group_ou_security[1024];
396 char group_ou_neither[1024];
397 char group_ou_both[1024];
398 char orphans_machines_ou[] = "OU=Machines,OU=Orphans";
399 char orphans_other_ou[] = "OU=Other,OU=Orphans";
400 char security_template_ou[] = "OU=security_templates";
402 char ldap_domain[256];
403 char ldap_realm[256];
405 char *ServerList[MAX_SERVER_NAMES];
406 char default_server[256];
407 static char tbl_buf[1024];
408 char group_suffix[256];
409 char exchange_acl[256];
410 int mr_connections = 0;
413 int UseGroupSuffix = 1;
414 int UseGroupUniversal = 0;
418 int ProcessMachineContainer = 1;
419 int ActiveDirectory = 1;
420 int UpdateDomainList;
422 int GroupPopulateDelete = 0;
424 extern int set_password(char *user, char *password, char *domain);
426 int ad_get_group(LDAP *ldap_handle, char *dn_path, char *group_name,
427 char *group_membership, char *MoiraId, char *attribute,
428 LK_ENTRY **linklist_base, int *linklist_count,
430 void AfsToWinAfs(char* path, char* winPath);
431 int ad_connect(LDAP **ldap_handle, char *ldap_domain, char *dn_path,
432 char *Win2kPassword, char *Win2kUser, char *default_server,
433 int connect_to_kdc, char **ServerList, char *ldap_realm,
435 void ad_kdc_disconnect();
436 int ad_server_connect(char *connectedServer, char *domain);
437 int attribute_update(LDAP *ldap_handle, char *distinguished_name,
438 char *attribute_value, char *attribute, char *user_name);
439 int BEREncodeSecurityBits(ULONG uBits, char *pBuffer);
440 int checkADname(LDAP *ldap_handle, char *dn_path, char *Name);
441 int check_winad(void);
442 int check_user(LDAP *ldap_handle, char *dn_path, char *UserName,
445 int container_adupdate(LDAP *ldap_handle, char *dn_path, char *dName,
446 char *distinguishedName, int count, char **av);
447 void container_check(LDAP *ldap_handle, char *dn_path, char *name);
448 int container_create(LDAP *ldap_handle, char *dn_path, int count, char **av);
449 int container_delete(LDAP *ldap_handle, char *dn_path, int count, char **av);
450 int container_get_distinguishedName(LDAP *ldap_handle, char *dn_path,
451 char *distinguishedName, int count,
453 void container_get_dn(char *src, char *dest);
454 void container_get_name(char *src, char *dest);
455 int container_move_objects(LDAP *ldap_handle, char *dn_path, char *dName);
456 int container_rename(LDAP *ldap_handle, char *dn_path, int beforec,
457 char **before, int afterc, char **after);
458 int container_update(LDAP *ldap_handle, char *dn_path, int beforec,
459 char **before, int afterc, char **after);
461 int GetAceInfo(int ac, char **av, void *ptr);
462 int get_group_membership(char *group_membership, char *group_ou,
463 int *security_flag, char **av);
464 int get_machine_ou(LDAP *ldap_handle, char *dn_path, char *member,
465 char *machine_ou, char *pPtr);
466 int Moira_container_group_create(char **after);
467 int Moira_container_group_delete(char **before);
468 int Moira_groupname_create(char *GroupName, char *ContainerName,
469 char *ContainerRowID);
470 int Moira_container_group_update(char **before, char **after);
471 int Moira_process_machine_container_group(char *MachineName, char* groupName,
473 int Moira_addGroupToParent(char *origContainerName, char *GroupName);
474 int Moira_getContainerGroup(int ac, char **av, void *ptr);
475 int Moira_getGroupName(char *origContainerName, char *GroupName,
477 int Moira_setContainerGroup(char *ContainerName, char *GroupName);
478 int ProcessAce(LDAP *ldap_handle, char *dn_path, char *group_name, char *Type,
479 int UpdateGroup, int *ProcessGroup, char *maillist);
480 int process_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
481 char *group_name, char *group_ou, char *group_membership,
482 int group_security_flag, int type, char *maillist);
483 int process_lists(int ac, char **av, void *ptr);
484 int ProcessGroupSecurity(LDAP *ldap_handle, char *dn_path,
485 char *TargetGroupName, int HiddenGroup,
486 char *AceType, char *AceName);
487 int ProcessMachineName(int ac, char **av, void *ptr);
488 int ReadConfigFile(char *DomainName);
489 int ReadDomainList();
490 void StringTrim(char *StringToTrim);
491 char *escape_string(char *s);
492 int save_query_info(int argc, char **argv, void *hint);
493 int save_fsgroup_info(int argc, char **argv, void *hint);
494 int user_create(int ac, char **av, void *ptr);
495 int user_change_status(LDAP *ldap_handle, char *dn_path,
496 char *user_name, char *MoiraId, int operation);
497 int user_delete(LDAP *ldap_handle, char *dn_path,
498 char *u_name, char *MoiraId);
499 int user_rename(LDAP *ldap_handle, char *dn_path, char *before_user_name,
501 int user_update(LDAP *ldap_handle, char *dn_path, char *user_name,
502 char *uid, char *MitId, char *MoiraId, int State,
503 char *WinHomeDir, char *WinProfileDir, char *first,
504 char *middle, char *last, char *shell, char *class);
505 void change_to_lower_case(char *ptr);
506 int contact_create(LDAP *ld, char *bind_path, char *user, char *group_ou);
507 int contact_remove_email(LDAP *ld, char *bind_path,
508 LK_ENTRY **linklist_entry, int linklist_current);
509 int group_create(int ac, char **av, void *ptr);
510 int group_delete(LDAP *ldap_handle, char *dn_path,
511 char *group_name, char *group_membership, char *MoiraId);
512 int group_rename(LDAP *ldap_handle, char *dn_path,
513 char *before_group_name, char *before_group_membership,
514 char *before_group_ou, int before_security_flag,
515 char *before_desc, char *after_group_name,
516 char *after_group_membership, char *after_group_ou,
517 int after_security_flag, char *after_desc,
518 char *MoiraId, char *filter, char *maillist);
519 int machine_check(LDAP *ldap_handle, char *dn_path, char *machine_name);
520 int machine_GetMoiraContainer(int ac, char **av, void *ptr);
521 int machine_get_moira_container(LDAP *ldap_handle, char *dn_path,
522 char *machine_name, char *container_name);
523 int machine_move_to_ou(LDAP *ldap_handle, char *dn_path,
524 char *MoiraMachineName, char *DestinationOu);
525 int make_new_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
526 char *group_name, char *group_ou, char *group_membership,
527 int group_security_flag, int updateGroup, char *maillist);
528 int member_list_build(int ac, char **av, void *ptr);
529 int member_add(LDAP *ldap_handle, char *dn_path, char *group_name,
530 char *group_ou, char *group_membership,
531 char *user_name, char *pUserOu, char *MoiraId);
532 int member_remove(LDAP *ldap_handle, char *dn_path, char *group_name,
533 char *group_ou, char *group_membership, char *user_name,
534 char *pUserOu, char *MoiraId);
535 int populate_group(LDAP *ldap_handle, char *dn_path, char *group_name,
536 char *group_ou, char *group_membership,
537 int group_security_flag, char *MoiraId);
538 int SetHomeDirectory(LDAP *ldap_handle, char *user_name,
539 char *DistinguishedName,
540 char *WinHomeDir, char *WinProfileDir,
541 char **homedir_v, char **winProfile_v,
542 char **drives_v, LDAPMod **mods,
544 int sid_update(LDAP *ldap_handle, char *dn_path);
545 void SwitchSFU(LDAPMod **mods, int *UseSFU30, int n);
546 int check_string(char *s);
547 int check_container_name(char* s);
549 int mr_connect_cl(char *server, char *client, int version, int auth);
550 void do_container(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
551 char **before, int beforec, char **after, int afterc);
552 void do_filesys(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
553 char **before, int beforec, char **after, int afterc);
554 void do_list(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
555 char **before, int beforec, char **after, int afterc);
556 void do_user(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
557 char **before, int beforec, char **after, int afterc);
558 void do_member(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
559 char **before, int beforec, char **after, int afterc);
560 void do_mcntmap(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
561 char **before, int beforec, char **after, int afterc);
562 int linklist_create_entry(char *attribute, char *value,
563 LK_ENTRY **linklist_entry);
564 int linklist_build(LDAP *ldap_handle, char *dn_path, char *search_exp,
565 char **attr_array, LK_ENTRY **linklist_base,
566 int *linklist_count, unsigned long ScopeType);
567 void linklist_free(LK_ENTRY *linklist_base);
569 int retrieve_attributes(LDAP *ldap_handle, LDAPMessage *ldap_entry,
570 char *distinguished_name, LK_ENTRY **linklist_current);
571 int retrieve_entries(LDAP *ldap_handle, LDAPMessage *ldap_entry,
572 LK_ENTRY **linklist_base, int *linklist_count);
573 int retrieve_values(LDAP *ldap_handle, LDAPMessage *ldap_entry,
574 char *Attribute, char *distinguished_name,
575 LK_ENTRY **linklist_current);
577 int construct_newvalues(LK_ENTRY *linklist_base, int modvalue_count,
578 char *oldValue, char *newValue,
579 char ***modvalues, int type);
580 void free_values(char **modvalues);
582 int convert_domain_to_dn(char *domain, char **bind_path);
583 void get_distinguished_name(LDAP *ldap_handle, LDAPMessage *ldap_entry,
584 char *distinguished_name);
585 int moira_disconnect(void);
586 int moira_connect(void);
587 void print_to_screen(const char *fmt, ...);
588 int GetMachineName(char *MachineName);
589 int tickets_get_k5();
590 int destroy_cache(void);
593 int find_homeMDB(LDAP *ldap_handle, char *dn_path, char **homeMDB,
594 char **homeServerName);
596 int main(int argc, char **argv)
612 whoami = ((whoami = (char *)strrchr(argv[0], '/')) ? whoami+1 : argv[0]);
616 com_err(whoami, 0, "Unable to process %s", "argc < 4");
620 if (argc < (4 + atoi(argv[2]) + atoi(argv[3])))
622 com_err(whoami, 0, "Unable to process %s",
623 "argc < (4 + beforec + afterc)");
627 if (!strcmp(argv[1], "filesys"))
630 for (i = 1; i < argc; i++)
632 strcat(tbl_buf, argv[i]);
633 strcat(tbl_buf, " ");
636 com_err(whoami, 0, "%s", tbl_buf);
640 com_err(whoami, 0, "%s failed", "check_winad()");
644 initialize_sms_error_table();
645 initialize_krb_error_table();
647 UpdateDomainList = 0;
648 memset(DomainNames, '\0', sizeof(DomainNames[0]) * MAX_DOMAINS);
650 if (ReadDomainList())
652 com_err(whoami, 0, "%s failed", "ReadDomainList()");
656 for (i = 0; i < argc; i++)
659 for (k = 0; k < MAX_DOMAINS; k++)
661 if (strlen(DomainNames[k]) == 0)
663 for (i = 0; i < argc; i++)
665 if (orig_argv[i] != NULL)
667 orig_argv[i] = strdup(argv[i]);
670 memset(PrincipalName, '\0', sizeof(PrincipalName));
671 memset(ldap_domain, '\0', sizeof(ldap_domain));
672 memset(ServerList, '\0', sizeof(ServerList[0]) * MAX_SERVER_NAMES);
673 memset(default_server, '\0', sizeof(default_server));
674 memset(dn_path, '\0', sizeof(dn_path));
675 memset(group_suffix, '\0', sizeof(group_suffix));
676 memset(exchange_acl, '\0', sizeof(exchange_acl));
680 UseGroupUniversal = 0;
684 ProcessMachineContainer = 1;
687 sprintf(group_suffix, "%s", "_group");
688 sprintf(exchange_acl, "%s", "exchange-acl");
690 beforec = atoi(orig_argv[2]);
691 afterc = atoi(orig_argv[3]);
692 table = orig_argv[1];
693 before = &orig_argv[4];
694 after = &orig_argv[4 + beforec];
702 if (ReadConfigFile(DomainNames[k]))
707 sprintf(group_ou_distribution, "OU=mail,OU=lists,OU=moira");
708 sprintf(group_ou_root, "OU=lists,OU=moira");
709 sprintf(group_ou_security, "OU=group,OU=lists,OU=moira");
710 sprintf(group_ou_neither, "OU=special,OU=lists,OU=moira");
711 sprintf(group_ou_both, "OU=mail,OU=group,OU=lists,OU=moira");
715 sprintf(group_ou_distribution, "OU=lists,OU=moira");
716 sprintf(group_ou_root, "OU=lists,OU=moira");
717 sprintf(group_ou_security, "OU=lists,OU=moira");
718 sprintf(group_ou_neither, "OU=lists,OU=moira");
719 sprintf(group_ou_both, "OU=lists,OU=moira");
722 OldUseSFU30 = UseSFU30;
724 for (i = 0; i < 5; i++)
726 ldap_handle = (LDAP *)NULL;
727 if (!(rc = ad_connect(&ldap_handle, ldap_domain, dn_path, "", "",
728 default_server, SetPassword, ServerList,
729 ldap_realm, ldap_port)))
731 com_err(whoami, 0, "connected to domain %s", DomainNames[k]);
736 if ((rc) || (ldap_handle == NULL))
738 critical_alert("incremental",
739 "ldap.incr cannot connect to any server in "
740 "domain %s", DomainNames[k]);
744 for (i = 0; i < (int)strlen(table); i++)
745 table[i] = tolower(table[i]);
747 if (!strcmp(table, "users"))
748 do_user(ldap_handle, dn_path, ldap_domain, before, beforec, after,
750 else if (!strcmp(table, "list"))
751 do_list(ldap_handle, dn_path, ldap_domain, before, beforec, after,
753 else if (!strcmp(table, "imembers"))
754 do_member(ldap_handle, dn_path, ldap_domain, before, beforec, after,
756 else if (!strcmp(table, "containers"))
757 do_container(ldap_handle, dn_path, ldap_domain, before, beforec, after,
759 else if (!strcmp(table, "mcntmap"))
760 do_mcntmap(ldap_handle, dn_path, ldap_domain, before, beforec, after,
766 for (i = 0; i < MAX_SERVER_NAMES; i++)
768 if (ServerList[i] != NULL)
771 ServerList[i] = NULL;
775 rc = ldap_unbind_s(ldap_handle);
781 void do_mcntmap(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
782 char **before, int beforec, char **after, int afterc)
784 char MoiraContainerName[128];
785 char ADContainerName[128];
786 char MachineName[1024];
787 char OriginalMachineName[1024];
790 char MoiraContainerGroup[64];
792 if (!ProcessMachineContainer)
794 com_err(whoami, 0, "Process machines and containers disabled, skipping");
799 memset(ADContainerName, '\0', sizeof(ADContainerName));
800 memset(MoiraContainerName, '\0', sizeof(MoiraContainerName));
802 if ((beforec == 0) && (afterc == 0))
805 if (rc = moira_connect())
807 critical_alert("Ldap incremental",
808 "Error contacting Moira server : %s",
813 if ((beforec != 0) && (afterc == 0)) /*remove a machine*/
815 strcpy(OriginalMachineName, before[OU_MACHINE_NAME]);
816 strcpy(MachineName, before[OU_MACHINE_NAME]);
817 strcpy(MoiraContainerGroup, before[OU_CONTAINER_GROUP]);
819 com_err(whoami, 0, "removing machine %s from %s",
820 OriginalMachineName, before[OU_CONTAINER_NAME]);
822 else if ((beforec == 0) && (afterc != 0)) /*add a machine*/
824 strcpy(OriginalMachineName, after[OU_MACHINE_NAME]);
825 strcpy(MachineName, after[OU_MACHINE_NAME]);
826 strcpy(MoiraContainerGroup, after[OU_CONTAINER_GROUP]);
827 com_err(whoami, 0, "adding machine %s to container %s",
828 OriginalMachineName, after[OU_CONTAINER_NAME]);
836 rc = GetMachineName(MachineName);
838 if (strlen(MachineName) == 0)
841 com_err(whoami, 0, "Unable to find alais for machine %s in Moira",
842 OriginalMachineName);
846 Moira_process_machine_container_group(MachineName, MoiraContainerGroup,
849 if (machine_check(ldap_handle, dn_path, MachineName))
851 com_err(whoami, 0, "Unable to find machine %s (alias %s) in directory.",
852 OriginalMachineName, MachineName);
857 memset(MoiraContainerName, '\0', sizeof(MoiraContainerName));
858 machine_get_moira_container(ldap_handle, dn_path, MachineName,
861 if (strlen(MoiraContainerName) == 0)
863 com_err(whoami, 0, "Unable to fine machine %s (alias %s) container "
864 "in Moira - moving to orphans OU.",
865 OriginalMachineName, MachineName);
866 machine_move_to_ou(ldap_handle, dn_path, MachineName,
867 orphans_machines_ou);
872 container_get_dn(MoiraContainerName, ADContainerName);
874 if (MoiraContainerName[strlen(MoiraContainerName) - 1] != '/')
875 strcat(MoiraContainerName, "/");
877 container_check(ldap_handle, dn_path, MoiraContainerName);
878 machine_move_to_ou(ldap_handle, dn_path, MachineName, ADContainerName);
883 void do_container(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
884 char **before, int beforec, char **after, int afterc)
888 if (!ProcessMachineContainer)
890 com_err(whoami, 0, "Process machines and containers disabled, skipping");
894 if ((beforec == 0) && (afterc == 0))
897 if (rc = moira_connect())
899 critical_alert("Ldap incremental", "Error contacting Moira server : %s",
904 if ((beforec != 0) && (afterc == 0)) /*delete a new container*/
906 com_err(whoami, 0, "deleting container %s", before[CONTAINER_NAME]);
907 container_delete(ldap_handle, dn_path, beforec, before);
908 Moira_container_group_delete(before);
913 if ((beforec == 0) && (afterc != 0)) /*create a container*/
915 com_err(whoami, 0, "creating container %s", after[CONTAINER_NAME]);
916 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
917 container_create(ldap_handle, dn_path, afterc, after);
918 Moira_container_group_create(after);
923 if (strcasecmp(before[CONTAINER_NAME], after[CONTAINER_NAME]))
925 com_err(whoami, 0, "renaming container %s to %s",
926 before[CONTAINER_NAME], after[CONTAINER_NAME]);
927 container_rename(ldap_handle, dn_path, beforec, before, afterc, after);
928 Moira_container_group_update(before, after);
933 com_err(whoami, 0, "updating container %s information",
934 after[CONTAINER_NAME]);
935 container_update(ldap_handle, dn_path, beforec, before, afterc, after);
936 Moira_container_group_update(before, after);
941 #define L_LIST_DESC 9
944 void do_list(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
945 char **before, int beforec, char **after, int afterc)
950 char group_membership[6];
955 char before_list_id[32];
956 char before_group_membership[1];
957 int before_security_flag;
958 char before_group_ou[256];
959 LK_ENTRY *ptr = NULL;
961 if (beforec == 0 && afterc == 0)
964 memset(list_id, '\0', sizeof(list_id));
965 memset(before_list_id, '\0', sizeof(before_list_id));
966 memset(before_group_ou, '\0', sizeof(before_group_ou));
967 memset(before_group_membership, '\0', sizeof(before_group_membership));
968 memset(group_ou, '\0', sizeof(group_ou));
969 memset(group_membership, '\0', sizeof(group_membership));
974 if (beforec < L_LIST_ID)
976 if (beforec > L_LIST_DESC)
978 strcpy(before_list_id, before[L_LIST_ID]);
980 before_security_flag = 0;
981 get_group_membership(before_group_membership, before_group_ou,
982 &before_security_flag, before);
987 if (afterc < L_LIST_ID)
989 if (afterc > L_LIST_DESC)
991 strcpy(list_id, after[L_LIST_ID]);
994 get_group_membership(group_membership, group_ou, &security_flag, after);
997 if ((beforec == 0) && (afterc == 0)) /*this case should never happen*/
1006 if ((rc = process_group(ldap_handle, dn_path, before_list_id,
1007 before[L_NAME], before_group_ou,
1008 before_group_membership,
1009 before_security_flag, CHECK_GROUPS,
1010 before[L_MAILLIST])))
1012 if (rc == AD_NO_GROUPS_FOUND)
1016 if ((rc == AD_WRONG_GROUP_DN_FOUND) ||
1017 (rc == AD_MULTIPLE_GROUPS_FOUND))
1019 rc = process_group(ldap_handle, dn_path, before_list_id,
1020 before[L_NAME], before_group_ou,
1021 before_group_membership,
1022 before_security_flag, CLEANUP_GROUPS,
1023 before[L_MAILLIST]);
1025 if ((rc != AD_NO_GROUPS_FOUND) && (rc != 0))
1027 com_err(whoami, 0, "Unable to process list %s",
1031 if (rc == AD_NO_GROUPS_FOUND)
1037 if ((beforec != 0) && (afterc != 0))
1039 if (((strcmp(after[L_NAME], before[L_NAME])) ||
1040 ((!strcmp(after[L_NAME], before[L_NAME])) &&
1041 (strcmp(before_group_ou, group_ou)))) &&
1044 com_err(whoami, 0, "Changing list name from %s to %s",
1045 before[L_NAME], after[L_NAME]);
1047 if ((strlen(before_group_ou) == 0) ||
1048 (strlen(before_group_membership) == 0) ||
1049 (strlen(group_ou) == 0) || (strlen(group_membership) == 0))
1051 com_err(whoami, 0, "%s", "Unable to find the group OU's");
1055 memset(filter, '\0', sizeof(filter));
1057 if ((rc = group_rename(ldap_handle, dn_path,
1058 before[L_NAME], before_group_membership,
1059 before_group_ou, before_security_flag,
1060 before[L_LIST_DESC], after[L_NAME],
1061 group_membership, group_ou, security_flag,
1063 list_id, filter, after[L_MAILLIST])))
1065 if (rc != AD_NO_GROUPS_FOUND)
1068 "Unable to change list name from %s to %s",
1069 before[L_NAME], after[L_NAME]);
1082 if ((strlen(before_group_ou) == 0) ||
1083 (strlen(before_group_membership) == 0))
1086 "Unable to find the group OU for group %s", before[L_NAME]);
1090 com_err(whoami, 0, "Deleting group %s", before[L_NAME]);
1091 rc = group_delete(ldap_handle, dn_path, before[L_NAME],
1092 before_group_membership, before_list_id);
1100 com_err(whoami, 0, "Creating group %s", after[L_NAME]);
1102 if (rc = process_group(ldap_handle, dn_path, list_id, after[L_NAME],
1103 group_ou, group_membership,
1104 security_flag, CHECK_GROUPS,
1107 if (rc != AD_NO_GROUPS_FOUND)
1109 if ((rc == AD_WRONG_GROUP_DN_FOUND) ||
1110 (rc == AD_MULTIPLE_GROUPS_FOUND))
1112 rc = process_group(ldap_handle, dn_path, list_id,
1114 group_ou, group_membership,
1115 security_flag, CLEANUP_GROUPS,
1122 "Unable to create list %s", after[L_NAME]);
1129 com_err(whoami, 0, "Updating group %s information", after[L_NAME]);
1131 if (rc = moira_connect())
1133 critical_alert("Ldap incremental",
1134 "Error contacting Moira server : %s",
1141 if (ProcessAce(ldap_handle, dn_path, after[L_NAME], "LIST", 0,
1142 &ProcessGroup, after[L_MAILLIST]))
1147 if (ProcessAce(ldap_handle, dn_path, after[L_NAME], "LIST", 1,
1148 &ProcessGroup, after[L_MAILLIST]))
1152 if (make_new_group(ldap_handle, dn_path, list_id, after[L_NAME],
1153 group_ou, group_membership, security_flag,
1154 updateGroup, after[L_MAILLIST]))
1160 if (atoi(after[L_ACTIVE]))
1162 populate_group(ldap_handle, dn_path, after[L_NAME], group_ou,
1163 group_membership, security_flag, list_id);
1171 #define LM_EXTRA_ACTIVE (LM_END)
1172 #define LM_EXTRA_PUBLIC (LM_END+1)
1173 #define LM_EXTRA_HIDDEN (LM_END+2)
1174 #define LM_EXTRA_MAILLIST (LM_END+3)
1175 #define LM_EXTRA_GROUP (LM_END+4)
1176 #define LM_EXTRA_GID (LM_END+5)
1177 #define LMN_LIST_ID (LM_END+6)
1178 #define LM_LIST_ID (LM_END+7)
1179 #define LM_USER_ID (LM_END+8)
1180 #define LM_EXTRA_END (LM_END+9)
1182 void do_member(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
1183 char **before, int beforec, char **after, int afterc)
1185 LK_ENTRY *group_base;
1188 char *attr_array[3];
1189 char group_name[128];
1190 char user_name[128];
1191 char user_type[128];
1192 char moira_list_id[32];
1193 char moira_user_id[32];
1194 char group_membership[1];
1196 char machine_ou[256];
1204 char NewMachineName[1024];
1208 char *save_argv[U_END];
1212 memset(moira_list_id, '\0', sizeof(moira_list_id));
1213 memset(moira_user_id, '\0', sizeof(moira_user_id));
1217 if (afterc < LM_EXTRA_GID)
1220 if (!atoi(after[LM_EXTRA_ACTIVE]))
1223 "Unable to add %s to group %s : group not active",
1224 after[2], after[0]);
1230 if (!strcasecmp(ptr[LM_TYPE], "LIST"))
1233 strcpy(user_name, after[LM_MEMBER]);
1234 strcpy(group_name, after[LM_LIST]);
1235 strcpy(user_type, after[LM_TYPE]);
1237 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1239 if (afterc > LM_EXTRA_GROUP)
1241 strcpy(moira_list_id, after[LMN_LIST_ID]);
1242 strcpy(moira_user_id, after[LM_LIST_ID]);
1245 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
1247 if (afterc > LMN_LIST_ID)
1249 strcpy(moira_list_id, after[LM_LIST_ID]);
1250 strcpy(moira_user_id, after[LM_USER_ID]);
1255 if (afterc > LM_EXTRA_GID)
1256 strcpy(moira_list_id, after[LMN_LIST_ID]);
1261 if (beforec < LM_EXTRA_GID)
1263 if (!atoi(before[LM_EXTRA_ACTIVE]))
1266 "Unable to remove %s from group %s : group not active",
1267 before[2], before[0]);
1273 if (!strcasecmp(ptr[LM_TYPE], "LIST"))
1276 strcpy(user_name, before[LM_MEMBER]);
1277 strcpy(group_name, before[LM_LIST]);
1278 strcpy(user_type, before[LM_TYPE]);
1280 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1282 if (beforec > LM_EXTRA_GROUP)
1284 strcpy(moira_list_id, before[LMN_LIST_ID]);
1285 strcpy(moira_user_id, before[LM_LIST_ID]);
1288 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
1290 if (beforec > LMN_LIST_ID)
1292 strcpy(moira_list_id, before[LM_LIST_ID]);
1293 strcpy(moira_user_id, before[LM_USER_ID]);
1298 if (beforec > LM_EXTRA_GID)
1299 strcpy(moira_list_id, before[LMN_LIST_ID]);
1306 "Unable to process group : beforec = %d, afterc = %d",
1311 args[L_NAME] = ptr[LM_LIST];
1312 args[L_ACTIVE] = ptr[LM_EXTRA_ACTIVE];
1313 args[L_PUBLIC] = ptr[LM_EXTRA_PUBLIC];
1314 args[L_HIDDEN] = ptr[LM_EXTRA_HIDDEN];
1315 args[L_MAILLIST] = ptr[LM_EXTRA_MAILLIST];
1316 args[L_GROUP] = ptr[LM_EXTRA_GROUP];
1317 args[L_GID] = ptr[LM_EXTRA_GID];
1320 memset(group_ou, '\0', sizeof(group_ou));
1321 get_group_membership(group_membership, group_ou, &security_flag, args);
1323 if (strlen(group_ou) == 0)
1325 com_err(whoami, 0, "Unable to find the group OU for group %s",
1330 if (rc = process_group(ldap_handle, dn_path, moira_list_id, group_name,
1331 group_ou, group_membership, security_flag,
1332 CHECK_GROUPS, args[L_MAILLIST]))
1334 if (rc != AD_NO_GROUPS_FOUND)
1336 if (rc = process_group(ldap_handle, dn_path, moira_list_id,
1337 group_name, group_ou, group_membership,
1338 security_flag, CLEANUP_GROUPS,
1341 if (rc != AD_NO_GROUPS_FOUND)
1344 com_err(whoami, 0, "Unable to add %s to group %s - "
1345 "unable to process group", user_name, group_name);
1347 com_err(whoami, 0, "Unable to remove %s from group %s - "
1348 "unable to process group", user_name, group_name);
1355 if (rc == AD_NO_GROUPS_FOUND)
1357 if (rc = moira_connect())
1359 critical_alert("Ldap incremental",
1360 "Error contacting Moira server : %s",
1365 com_err(whoami, 0, "creating group %s", group_name);
1368 if (ProcessAce(ldap_handle, dn_path, ptr[LM_LIST], "LIST", 0,
1369 &ProcessGroup, ptr[LM_EXTRA_MAILLIST]))
1374 if (ProcessAce(ldap_handle, dn_path, ptr[LM_LIST], "LIST", 1,
1375 &ProcessGroup, ptr[LM_EXTRA_MAILLIST]))
1379 if (make_new_group(ldap_handle, dn_path, moira_list_id, ptr[LM_LIST],
1380 group_ou, group_membership, security_flag, 0,
1381 ptr[LM_EXTRA_MAILLIST]))
1387 if (atoi(ptr[LM_EXTRA_ACTIVE]))
1389 populate_group(ldap_handle, dn_path, ptr[LM_LIST], group_ou,
1390 group_membership, security_flag, moira_list_id);
1400 com_err(whoami, 0, "removing user %s from list %s", user_name,
1404 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1406 if (!ProcessMachineContainer)
1408 com_err(whoami, 0, "Process machines and containers disabled, "
1413 memset(machine_ou, '\0', sizeof(machine_ou));
1414 memset(NewMachineName, '\0', sizeof(NewMachineName));
1415 if (get_machine_ou(ldap_handle, dn_path, ptr[LM_MEMBER],
1416 machine_ou, NewMachineName))
1418 if (ptr[LM_MEMBER] != NULL)
1419 free(ptr[LM_MEMBER]);
1420 ptr[LM_MEMBER] = strdup(NewMachineName);
1421 pUserOu = machine_ou;
1424 if (!strcasecmp(ptr[LM_TYPE], "STRING"))
1426 strcpy(member, ptr[LM_MEMBER]);
1430 if((s = strchr(member, '@')) == (char *) NULL)
1432 strcat(member, "@mit.edu");
1434 if (ptr[LM_MEMBER] != NULL)
1435 free(ptr[LM_MEMBER]);
1436 ptr[LM_MEMBER] = strdup(member);
1439 if(!strncasecmp(&member[strlen(member) - 6], ".LOCAL", 6))
1441 s = strrchr(member, '.');
1443 strcat(s, ".mit.edu");
1445 if (ptr[LM_MEMBER] != NULL)
1446 free(ptr[LM_MEMBER]);
1447 ptr[LM_MEMBER] = strdup(member);
1451 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER],
1455 pUserOu = contact_ou;
1457 else if (!strcasecmp(ptr[LM_TYPE], "KERBEROS"))
1459 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER],
1463 pUserOu = kerberos_ou;
1466 if (rc = moira_connect()) {
1467 critical_alert("Ldap incremental",
1468 "Error contacting Moira server : %s",
1473 if (rc = populate_group(ldap_handle, dn_path, group_name,
1474 group_ou, group_membership,
1475 security_flag, moira_list_id))
1476 com_err(whoami, 0, "Unable to remove %s from group %s", user_name,
1481 if (!strcasecmp(ptr[LM_TYPE], "STRING"))
1483 if (rc = moira_connect())
1485 critical_alert("Ldap incremental",
1486 "Error contacting Moira server : %s",
1491 if (rc = populate_group(ldap_handle, dn_path, group_name,
1492 group_ou, group_membership, security_flag,
1494 com_err(whoami, 0, "Unable to remove %s from group %s",
1495 user_name, group_name);
1502 com_err(whoami, 0, "Adding %s to list %s", user_name, group_name);
1505 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1507 memset(machine_ou, '\0', sizeof(machine_ou));
1508 memset(NewMachineName, '\0', sizeof(NewMachineName));
1510 if (get_machine_ou(ldap_handle, dn_path, ptr[LM_MEMBER], machine_ou,
1514 if (ptr[LM_MEMBER] != NULL)
1515 free(ptr[LM_MEMBER]);
1517 ptr[LM_MEMBER] = strdup(NewMachineName);
1518 pUserOu = machine_ou;
1520 else if (!strcasecmp(ptr[LM_TYPE], "STRING"))
1522 strcpy(member, ptr[LM_MEMBER]);
1526 if((s = strchr(member, '@')) == (char *) NULL)
1528 strcat(member, "@mit.edu");
1530 if (ptr[LM_MEMBER] != NULL)
1531 free(ptr[LM_MEMBER]);
1532 ptr[LM_MEMBER] = strdup(member);
1535 if(!strncasecmp(&member[strlen(member) - 6], ".LOCAL", 6))
1537 s = strrchr(member, '.');
1539 strcat(s, ".mit.edu");
1541 if (ptr[LM_MEMBER] != NULL)
1542 free(ptr[LM_MEMBER]);
1543 ptr[LM_MEMBER] = strdup(member);
1547 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER],
1551 pUserOu = contact_ou;
1553 else if (!strcasecmp(ptr[LM_TYPE], "KERBEROS"))
1555 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER],
1559 pUserOu = kerberos_ou;
1561 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
1563 if ((rc = check_user(ldap_handle, dn_path, ptr[LM_MEMBER],
1564 moira_user_id)) == AD_NO_USER_FOUND)
1566 if (rc = moira_connect())
1568 critical_alert("Ldap incremental",
1569 "Error connection to Moira : %s",
1574 com_err(whoami, 0, "creating user %s", ptr[LM_MEMBER]);
1575 av[0] = ptr[LM_MEMBER];
1576 call_args[0] = (char *)ldap_handle;
1577 call_args[1] = dn_path;
1578 call_args[2] = moira_user_id;
1579 call_args[3] = NULL;
1588 sprintf(filter, "(&(objectClass=group)(cn=%s))", ptr[LM_MEMBER]);
1589 attr_array[0] = "cn";
1590 attr_array[1] = NULL;
1591 if ((rc = linklist_build(ldap_handle, dn_path, filter,
1592 attr_array, &group_base, &group_count,
1593 LDAP_SCOPE_SUBTREE)) != 0)
1595 com_err(whoami, 0, "Unable to process user %s : %s",
1596 ptr[LM_MEMBER], ldap_err2string(rc));
1602 com_err(whoami, 0, "Object already exists with name %s",
1607 linklist_free(group_base);
1612 if (rc = mr_query("get_user_account_by_login", 1, av,
1613 save_query_info, save_argv))
1616 com_err(whoami, 0, "Unable to create user %s : %s",
1617 ptr[LM_MEMBER], error_message(rc));
1621 if (rc = user_create(U_END, save_argv, call_args))
1624 com_err(whoami, 0, "Unable to create user %s", ptr[LM_MEMBER]);
1631 com_err(whoami, 0, "Unable to create user %s", ptr[LM_MEMBER]);
1643 if (rc = moira_connect()) {
1644 critical_alert("Ldap incremental",
1645 "Error contacting Moira server : %s",
1650 if (rc = populate_group(ldap_handle, dn_path, group_name,
1651 group_ou, group_membership, security_flag,
1653 com_err(whoami, 0, "Unable to add %s to group %s", user_name,
1658 if (!strcasecmp(ptr[LM_TYPE], "STRING"))
1660 if (rc = moira_connect())
1662 critical_alert("Ldap incremental",
1663 "Error contacting Moira server : %s",
1668 if (rc = populate_group(ldap_handle, dn_path, group_name,
1669 group_ou, group_membership, security_flag,
1671 com_err(whoami, 0, "Unable to add %s to group %s",
1672 user_name, group_name);
1681 #define U_USER_ID 10
1682 #define U_HOMEDIR 11
1683 #define U_PROFILEDIR 12
1685 void do_user(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
1686 char **before, int beforec, char **after,
1689 LK_ENTRY *group_base;
1692 char *attr_array[3];
1695 char after_user_id[32];
1696 char before_user_id[32];
1698 char *save_argv[U_END];
1700 if ((beforec == 0) && (afterc == 0))
1703 memset(after_user_id, '\0', sizeof(after_user_id));
1704 memset(before_user_id, '\0', sizeof(before_user_id));
1706 if (beforec > U_USER_ID)
1707 strcpy(before_user_id, before[U_USER_ID]);
1709 if (afterc > U_USER_ID)
1710 strcpy(after_user_id, after[U_USER_ID]);
1712 if ((beforec == 0) && (afterc == 0)) /*this case should never happen */
1715 if ((beforec == 0) && (afterc != 0))
1717 /*this case only happens when the account*/
1718 /*account is first created but not usable*/
1720 com_err(whoami, 0, "Unable to process user %s because the user account "
1721 "is not yet usable", after[U_NAME]);
1725 /*this case only happens when the account is expunged */
1727 if ((beforec != 0) && (afterc == 0))
1729 if (atoi(before[U_STATE]) == 0)
1731 com_err(whoami, 0, "expunging user %s from directory",
1733 user_delete(ldap_handle, dn_path, before[U_NAME], before_user_id);
1737 com_err(whoami, 0, "Unable to process because user %s has been "
1738 "previously expungeded", before[U_NAME]);
1743 /*process anything that gets here*/
1745 if ((rc = check_user(ldap_handle, dn_path, before[U_NAME],
1746 before_user_id)) == AD_NO_USER_FOUND)
1748 if (!check_string(after[U_NAME]))
1751 if (rc = moira_connect())
1753 critical_alert("Ldap incremental",
1754 "Error connection to Moira : %s",
1759 com_err(whoami, 0, "creating user %s", after[U_NAME]);
1761 av[0] = after[U_NAME];
1762 call_args[0] = (char *)ldap_handle;
1763 call_args[1] = dn_path;
1764 call_args[2] = after_user_id;
1765 call_args[3] = NULL;
1773 sprintf(filter, "(&(objectClass=group)(cn=%s))", after[U_NAME]);
1774 attr_array[0] = "cn";
1775 attr_array[1] = NULL;
1777 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
1778 &group_base, &group_count,
1779 LDAP_SCOPE_SUBTREE)) != 0)
1781 com_err(whoami, 0, "Unable to process user %s : %s",
1782 after[U_NAME], ldap_err2string(rc));
1786 if (group_count >= 1)
1788 com_err(whoami, 0, "Object already exists with name %s",
1793 linklist_free(group_base);
1798 if (rc = mr_query("get_user_account_by_login", 1, av,
1799 save_query_info, save_argv))
1802 com_err(whoami, 0, "Unable to create user %s : %s",
1803 after[U_NAME], error_message(rc));
1807 if (rc = user_create(U_END, save_argv, call_args))
1809 com_err(whoami, 0, "Unable to create user %s : %s",
1810 after[U_NAME], error_message(rc));
1817 com_err(whoami, 0, "Unable to create user %s", after[U_NAME]);
1829 if (strcmp(before[U_NAME], after[U_NAME]))
1831 if ((check_string(before[U_NAME])) && (check_string(after[U_NAME])))
1833 com_err(whoami, 0, "changing user %s to %s",
1834 before[U_NAME], after[U_NAME]);
1836 if ((rc = user_rename(ldap_handle, dn_path, before[U_NAME],
1837 after[U_NAME])) != LDAP_SUCCESS)
1844 com_err(whoami, 0, "updating user %s information", after[U_NAME]);
1845 rc = user_update(ldap_handle, dn_path, after[U_NAME],
1846 after[U_UID], after[U_MITID],
1847 after_user_id, atoi(after[U_STATE]),
1848 after[U_HOMEDIR], after[U_PROFILEDIR],
1849 after[U_FIRST], after[U_MIDDLE], after[U_LAST],
1850 after[U_SHELL], after[U_CLASS]);
1855 int construct_newvalues(LK_ENTRY *linklist_base, int modvalue_count,
1856 char *oldValue, char *newValue,
1857 char ***modvalues, int type)
1859 LK_ENTRY *linklist_ptr;
1863 if (((*modvalues) = calloc(1,
1864 (modvalue_count + 1) * sizeof(char *))) == NULL)
1869 for (i = 0; i < (modvalue_count + 1); i++)
1870 (*modvalues)[i] = NULL;
1872 if (modvalue_count != 0)
1874 linklist_ptr = linklist_base;
1875 for (i = 0; i < modvalue_count; i++)
1877 if ((oldValue != NULL) && (newValue != NULL))
1879 if ((cPtr = (char *)strstr(linklist_ptr->value, oldValue))
1882 if (type == REPLACE)
1884 if (((*modvalues)[i] = calloc(1, strlen(newValue) + 1))
1887 memset((*modvalues)[i], '\0', strlen(newValue) + 1);
1888 strcpy((*modvalues)[i], newValue);
1892 if (((*modvalues)[i] = calloc(1,
1893 (int)(cPtr - linklist_ptr->value) +
1894 (linklist_ptr->length -
1896 strlen(newValue) + 1)) == NULL)
1898 memset((*modvalues)[i], '\0',
1899 (int)(cPtr - linklist_ptr->value) +
1900 (linklist_ptr->length - strlen(oldValue)) +
1901 strlen(newValue) + 1);
1902 memcpy((*modvalues)[i], linklist_ptr->value,
1903 (int)(cPtr - linklist_ptr->value));
1904 strcat((*modvalues)[i], newValue);
1905 strcat((*modvalues)[i],
1906 &linklist_ptr->value[(int)(cPtr -
1907 linklist_ptr->value) + strlen(oldValue)]);
1912 (*modvalues)[i] = calloc(1, linklist_ptr->length + 1);
1913 memset((*modvalues)[i], '\0', linklist_ptr->length + 1);
1914 memcpy((*modvalues)[i], linklist_ptr->value,
1915 linklist_ptr->length);
1920 (*modvalues)[i] = calloc(1, linklist_ptr->length + 1);
1921 memset((*modvalues)[i], '\0', linklist_ptr->length + 1);
1922 memcpy((*modvalues)[i], linklist_ptr->value,
1923 linklist_ptr->length);
1925 linklist_ptr = linklist_ptr->next;
1927 (*modvalues)[i] = NULL;
1933 int linklist_build(LDAP *ldap_handle, char *dn_path, char *search_exp,
1934 char **attr_array, LK_ENTRY **linklist_base,
1935 int *linklist_count, unsigned long ScopeType)
1938 LDAPMessage *ldap_entry;
1942 (*linklist_base) = NULL;
1943 (*linklist_count) = 0;
1945 if ((rc = ldap_search_s(ldap_handle, dn_path, ScopeType,
1946 search_exp, attr_array, 0,
1947 &ldap_entry)) != LDAP_SUCCESS)
1949 if (rc != LDAP_SIZELIMIT_EXCEEDED)
1953 rc = retrieve_entries(ldap_handle, ldap_entry, linklist_base,
1956 ldap_msgfree(ldap_entry);
1960 int retrieve_entries(LDAP *ldap_handle, LDAPMessage *ldap_entry,
1961 LK_ENTRY **linklist_base, int *linklist_count)
1963 char distinguished_name[1024];
1964 LK_ENTRY *linklist_ptr;
1967 if ((ldap_entry = ldap_first_entry(ldap_handle, ldap_entry)) == NULL)
1970 memset(distinguished_name, '\0', sizeof(distinguished_name));
1971 get_distinguished_name(ldap_handle, ldap_entry, distinguished_name);
1973 if ((rc = retrieve_attributes(ldap_handle, ldap_entry, distinguished_name,
1974 linklist_base)) != 0)
1977 while ((ldap_entry = ldap_next_entry(ldap_handle, ldap_entry)) != NULL)
1979 memset(distinguished_name, '\0', sizeof(distinguished_name));
1980 get_distinguished_name(ldap_handle, ldap_entry, distinguished_name);
1982 if ((rc = retrieve_attributes(ldap_handle, ldap_entry,
1983 distinguished_name, linklist_base)) != 0)
1987 linklist_ptr = (*linklist_base);
1988 (*linklist_count) = 0;
1990 while (linklist_ptr != NULL)
1992 ++(*linklist_count);
1993 linklist_ptr = linklist_ptr->next;
1999 int retrieve_attributes(LDAP *ldap_handle, LDAPMessage *ldap_entry,
2000 char *distinguished_name, LK_ENTRY **linklist_current)
2007 if ((Attribute = ldap_first_attribute(ldap_handle, ldap_entry,
2010 retrieve_values(ldap_handle, ldap_entry, Attribute, distinguished_name,
2012 ldap_memfree(Attribute);
2013 while ((Attribute = ldap_next_attribute(ldap_handle, ldap_entry,
2016 retrieve_values(ldap_handle, ldap_entry, Attribute,
2017 distinguished_name, linklist_current);
2018 ldap_memfree(Attribute);
2022 ldap_ber_free(ptr, 0);
2027 int retrieve_values(LDAP *ldap_handle, LDAPMessage *ldap_entry,
2028 char *Attribute, char *distinguished_name,
2029 LK_ENTRY **linklist_current)
2035 LK_ENTRY *linklist_previous;
2036 LDAP_BERVAL **ber_value;
2045 SID_IDENTIFIER_AUTHORITY *sid_auth;
2046 unsigned char *subauth_count;
2047 #endif /*LDAP_BEGUG*/
2050 memset(temp, '\0', sizeof(temp));
2052 if ((!strcmp(Attribute, "objectSid")) ||
2053 (!strcmp(Attribute, "objectGUID")))
2058 ber_value = ldap_get_values_len(ldap_handle, ldap_entry, Attribute);
2059 Ptr = (void **)ber_value;
2064 str_value = ldap_get_values(ldap_handle, ldap_entry, Attribute);
2065 Ptr = (void **)str_value;
2073 if ((linklist_previous = calloc(1, sizeof(LK_ENTRY))) == NULL)
2076 memset(linklist_previous, '\0', sizeof(LK_ENTRY));
2077 linklist_previous->next = (*linklist_current);
2078 (*linklist_current) = linklist_previous;
2080 if (((*linklist_current)->attribute = calloc(1,
2081 strlen(Attribute) + 1)) == NULL)
2084 memset((*linklist_current)->attribute, '\0', strlen(Attribute) + 1);
2085 strcpy((*linklist_current)->attribute, Attribute);
2089 ber_length = (*(LDAP_BERVAL **)Ptr)->bv_len;
2091 if (((*linklist_current)->value = calloc(1, ber_length)) == NULL)
2094 memset((*linklist_current)->value, '\0', ber_length);
2095 memcpy((*linklist_current)->value,
2096 (*(LDAP_BERVAL **)Ptr)->bv_val, ber_length);
2097 (*linklist_current)->length = ber_length;
2101 if (((*linklist_current)->value = calloc(1,
2102 strlen(*Ptr) + 1)) == NULL)
2105 memset((*linklist_current)->value, '\0', strlen(*Ptr) + 1);
2106 (*linklist_current)->length = strlen(*Ptr);
2107 strcpy((*linklist_current)->value, *Ptr);
2110 (*linklist_current)->ber_value = use_bervalue;
2112 if (((*linklist_current)->dn = calloc(1,
2113 strlen(distinguished_name) + 1)) == NULL)
2116 memset((*linklist_current)->dn, '\0',
2117 strlen(distinguished_name) + 1);
2118 strcpy((*linklist_current)->dn, distinguished_name);
2121 if (!strcmp(Attribute, "objectGUID"))
2123 guid = (GUID *)((*linklist_current)->value);
2125 "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
2126 guid->Data1, guid->Data2, guid->Data3,
2127 guid->Data4[0], guid->Data4[1], guid->Data4[2],
2128 guid->Data4[3], guid->Data4[4], guid->Data4[5],
2129 guid->Data4[6], guid->Data4[7]);
2130 print_to_screen(" %20s : {%s}\n", Attribute, temp);
2132 else if (!strcmp(Attribute, "objectSid"))
2134 sid = (SID *)((*(LDAP_BERVAL **)Ptr)->bv_val);
2137 print_to_screen(" Revision = %d\n", sid->Revision);
2138 print_to_screen(" SID Identifier Authority:\n");
2139 sid_auth = &sid->IdentifierAuthority;
2140 if (sid_auth->Value[0])
2141 print_to_screen(" SECURITY_NULL_SID_AUTHORITY\n");
2142 else if (sid_auth->Value[1])
2143 print_to_screen(" SECURITY_WORLD_SID_AUTHORITY\n");
2144 else if (sid_auth->Value[2])
2145 print_to_screen(" SECURITY_LOCAL_SID_AUTHORITY\n");
2146 else if (sid_auth->Value[3])
2147 print_to_screen(" SECURITY_CREATOR_SID_AUTHORITY\n");
2148 else if (sid_auth->Value[5])
2149 print_to_screen(" SECURITY_NT_AUTHORITY\n");
2151 print_to_screen(" UNKNOWN SID AUTHORITY\n");
2152 subauth_count = GetSidSubAuthorityCount(sid);
2153 print_to_screen(" SidSubAuthorityCount = %d\n",
2155 print_to_screen(" SidSubAuthority:\n");
2156 for (i = 0; i < *subauth_count; i++)
2158 if ((subauth = GetSidSubAuthority(sid, i)) != NULL)
2159 print_to_screen(" %u\n", *subauth);
2163 else if ((!memcmp(Attribute, "userAccountControl",
2164 strlen("userAccountControl"))) ||
2165 (!memcmp(Attribute, "sAMAccountType",
2166 strlen("sAmAccountType"))))
2168 intValue = atoi(*Ptr);
2169 print_to_screen(" %20s : %ld\n",Attribute, intValue);
2171 if (!memcmp(Attribute, "userAccountControl",
2172 strlen("userAccountControl")))
2174 if (intValue & UF_ACCOUNTDISABLE)
2175 print_to_screen(" %20s : %s\n",
2176 "", "Account disabled");
2178 print_to_screen(" %20s : %s\n",
2179 "", "Account active");
2180 if (intValue & UF_HOMEDIR_REQUIRED)
2181 print_to_screen(" %20s : %s\n",
2182 "", "Home directory required");
2183 if (intValue & UF_LOCKOUT)
2184 print_to_screen(" %20s : %s\n",
2185 "", "Account locked out");
2186 if (intValue & UF_PASSWD_NOTREQD)
2187 print_to_screen(" %20s : %s\n",
2188 "", "No password required");
2189 if (intValue & UF_PASSWD_CANT_CHANGE)
2190 print_to_screen(" %20s : %s\n",
2191 "", "Cannot change password");
2192 if (intValue & UF_TEMP_DUPLICATE_ACCOUNT)
2193 print_to_screen(" %20s : %s\n",
2194 "", "Temp duplicate account");
2195 if (intValue & UF_NORMAL_ACCOUNT)
2196 print_to_screen(" %20s : %s\n",
2197 "", "Normal account");
2198 if (intValue & UF_INTERDOMAIN_TRUST_ACCOUNT)
2199 print_to_screen(" %20s : %s\n",
2200 "", "Interdomain trust account");
2201 if (intValue & UF_WORKSTATION_TRUST_ACCOUNT)
2202 print_to_screen(" %20s : %s\n",
2203 "", "Workstation trust account");
2204 if (intValue & UF_SERVER_TRUST_ACCOUNT)
2205 print_to_screen(" %20s : %s\n",
2206 "", "Server trust account");
2211 print_to_screen(" %20s : %s\n",Attribute, *Ptr);
2213 #endif /*LDAP_DEBUG*/
2216 if (str_value != NULL)
2217 ldap_value_free(str_value);
2219 if (ber_value != NULL)
2220 ldap_value_free_len(ber_value);
2223 (*linklist_current) = linklist_previous;
2228 int moira_connect(void)
2233 if (!mr_connections++)
2237 memset(HostName, '\0', sizeof(HostName));
2238 strcpy(HostName, "ttsp");
2239 rc = mr_connect_cl(HostName, "ldap.incr", QUERY_VERSION, 1);
2243 rc = mr_connect_cl(uts.nodename, "ldap.incr", QUERY_VERSION, 1);
2252 int check_winad(void)
2256 for (i = 0; file_exists(STOP_FILE); i++)
2260 critical_alert("Ldap incremental",
2261 "Ldap incremental failed (%s exists): %s",
2262 STOP_FILE, tbl_buf);
2272 int moira_disconnect(void)
2275 if (!--mr_connections)
2283 void get_distinguished_name(LDAP *ldap_handle, LDAPMessage *ldap_entry,
2284 char *distinguished_name)
2288 CName = ldap_get_dn(ldap_handle, ldap_entry);
2293 strcpy(distinguished_name, CName);
2294 ldap_memfree(CName);
2297 int linklist_create_entry(char *attribute, char *value,
2298 LK_ENTRY **linklist_entry)
2300 (*linklist_entry) = calloc(1, sizeof(LK_ENTRY));
2302 if (!(*linklist_entry))
2307 memset((*linklist_entry), '\0', sizeof(LK_ENTRY));
2308 (*linklist_entry)->attribute = calloc(1, strlen(attribute) + 1);
2309 memset((*linklist_entry)->attribute, '\0', strlen(attribute) + 1);
2310 strcpy((*linklist_entry)->attribute, attribute);
2311 (*linklist_entry)->value = calloc(1, strlen(value) + 1);
2312 memset((*linklist_entry)->value, '\0', strlen(value) + 1);
2313 strcpy((*linklist_entry)->value, value);
2314 (*linklist_entry)->length = strlen(value);
2315 (*linklist_entry)->next = NULL;
2320 void print_to_screen(const char *fmt, ...)
2324 va_start(pvar, fmt);
2325 vfprintf(stderr, fmt, pvar);
2330 int get_group_membership(char *group_membership, char *group_ou,
2331 int *security_flag, char **av)
2336 maillist_flag = atoi(av[L_MAILLIST]);
2337 group_flag = atoi(av[L_GROUP]);
2339 if (security_flag != NULL)
2340 (*security_flag) = 0;
2342 if ((maillist_flag) && (group_flag))
2344 if (group_membership != NULL)
2345 group_membership[0] = 'B';
2347 if (security_flag != NULL)
2348 (*security_flag) = 1;
2350 if (group_ou != NULL)
2351 strcpy(group_ou, group_ou_both);
2353 else if ((!maillist_flag) && (group_flag))
2355 if (group_membership != NULL)
2356 group_membership[0] = 'S';
2358 if (security_flag != NULL)
2359 (*security_flag) = 1;
2361 if (group_ou != NULL)
2362 strcpy(group_ou, group_ou_security);
2364 else if ((maillist_flag) && (!group_flag))
2366 if (group_membership != NULL)
2367 group_membership[0] = 'D';
2369 if (group_ou != NULL)
2370 strcpy(group_ou, group_ou_distribution);
2374 if (group_membership != NULL)
2375 group_membership[0] = 'N';
2377 if (group_ou != NULL)
2378 strcpy(group_ou, group_ou_neither);
2384 int group_rename(LDAP *ldap_handle, char *dn_path,
2385 char *before_group_name, char *before_group_membership,
2386 char *before_group_ou, int before_security_flag,
2387 char *before_desc, char *after_group_name,
2388 char *after_group_membership, char *after_group_ou,
2389 int after_security_flag, char *after_desc,
2390 char *MoiraId, char *filter, char *maillist)
2395 char new_dn_path[512];
2398 char mail_nickname[256];
2399 char proxy_address[256];
2400 char address_book[256];
2401 char *attr_array[3];
2402 char *mitMoiraId_v[] = {NULL, NULL};
2403 char *name_v[] = {NULL, NULL};
2404 char *samAccountName_v[] = {NULL, NULL};
2405 char *groupTypeControl_v[] = {NULL, NULL};
2406 char *mail_v[] = {NULL, NULL};
2407 char *proxy_address_v[] = {NULL, NULL};
2408 char *mail_nickname_v[] = {NULL, NULL};
2409 char *report_to_originator_v[] = {NULL, NULL};
2410 char *address_book_v[] = {NULL, NULL};
2411 char *legacy_exchange_dn_v[] = {NULL, NULL};
2412 u_int groupTypeControl;
2413 char groupTypeControlStr[80];
2414 char contact_mail[256];
2418 LK_ENTRY *group_base;
2420 int MailDisabled = 0;
2422 if(UseGroupUniversal)
2423 groupTypeControl = ADS_GROUP_TYPE_UNIVERSAL_GROUP;
2425 groupTypeControl = ADS_GROUP_TYPE_GLOBAL_GROUP;
2427 if (!check_string(before_group_name))
2430 "Unable to process invalid LDAP list name %s",
2432 return(AD_INVALID_NAME);
2435 if (!check_string(after_group_name))
2438 "Unable to process invalid LDAP list name %s", after_group_name);
2439 return(AD_INVALID_NAME);
2449 sprintf(filter, "(&(objectClass=user)(cn=%s))", after_group_name);
2450 attr_array[0] = "cn";
2451 attr_array[1] = NULL;
2453 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
2454 &group_base, &group_count,
2455 LDAP_SCOPE_SUBTREE)) != 0)
2457 com_err(whoami, 0, "Unable to process group %s : %s",
2458 after_group_name, ldap_err2string(rc));
2464 com_err(whoami, 0, "Object already exists with name %s",
2469 linklist_free(group_base);
2478 if (rc = ad_get_group(ldap_handle, dn_path, before_group_name,
2479 before_group_membership,
2480 MoiraId, "samAccountName", &group_base,
2481 &group_count, filter))
2484 if (group_count == 0)
2486 return(AD_NO_GROUPS_FOUND);
2489 if (group_count != 1)
2491 com_err(whoami, 0, "Unable to process multiple groups with "
2492 "MoiraId = %s exist in the directory", MoiraId);
2493 return(AD_MULTIPLE_GROUPS_FOUND);
2496 strcpy(old_dn, group_base->dn);
2498 linklist_free(group_base);
2501 attr_array[0] = "sAMAccountName";
2502 attr_array[1] = NULL;
2504 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
2505 &group_base, &group_count,
2506 LDAP_SCOPE_SUBTREE)) != 0)
2508 com_err(whoami, 0, "Unable to get list %s dn : %s",
2509 after_group_name, ldap_err2string(rc));
2513 if (group_count != 1)
2516 "Unable to get sAMAccountName for group %s",
2518 return(AD_LDAP_FAILURE);
2521 strcpy(sam_name, group_base->value);
2522 linklist_free(group_base);
2526 sprintf(new_dn_path, "%s,%s", after_group_ou, dn_path);
2527 sprintf(new_dn, "cn=%s", after_group_name);
2528 sprintf(mail, "%s@%s", after_group_name, lowercase(ldap_domain));
2529 sprintf(contact_mail, "%s@mit.edu", after_group_name);
2530 sprintf(proxy_address, "SMTP:%s@%s", after_group_name,
2531 lowercase(ldap_domain));
2532 sprintf(mail_nickname, "%s", after_group_name);
2534 com_err(whoami, 0, "Old %s New %s,%s", old_dn, new_dn, new_dn_path);
2536 if ((rc = ldap_rename_s(ldap_handle, old_dn, new_dn, new_dn_path,
2537 TRUE, NULL, NULL)) != LDAP_SUCCESS)
2539 com_err(whoami, 0, "Unable to rename list from %s to %s : %s",
2540 before_group_name, after_group_name, ldap_err2string(rc));
2544 name_v[0] = after_group_name;
2546 if (!strncmp(&sam_name[strlen(sam_name) - strlen(group_suffix)],
2547 group_suffix, strlen(group_suffix)))
2549 sprintf(sam_name, "%s%s", after_group_name, group_suffix);
2554 "Unable to rename list from %s to %s : sAMAccountName not found",
2555 before_group_name, after_group_name);
2559 samAccountName_v[0] = sam_name;
2561 if (after_security_flag)
2562 groupTypeControl |= ADS_GROUP_TYPE_SECURITY_ENABLED;
2564 sprintf(groupTypeControlStr, "%ld", groupTypeControl);
2565 groupTypeControl_v[0] = groupTypeControlStr;
2566 mitMoiraId_v[0] = MoiraId;
2568 sprintf(new_dn, "cn=%s,%s,%s", after_group_name, after_group_ou, dn_path);
2569 rc = attribute_update(ldap_handle, new_dn, after_desc, "description",
2572 ADD_ATTR("samAccountName", samAccountName_v, LDAP_MOD_REPLACE);
2573 ADD_ATTR("displayName", name_v, LDAP_MOD_REPLACE);
2574 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
2575 ADD_ATTR("groupType", groupTypeControl_v, LDAP_MOD_REPLACE);
2579 if(atoi(maillist) && !MailDisabled && email_isvalid(mail))
2581 mail_nickname_v[0] = mail_nickname;
2582 proxy_address_v[0] = proxy_address;
2584 report_to_originator_v[0] = "TRUE";
2586 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
2587 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2588 ADD_ATTR("proxyAddresses", proxy_address_v, LDAP_MOD_REPLACE);
2589 ADD_ATTR("reportToOriginator", report_to_originator_v,
2594 mail_nickname_v[0] = NULL;
2595 proxy_address_v[0] = NULL;
2597 legacy_exchange_dn_v[0] = NULL;
2598 address_book_v[0] = NULL;
2599 report_to_originator_v[0] = NULL;
2601 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
2602 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2603 ADD_ATTR("proxyAddresses", proxy_address_v, LDAP_MOD_REPLACE);
2604 ADD_ATTR("legacyExchangeDN", legacy_exchange_dn_v, LDAP_MOD_REPLACE);
2605 ADD_ATTR("showInAddressBook", address_book_v, LDAP_MOD_REPLACE);
2606 ADD_ATTR("reportToOriginator", report_to_originator_v,
2612 if(atoi(maillist) && email_isvalid(contact_mail))
2614 mail_v[0] = contact_mail;
2615 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2621 if ((rc = ldap_modify_s(ldap_handle, new_dn, mods)) != LDAP_SUCCESS)
2624 "Unable to modify list data for %s after renaming: %s",
2625 after_group_name, ldap_err2string(rc));
2628 for (i = 0; i < n; i++)
2634 int group_create(int ac, char **av, void *ptr)
2639 char new_group_name[256];
2640 char sam_group_name[256];
2641 char cn_group_name[256];
2643 char contact_mail[256];
2644 char mail_nickname[256];
2645 char proxy_address[256];
2646 char address_book[256];
2647 char *cn_v[] = {NULL, NULL};
2648 char *objectClass_v[] = {"top", "group", NULL};
2649 char *objectClass_ldap_v[] = {"top", "microsoftComTop", "securityPrincipal",
2650 "group", "mailRecipient", NULL};
2652 char *samAccountName_v[] = {NULL, NULL};
2653 char *altSecurityIdentities_v[] = {NULL, NULL};
2654 char *member_v[] = {NULL, NULL};
2655 char *name_v[] = {NULL, NULL};
2656 char *desc_v[] = {NULL, NULL};
2657 char *info_v[] = {NULL, NULL};
2658 char *mitMoiraId_v[] = {NULL, NULL};
2659 char *mitMoiraPublic_v[] = {NULL, NULL};
2660 char *mitMoiraHidden_v[] = {NULL, NULL};
2661 char *groupTypeControl_v[] = {NULL, NULL};
2662 char *mail_v[] = {NULL, NULL};
2663 char *proxy_address_v[] = {NULL, NULL};
2664 char *mail_nickname_v[] = {NULL, NULL};
2665 char *report_to_originator_v[] = {NULL, NULL};
2666 char *address_book_v[] = {NULL, NULL};
2667 char *legacy_exchange_dn_v[] = {NULL, NULL};
2668 char *gidNumber_v[] = {NULL, NULL};
2669 char groupTypeControlStr[80];
2670 char group_membership[1];
2673 u_int groupTypeControl;
2677 int MailDisabled = 0;
2679 LK_ENTRY *group_base;
2682 char *attr_array[3];
2686 if(UseGroupUniversal)
2687 groupTypeControl = ADS_GROUP_TYPE_UNIVERSAL_GROUP;
2689 groupTypeControl = ADS_GROUP_TYPE_GLOBAL_GROUP;
2691 if (!check_string(av[L_NAME]))
2693 com_err(whoami, 0, "Unable to process invalid LDAP list name %s",
2695 return(AD_INVALID_NAME);
2698 updateGroup = (int)call_args[4];
2699 memset(group_ou, 0, sizeof(group_ou));
2700 memset(group_membership, 0, sizeof(group_membership));
2703 get_group_membership(group_membership, group_ou, &security_flag, av);
2705 strcpy(new_group_name, av[L_NAME]);
2706 sprintf(new_dn, "cn=%s,%s,%s", new_group_name, group_ou, call_args[1]);
2707 sprintf(contact_mail, "%s@mit.edu", av[L_NAME]);
2708 sprintf(mail, "%s@%s", av[L_NAME], lowercase(ldap_domain));
2709 sprintf(mail_nickname, "%s", av[L_NAME]);
2712 groupTypeControl |= ADS_GROUP_TYPE_SECURITY_ENABLED;
2714 sprintf(sam_group_name, "%s%s", av[L_NAME], group_suffix);
2718 sprintf(groupTypeControlStr, "%ld", groupTypeControl);
2719 groupTypeControl_v[0] = groupTypeControlStr;
2721 strcpy(cn_group_name, av[L_NAME]);
2723 samAccountName_v[0] = sam_group_name;
2724 name_v[0] = new_group_name;
2725 cn_v[0] = new_group_name;
2728 ADD_ATTR("cn", cn_v, LDAP_MOD_ADD);
2732 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
2736 mitMoiraPublic_v[0] = av[L_PUBLIC];
2737 mitMoiraHidden_v[0] = av[L_HIDDEN];
2738 ADD_ATTR("objectClass", objectClass_ldap_v, LDAP_MOD_ADD);
2739 ADD_ATTR("mitMoiraPublic", mitMoiraPublic_v, LDAP_MOD_ADD);
2740 ADD_ATTR("mitMoiraHidden", mitMoiraHidden_v, LDAP_MOD_ADD);
2742 if(atoi(av[L_GROUP]))
2744 gidNumber_v[0] = av[L_GID];
2745 ADD_ATTR("gidNumber", gidNumber_v, LDAP_MOD_ADD);
2749 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_ADD);
2750 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
2751 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
2755 if(atoi(av[L_MAILLIST]))
2760 sprintf(filter, "(&(objectClass=user)(cn=%s))", av[L_NAME]);
2761 attr_array[0] = "cn";
2762 attr_array[1] = NULL;
2764 if ((rc = linklist_build((LDAP *)call_args[0], call_args[1],
2765 filter, attr_array, &group_base,
2767 LDAP_SCOPE_SUBTREE)) != 0)
2769 com_err(whoami, 0, "Unable to process group %s : %s",
2770 av[L_NAME], ldap_err2string(rc));
2776 com_err(whoami, 0, "Object already exists with name %s",
2781 linklist_free(group_base);
2786 if(atoi(av[L_MAILLIST]) && !MailDisabled && email_isvalid(mail))
2788 mail_nickname_v[0] = mail_nickname;
2789 report_to_originator_v[0] = "TRUE";
2791 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_ADD);
2792 ADD_ATTR("reportToOriginator", report_to_originator_v,
2798 if(atoi(av[L_MAILLIST]) && email_isvalid(contact_mail))
2800 mail_v[0] = contact_mail;
2801 ADD_ATTR("mail", mail_v, LDAP_MOD_ADD);
2805 if (strlen(av[L_DESC]) != 0)
2807 desc_v[0] = av[L_DESC];
2808 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
2811 ADD_ATTR("groupType", groupTypeControl_v, LDAP_MOD_ADD);
2813 if (strlen(av[L_ACE_NAME]) != 0)
2815 sprintf(info, "The Administrator of this list is: %s",
2818 ADD_ATTR("info", info_v, LDAP_MOD_ADD);
2821 if (strlen(call_args[5]) != 0)
2823 mitMoiraId_v[0] = call_args[5];
2824 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_ADD);
2829 rc = ldap_add_ext_s((LDAP *)call_args[0], new_dn, mods, NULL, NULL);
2831 for (i = 0; i < n; i++)
2834 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
2836 com_err(whoami, 0, "Unable to create list %s in directory : %s",
2837 av[L_NAME], ldap_err2string(rc));
2843 if ((rc == LDAP_ALREADY_EXISTS) || (updateGroup))
2845 rc = attribute_update((LDAP *)call_args[0], new_dn, av[L_DESC],
2846 "description", av[L_NAME]);
2847 sprintf(info, "The Administrator of this list is: %s", av[L_ACE_NAME]);
2849 rc = attribute_update((LDAP *)call_args[0], new_dn, info, "info",
2854 if (strlen(call_args[5]) != 0)
2856 mitMoiraId_v[0] = call_args[5];
2857 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
2860 if (!(atoi(av[L_ACTIVE])))
2863 ADD_ATTR("member", member_v, LDAP_MOD_REPLACE);
2866 if (!ActiveDirectory)
2868 mitMoiraPublic_v[0] = av[L_PUBLIC];
2869 mitMoiraHidden_v[0] = av[L_HIDDEN];
2870 ADD_ATTR("mitMoiraPublic", mitMoiraPublic_v, LDAP_MOD_REPLACE);
2871 ADD_ATTR("mitMoiraHidden", mitMoiraHidden_v, LDAP_MOD_REPLACE);
2873 if(atoi(av[L_GROUP]))
2875 gidNumber_v[0] = av[L_GID];
2876 ADD_ATTR("gidNumber", gidNumber_v, LDAP_MOD_REPLACE);
2880 ADD_ATTR("gidNumber", gidNumber_v, LDAP_MOD_REPLACE);
2886 if(atoi(av[L_MAILLIST]))
2891 sprintf(filter, "(&(objectClass=user)(cn=%s))", av[L_NAME]);
2892 attr_array[0] = "cn";
2893 attr_array[1] = NULL;
2895 if ((rc = linklist_build((LDAP *)call_args[0], call_args[1],
2896 filter, attr_array, &group_base,
2898 LDAP_SCOPE_SUBTREE)) != 0)
2900 com_err(whoami, 0, "Unable to process group %s : %s",
2901 av[L_NAME], ldap_err2string(rc));
2907 com_err(whoami, 0, "Object already exists with name %s",
2912 linklist_free(group_base);
2917 if (atoi(av[L_MAILLIST]) && !MailDisabled && email_isvalid(mail))
2919 mail_nickname_v[0] = mail_nickname;
2920 report_to_originator_v[0] = "TRUE";
2922 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
2923 ADD_ATTR("reportToOriginator", report_to_originator_v,
2929 mail_nickname_v[0] = NULL;
2930 proxy_address_v[0] = NULL;
2931 legacy_exchange_dn_v[0] = NULL;
2932 address_book_v[0] = NULL;
2933 report_to_originator_v[0] = NULL;
2935 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
2936 ADD_ATTR("proxyAddresses", proxy_address_v, LDAP_MOD_REPLACE);
2937 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2938 ADD_ATTR("legacyExchangeDN", legacy_exchange_dn_v,
2940 ADD_ATTR("showInAddressBook", address_book_v, LDAP_MOD_REPLACE);
2941 ADD_ATTR("reportToOriginator", report_to_originator_v,
2947 if (atoi(av[L_MAILLIST]) && email_isvalid(contact_mail))
2949 mail_v[0] = contact_mail;
2950 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2955 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
2964 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
2966 for (i = 0; i < n; i++)
2969 if (rc != LDAP_SUCCESS)
2971 com_err(whoami, 0, "Unable to update list %s in directory : %s",
2972 av[L_NAME], ldap_err2string(rc));
2979 ProcessGroupSecurity((LDAP *)call_args[0], call_args[1], av[L_NAME],
2980 atoi(av[L_HIDDEN]), av[L_ACE_TYPE], av[L_ACE_NAME]);
2982 return(LDAP_SUCCESS);
2985 int ProcessGroupSecurity(LDAP *ldap_handle, char *dn_path,
2986 char *TargetGroupName, int HiddenGroup,
2987 char *AceType, char *AceName)
2989 char filter_exp[1024];
2990 char *attr_array[5];
2991 char search_path[512];
2993 char TemplateDn[512];
2994 char TemplateSamName[128];
2996 char TargetSamName[128];
2997 char AceSamAccountName[128];
2999 unsigned char AceSid[128];
3000 unsigned char UserTemplateSid[128];
3001 char acBERBuf[N_SD_BER_BYTES];
3002 char GroupSecurityTemplate[256];
3003 char hide_addres_lists[256];
3004 char address_book[256];
3005 char *hide_address_lists_v[] = {NULL, NULL};
3006 char *address_book_v[] = {NULL, NULL};
3007 char *owner_v[] = {NULL, NULL};
3009 int UserTemplateSidCount;
3016 int array_count = 0;
3018 LK_ENTRY *group_base;
3019 LDAP_BERVAL **ppsValues;
3020 LDAPControl sControl = {"1.2.840.113556.1.4.801",
3021 { N_SD_BER_BYTES, acBERBuf },
3024 LDAPControl *apsServerControls[] = {&sControl, NULL};
3027 dwInfo = OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION |
3028 DACL_SECURITY_INFORMATION | SACL_SECURITY_INFORMATION;
3029 BEREncodeSecurityBits(dwInfo, acBERBuf);
3031 sprintf(search_path, "%s,%s", group_ou_root, dn_path);
3032 sprintf(filter_exp, "(sAMAccountName=%s%s)", TargetGroupName, group_suffix);
3033 attr_array[0] = "sAMAccountName";
3034 attr_array[1] = NULL;
3038 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
3039 &group_base, &group_count,
3040 LDAP_SCOPE_SUBTREE) != 0))
3043 if (group_count != 1)
3045 linklist_free(group_base);
3049 strcpy(TargetDn, group_base->dn);
3050 strcpy(TargetSamName, group_base->value);
3051 linklist_free(group_base);
3055 UserTemplateSidCount = 0;
3056 memset(UserTemplateSid, '\0', sizeof(UserTemplateSid));
3057 memset(AceSamAccountName, '\0', sizeof(AceSamAccountName));
3058 memset(AceSid, '\0', sizeof(AceSid));
3063 if (strlen(AceName) != 0)
3065 if (!strcmp(AceType, "LIST"))
3067 sprintf(AceSamAccountName, "%s%s", AceName, group_suffix);
3068 strcpy(root_ou, group_ou_root);
3070 else if (!strcmp(AceType, "USER"))
3072 sprintf(AceSamAccountName, "%s", AceName);
3073 strcpy(root_ou, user_ou);
3076 if (ActiveDirectory)
3078 if (strlen(AceSamAccountName) != 0)
3080 sprintf(search_path, "%s", dn_path);
3081 sprintf(filter_exp, "(sAMAccountName=%s)", AceSamAccountName);
3082 attr_array[0] = "objectSid";
3083 attr_array[1] = NULL;
3087 if ((rc = linklist_build(ldap_handle, search_path, filter_exp,
3088 attr_array, &group_base, &group_count,
3089 LDAP_SCOPE_SUBTREE) != 0))
3091 if (group_count == 1)
3093 strcpy(AceDn, group_base->dn);
3094 AceSidCount = group_base->length;
3095 memcpy(AceSid, group_base->value, AceSidCount);
3097 linklist_free(group_base);
3104 if (strlen(AceSamAccountName) != 0)
3106 sprintf(search_path, "%s", dn_path);
3107 sprintf(filter_exp, "(sAMAccountName=%s)", AceSamAccountName);
3108 attr_array[0] = "samAccountName";
3109 attr_array[1] = NULL;
3113 if ((rc = linklist_build(ldap_handle, search_path, filter_exp,
3114 attr_array, &group_base, &group_count,
3115 LDAP_SCOPE_SUBTREE) != 0))
3117 if (group_count == 1)
3119 strcpy(AceDn, group_base->dn);
3121 linklist_free(group_base);
3128 if (!ActiveDirectory)
3130 if (strlen(AceDn) != 0)
3132 owner_v[0] = strdup(AceDn);
3134 ADD_ATTR("owner", owner_v, LDAP_MOD_REPLACE);
3138 rc = ldap_modify_s(ldap_handle, TargetDn, mods);
3140 for (i = 0; i < n; i++)
3143 if (rc != LDAP_SUCCESS)
3144 com_err(whoami, 0, "Unable to set owner for group %s : %s",
3145 TargetGroupName, ldap_err2string(rc));
3151 if (AceSidCount == 0)
3153 com_err(whoami, 0, "Group %s: Administrator: %s, Type: %s - does not "
3154 "have a directory SID.", TargetGroupName, AceName, AceType);
3155 com_err(whoami, 0, " Non-admin security group template will be used.");
3159 sprintf(search_path, "%s,%s", security_template_ou, dn_path);
3160 sprintf(filter_exp, "(sAMAccountName=%s)", "UserTemplate.u");
3161 attr_array[0] = "objectSid";
3162 attr_array[1] = NULL;
3167 if ((rc = linklist_build(ldap_handle, search_path, filter_exp,
3168 attr_array, &group_base, &group_count,
3169 LDAP_SCOPE_SUBTREE) != 0))
3172 if ((rc != 0) || (group_count != 1))
3174 com_err(whoami, 0, "Unable to process user security template: %s",
3180 UserTemplateSidCount = group_base->length;
3181 memcpy(UserTemplateSid, group_base->value, UserTemplateSidCount);
3183 linklist_free(group_base);
3190 if (AceSidCount == 0)
3192 strcpy(GroupSecurityTemplate, HIDDEN_GROUP);
3193 sprintf(filter_exp, "(sAMAccountName=%s)", HIDDEN_GROUP);
3197 strcpy(GroupSecurityTemplate, HIDDEN_GROUP_WITH_ADMIN);
3198 sprintf(filter_exp, "(sAMAccountName=%s)", HIDDEN_GROUP_WITH_ADMIN);
3203 if (AceSidCount == 0)
3205 strcpy(GroupSecurityTemplate, NOT_HIDDEN_GROUP);
3206 sprintf(filter_exp, "(sAMAccountName=%s)", NOT_HIDDEN_GROUP);
3210 strcpy(GroupSecurityTemplate, NOT_HIDDEN_GROUP_WITH_ADMIN);
3211 sprintf(filter_exp, "(sAMAccountName=%s)",
3212 NOT_HIDDEN_GROUP_WITH_ADMIN);
3216 sprintf(search_path, "%s,%s", security_template_ou, dn_path);
3217 attr_array[0] = "sAMAccountName";
3218 attr_array[1] = NULL;
3222 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
3223 &group_base, &group_count,
3224 LDAP_SCOPE_SUBTREE) != 0))
3227 if (group_count != 1)
3229 linklist_free(group_base);
3230 com_err(whoami, 0, "Unable to process group security template: %s - "
3231 "security not set", GroupSecurityTemplate);
3235 strcpy(TemplateDn, group_base->dn);
3236 strcpy(TemplateSamName, group_base->value);
3237 linklist_free(group_base);
3241 sprintf(filter_exp, "(sAMAccountName=%s)", TemplateSamName);
3242 rc = ldap_search_ext_s(ldap_handle,
3254 if ((psMsg = ldap_first_entry(ldap_handle, psMsg)) == NULL)
3256 com_err(whoami, 0, "Unable to find group security template: %s - "
3257 "security not set", GroupSecurityTemplate);
3261 ppsValues = ldap_get_values_len(ldap_handle, psMsg, "ntSecurityDescriptor");
3263 if (ppsValues == NULL)
3265 com_err(whoami, 0, "Unable to find group security descriptor for group "
3266 "%s - security not set", GroupSecurityTemplate);
3270 if (AceSidCount != 0)
3272 for (nVal = 0; ppsValues[nVal] != NULL; nVal++)
3275 i < (int)(ppsValues[nVal]->bv_len - UserTemplateSidCount); i++)
3277 if (!memcmp(&ppsValues[nVal]->bv_val[i], UserTemplateSid,
3278 UserTemplateSidCount))
3280 memcpy(&ppsValues[nVal]->bv_val[i], AceSid, AceSidCount);
3288 ADD_ATTR("ntSecurityDescriptor", (char **)ppsValues,
3289 LDAP_MOD_REPLACE | LDAP_MOD_BVALUES);
3295 hide_address_lists_v[0] = "TRUE";
3296 address_book_v[0] = NULL;
3297 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
3299 ADD_ATTR("showInAddressBook", address_book_v, LDAP_MOD_REPLACE);
3301 hide_address_lists_v[0] = NULL;
3302 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
3309 rc = ldap_modify_s(ldap_handle, TargetDn, mods);
3311 for (i = 0; i < n; i++)
3314 ldap_value_free_len(ppsValues);
3315 ldap_msgfree(psMsg);
3317 if (rc != LDAP_SUCCESS)
3319 com_err(whoami, 0, "Unable to set security settings for group %s : %s",
3320 TargetGroupName, ldap_err2string(rc));
3322 if (AceSidCount != 0)
3325 "Trying to set security for group %s without admin.",
3328 if (rc = ProcessGroupSecurity(ldap_handle, dn_path, TargetGroupName,
3329 HiddenGroup, "", ""))
3331 com_err(whoami, 0, "Unable to set security for group %s.",
3342 int group_delete(LDAP *ldap_handle, char *dn_path, char *group_name,
3343 char *group_membership, char *MoiraId)
3345 LK_ENTRY *group_base;
3351 if (!check_string(group_name))
3354 "Unable to process invalid LDAP list name %s", group_name);
3355 return(AD_INVALID_NAME);
3358 memset(filter, '\0', sizeof(filter));
3361 sprintf(temp, "%s,%s", group_ou_root, dn_path);
3363 if (rc = ad_get_group(ldap_handle, temp, group_name,
3364 group_membership, MoiraId,
3365 "samAccountName", &group_base,
3366 &group_count, filter))
3369 if (group_count == 1)
3371 if ((rc = ldap_delete_s(ldap_handle, group_base->dn)) != LDAP_SUCCESS)
3373 linklist_free(group_base);
3374 com_err(whoami, 0, "Unable to delete list %s from directory : %s",
3375 group_name, ldap_err2string(rc));
3378 linklist_free(group_base);
3382 linklist_free(group_base);
3383 com_err(whoami, 0, "Unable to find list %s in directory.", group_name);
3384 return(AD_NO_GROUPS_FOUND);
3390 int BEREncodeSecurityBits(ULONG uBits, char *pBuffer)
3396 return(N_SD_BER_BYTES);
3399 int process_lists(int ac, char **av, void *ptr)
3404 char group_membership[2];
3410 memset(group_ou, '\0', sizeof(group_ou));
3411 memset(group_membership, '\0', sizeof(group_membership));
3412 get_group_membership(group_membership, group_ou, &security_flag, av);
3413 rc = populate_group((LDAP *)call_args[0], (char *)call_args[1],
3414 av[L_NAME], group_ou, group_membership,
3420 int member_list_build(int ac, char **av, void *ptr)
3428 strcpy(temp, av[ACE_NAME]);
3431 if (!check_string(temp))
3434 if (!strcmp(av[ACE_TYPE], "USER"))
3436 if (!((int)call_args[3] & MOIRA_USERS))
3439 else if (!strcmp(av[ACE_TYPE], "STRING"))
3443 if((s = strchr(temp, '@')) == (char *) NULL)
3445 strcat(temp, "@mit.edu");
3448 if(!strncasecmp(&temp[strlen(temp) - 6], ".LOCAL", 6))
3450 s = strrchr(temp, '.');
3452 strcat(s, ".mit.edu");
3456 if (!((int)call_args[3] & MOIRA_STRINGS))
3459 if (contact_create((LDAP *)call_args[0], call_args[1], temp, contact_ou))
3462 else if (!strcmp(av[ACE_TYPE], "LIST"))
3464 if (!((int)call_args[3] & MOIRA_LISTS))
3467 else if (!strcmp(av[ACE_TYPE], "KERBEROS"))
3469 if (!((int)call_args[3] & MOIRA_KERBEROS))
3472 if (contact_create((LDAP *)call_args[0], call_args[1], temp,
3477 else if (!strcmp(av[ACE_TYPE], "MACHINE"))
3479 if (!((int)call_args[3] & MOIRA_MACHINE))
3485 linklist = member_base;
3489 if (!strcasecmp(temp, linklist->member) &&
3490 !strcasecmp(av[ACE_TYPE], linklist->type))
3493 linklist = linklist->next;
3496 linklist = calloc(1, sizeof(LK_ENTRY));
3498 linklist->dn = NULL;
3499 linklist->list = calloc(1, strlen(call_args[2]) + 1);
3500 strcpy(linklist->list, call_args[2]);
3501 linklist->type = calloc(1, strlen(av[ACE_TYPE]) + 1);
3502 strcpy(linklist->type, av[ACE_TYPE]);
3503 linklist->member = calloc(1, strlen(temp) + 1);
3504 strcpy(linklist->member, temp);
3505 linklist->next = member_base;
3506 member_base = linklist;
3511 int member_remove(LDAP *ldap_handle, char *dn_path, char *group_name,
3512 char *group_ou, char *group_membership, char *user_name,
3513 char *UserOu, char *MoiraId)
3515 char distinguished_name[1024];
3519 char *attr_array[3];
3524 LK_ENTRY *group_base;
3528 if (!check_string(group_name))
3529 return(AD_INVALID_NAME);
3531 memset(filter, '\0', sizeof(filter));
3535 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
3536 group_membership, MoiraId,
3537 "samAccountName", &group_base,
3538 &group_count, filter))
3541 if (group_count != 1)
3543 com_err(whoami, 0, "Unable to find list %s in directory",
3545 linklist_free(group_base);
3551 strcpy(distinguished_name, group_base->dn);
3552 linklist_free(group_base);
3558 sprintf(temp, "CN=%s,%s,%s", user_name, UserOu, dn_path);
3562 if(!strcmp(UserOu, user_ou))
3563 sprintf(temp, "uid=%s,%s,%s", user_name, UserOu, dn_path);
3565 sprintf(temp, "CN=%s,%s,%s", user_name, UserOu, dn_path);
3568 modvalues[0] = temp;
3569 modvalues[1] = NULL;
3572 ADD_ATTR("member", modvalues, LDAP_MOD_DELETE);
3574 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
3576 for (i = 0; i < n; i++)
3579 if (rc == LDAP_UNWILLING_TO_PERFORM)
3582 if (rc != LDAP_SUCCESS)
3584 com_err(whoami, 0, "Unable to modify list %s members : %s",
3585 group_name, ldap_err2string(rc));
3589 if ((!strcmp(UserOu, contact_ou)) || (!strcmp(UserOu, kerberos_ou)))
3593 if(!strcmp(UserOu, contact_ou) &&
3594 ((s = strstr(user_name, "@mit.edu")) != (char *) NULL))
3596 memset(temp, '\0', sizeof(temp));
3597 strcpy(temp, user_name);
3598 s = strchr(temp, '@');
3601 sprintf(filter, "(&(objectClass=user)(mailNickName=%s))", temp);
3603 if ((rc = linklist_build(ldap_handle, dn_path, filter, NULL,
3604 &group_base, &group_count,
3605 LDAP_SCOPE_SUBTREE) != 0))
3611 linklist_free(group_base);
3616 sprintf(filter, "(distinguishedName=%s)", temp);
3617 attr_array[0] = "memberOf";
3618 attr_array[1] = NULL;
3620 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3621 &group_base, &group_count,
3622 LDAP_SCOPE_SUBTREE) != 0))
3628 com_err(whoami, 0, "Removing unreferenced object %s", temp);
3630 if ((rc = ldap_delete_s(ldap_handle, temp)) != 0)
3640 int member_add(LDAP *ldap_handle, char *dn_path, char *group_name,
3641 char *group_ou, char *group_membership, char *user_name,
3642 char *UserOu, char *MoiraId)
3644 char distinguished_name[1024];
3652 LK_ENTRY *group_base;
3655 if (!check_string(group_name))
3656 return(AD_INVALID_NAME);
3659 memset(filter, '\0', sizeof(filter));
3663 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
3664 group_membership, MoiraId,
3665 "samAccountName", &group_base,
3666 &group_count, filter))
3669 if (group_count != 1)
3671 linklist_free(group_base);
3674 com_err(whoami, 0, "Unable to find list %s %d in directory",
3675 group_name, group_count);
3676 return(AD_MULTIPLE_GROUPS_FOUND);
3679 strcpy(distinguished_name, group_base->dn);
3680 linklist_free(group_base);
3686 sprintf(temp, "CN=%s,%s,%s", user_name, UserOu, dn_path);
3690 if(!strcmp(UserOu, user_ou))
3691 sprintf(temp, "uid=%s,%s,%s", user_name, UserOu, dn_path);
3693 sprintf(temp, "cn=%s,%s,%s", user_name, UserOu, dn_path);
3696 modvalues[0] = temp;
3697 modvalues[1] = NULL;
3700 ADD_ATTR("member", modvalues, LDAP_MOD_ADD);
3702 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
3704 if (rc == LDAP_ALREADY_EXISTS || rc == LDAP_TYPE_OR_VALUE_EXISTS)
3707 if ((!strcmp(UserOu, contact_ou)) || (!strcmp(UserOu, kerberos_ou)))
3709 if (rc == LDAP_UNWILLING_TO_PERFORM)
3713 for (i = 0; i < n; i++)
3716 if (rc != LDAP_SUCCESS)
3718 com_err(whoami, 0, "Unable to add %s to list %s as a member : %s",
3719 user_name, group_name, ldap_err2string(rc));
3725 int contact_remove_email(LDAP *ld, char *bind_path,
3726 LK_ENTRY **linklist_base, int linklist_current)
3730 char *mail_v[] = {NULL, NULL};
3738 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
3739 ADD_ATTR("mailNickName", mail_v, LDAP_MOD_REPLACE);
3740 ADD_ATTR("proxyAddresses", mail_v, LDAP_MOD_REPLACE);
3741 ADD_ATTR("targetAddress", mail_v, LDAP_MOD_REPLACE);
3744 gPtr = (*linklist_base);
3747 rc = ldap_modify_s(ld, gPtr->dn, mods);
3749 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
3751 com_err(whoami, 0, "Unable to modify contact %s in directory : %s",
3752 gPtr->dn, ldap_err2string(rc));
3759 for (i = 0; i < n; i++)
3765 int contact_create(LDAP *ld, char *bind_path, char *user, char *group_ou)
3768 LK_ENTRY *group_base;
3771 char cn_user_name[256];
3772 char contact_name[256];
3773 char mail_nickname[256];
3774 char proxy_address_internal[256];
3775 char proxy_address_external[256];
3776 char target_address[256];
3777 char internal_contact_name[256];
3780 char principal[256];
3781 char mit_address_book[256];
3782 char default_address_book[256];
3783 char contact_address_book[256];
3785 char *email_v[] = {NULL, NULL};
3786 char *cn_v[] = {NULL, NULL};
3787 char *contact_v[] = {NULL, NULL};
3788 char *uid_v[] = {NULL, NULL};
3789 char *mail_nickname_v[] = {NULL, NULL};
3790 char *proxy_address_internal_v[] = {NULL, NULL};
3791 char *proxy_address_external_v[] = {NULL, NULL};
3792 char *target_address_v[] = {NULL, NULL};
3793 char *mit_address_book_v[] = {NULL, NULL};
3794 char *default_address_book_v[] = {NULL, NULL};
3795 char *contact_address_book_v[] = {NULL, NULL};
3796 char *hide_address_lists_v[] = {NULL, NULL};
3797 char *attr_array[3];
3798 char *objectClass_v[] = {"top", "person",
3799 "organizationalPerson",
3801 char *objectClass_ldap_v[] = {"top", "person", "microsoftComTop",
3802 "inetOrgPerson", "organizationalPerson",
3803 "contact", "mailRecipient", "eduPerson",
3805 char *name_v[] = {NULL, NULL};
3806 char *desc_v[] = {NULL, NULL};
3813 char *mail_routing_v[] = {NULL, NULL};
3814 char *principal_v[] = {NULL, NULL};
3816 if (!check_string(user))
3818 com_err(whoami, 0, "Unable to process invalid LDAP name %s", user);
3819 return(AD_INVALID_NAME);
3823 strcpy(contact_name, mail);
3824 strcpy(internal_contact_name, mail);
3826 if((s = strchr(internal_contact_name, '@')) != NULL) {
3830 sprintf(cn_user_name,"CN=%s,%s,%s", escape_string(contact_name), group_ou,
3833 sprintf(target_address, "SMTP:%s", contact_name);
3834 sprintf(proxy_address_external, "SMTP:%s", contact_name);
3835 sprintf(mail_nickname, "%s", internal_contact_name);
3837 cn_v[0] = cn_user_name;
3838 contact_v[0] = contact_name;
3841 desc_v[0] = "Auto account created by Moira";
3843 proxy_address_internal_v[0] = proxy_address_internal;
3844 proxy_address_external_v[0] = proxy_address_external;
3845 mail_nickname_v[0] = mail_nickname;
3846 target_address_v[0] = target_address;
3847 mit_address_book_v[0] = mit_address_book;
3848 default_address_book_v[0] = default_address_book;
3849 contact_address_book_v[0] = contact_address_book;
3850 strcpy(new_dn, cn_user_name);
3853 ADD_ATTR("cn", contact_v, LDAP_MOD_ADD);
3855 if(!ActiveDirectory)
3857 if(!strcmp(group_ou, contact_ou))
3858 sprintf(uid, "%s%s", contact_name, "_strings");
3860 if(!strcmp(group_ou, kerberos_ou))
3861 sprintf(uid, "%s%s", contact_name, "_kerberos");
3865 ADD_ATTR("sn", contact_v, LDAP_MOD_ADD);
3866 ADD_ATTR("uid", uid_v, LDAP_MOD_ADD);
3871 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
3875 ADD_ATTR("objectClass", objectClass_ldap_v, LDAP_MOD_ADD);
3878 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
3879 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
3880 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
3884 if (!strcmp(group_ou, contact_ou) && email_isvalid(mail))
3889 sprintf(filter, "(&(objectClass=user)(cn=%s))", mail);
3890 attr_array[0] = "cn";
3891 attr_array[1] = NULL;
3893 if ((rc = linklist_build(ld, bind_path, filter, attr_array,
3894 &group_base, &group_count,
3895 LDAP_SCOPE_SUBTREE)) != 0)
3897 com_err(whoami, 0, "Unable to process contact %s : %s",
3898 user, ldap_err2string(rc));
3904 com_err(whoami, 0, "Object already exists with name %s",
3909 linklist_free(group_base);
3913 sprintf(filter, "(&(objectClass=group)(cn=%s))", mail);
3914 attr_array[0] = "cn";
3915 attr_array[1] = NULL;
3917 if ((rc = linklist_build(ld, bind_path, filter, attr_array,
3918 &group_base, &group_count,
3919 LDAP_SCOPE_SUBTREE)) != 0)
3921 com_err(whoami, 0, "Unable to process contact %s : %s",
3922 user, ldap_err2string(rc));
3928 com_err(whoami, 0, "Object already exists with name %s",
3933 linklist_free(group_base);
3937 sprintf(filter, "(&(objectClass=user)(mail=%s))", mail);
3938 attr_array[0] = "cn";
3939 attr_array[1] = NULL;
3941 if ((rc = linklist_build(ld, bind_path, filter, attr_array,
3942 &group_base, &group_count,
3943 LDAP_SCOPE_SUBTREE)) != 0)
3945 com_err(whoami, 0, "Unable to process contact %s : %s",
3946 user, ldap_err2string(rc));
3952 com_err(whoami, 0, "Object already exists with name %s",
3957 linklist_free(group_base);
3961 sprintf(filter, "(&(objectClass=group)(mail=%s))", mail);
3962 attr_array[0] = "cn";
3963 attr_array[1] = NULL;
3965 if ((rc = linklist_build(ld, bind_path, filter, attr_array,
3966 &group_base, &group_count,
3967 LDAP_SCOPE_SUBTREE)) != 0)
3969 com_err(whoami, 0, "Unable to process contact %s : %s",
3970 user, ldap_err2string(rc));
3976 com_err(whoami, 0, "Object already exists with name %s",
3981 linklist_free(group_base);
3985 ADD_ATTR("mail", email_v, LDAP_MOD_ADD);
3986 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_ADD);
3987 ADD_ATTR("proxyAddresses", proxy_address_external_v, LDAP_MOD_ADD);
3988 ADD_ATTR("targetAddress", target_address_v, LDAP_MOD_ADD);
3990 hide_address_lists_v[0] = "TRUE";
3991 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
3996 if(!ActiveDirectory)
3998 if((c = strchr(mail, '@')) == NULL)
3999 sprintf(temp, "%s@mit.edu", mail);
4001 sprintf(temp, "%s", mail);
4003 mail_routing_v[0] = temp;
4005 principal_v[0] = principal;
4007 if(!strcmp(group_ou, contact_ou))
4009 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
4010 ADD_ATTR("eduPersonPrincipalName", mail_routing_v, LDAP_MOD_ADD);
4016 rc = ldap_add_ext_s(ld, new_dn, mods, NULL, NULL);
4018 for (i = 0; i < n; i++)
4023 if ((rc != LDAP_SUCCESS) && (rc == LDAP_ALREADY_EXISTS) &&
4024 !strcmp(group_ou, contact_ou) && email_isvalid(mail))
4028 ADD_ATTR("mail", email_v, LDAP_MOD_REPLACE);
4029 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
4030 ADD_ATTR("proxyAddresses", proxy_address_external_v,
4032 ADD_ATTR("targetAddress", target_address_v, LDAP_MOD_REPLACE);
4034 hide_address_lists_v[0] = "TRUE";
4035 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
4039 rc = ldap_modify_s(ld, new_dn, mods);
4043 com_err(whoami, 0, "Unable to update contact %s", mail);
4046 for (i = 0; i < n; i++)
4051 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
4053 com_err(whoami, 0, "Unable to create contact %s : %s",
4054 user, ldap_err2string(rc));
4061 int user_update(LDAP *ldap_handle, char *dn_path, char *user_name,
4062 char *Uid, char *MitId, char *MoiraId, int State,
4063 char *WinHomeDir, char *WinProfileDir, char *first,
4064 char *middle, char *last, char *shell, char *class)
4067 LK_ENTRY *group_base;
4069 char distinguished_name[512];
4070 char displayName[256];
4071 char *mitMoiraId_v[] = {NULL, NULL};
4072 char *mitMoiraClass_v[] = {NULL, NULL};
4073 char *mitMoiraStatus_v[] = {NULL, NULL};
4074 char *uid_v[] = {NULL, NULL};
4075 char *mitid_v[] = {NULL, NULL};
4076 char *homedir_v[] = {NULL, NULL};
4077 char *winProfile_v[] = {NULL, NULL};
4078 char *drives_v[] = {NULL, NULL};
4079 char *userAccountControl_v[] = {NULL, NULL};
4080 char *alt_recipient_v[] = {NULL, NULL};
4081 char *hide_address_lists_v[] = {NULL, NULL};
4082 char *mail_v[] = {NULL, NULL};
4083 char *gid_v[] = {NULL, NULL};
4084 char *loginshell_v[] = {NULL, NULL};
4085 char *principal_v[] = {NULL, NULL};
4086 char userAccountControlStr[80];
4091 u_int userAccountControl = UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD |
4092 UF_PASSWD_CANT_CHANGE;
4094 char *attr_array[3];
4097 char contact_mail[256];
4098 char filter_exp[1024];
4099 char search_path[512];
4100 char TemplateDn[512];
4101 char TemplateSamName[128];
4102 char alt_recipient[256];
4103 char principal[256];
4105 char acBERBuf[N_SD_BER_BYTES];
4106 LDAPControl sControl = {"1.2.840.113556.1.4.801",
4107 { N_SD_BER_BYTES, acBERBuf },
4109 LDAPControl *apsServerControls[] = {&sControl, NULL};
4111 LDAP_BERVAL **ppsValues;
4115 char *homeServerName;
4117 char search_string[256];
4119 char *mail_routing_v[] = {NULL, NULL};
4122 dwInfo = OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION |
4123 DACL_SECURITY_INFORMATION | SACL_SECURITY_INFORMATION;
4124 BEREncodeSecurityBits(dwInfo, acBERBuf);
4126 if (!check_string(user_name))
4128 com_err(whoami, 0, "Unable to process invalid LDAP user name %s",
4130 return(AD_INVALID_NAME);
4133 memset(contact_mail, '\0', sizeof(contact_mail));
4134 sprintf(contact_mail, "%s@mit.edu", user_name);
4135 memset(mail, '\0', sizeof(mail));
4136 sprintf(mail, "%s@%s", user_name, lowercase(ldap_domain));
4137 memset(alt_recipient, '\0', sizeof(alt_recipient));
4138 sprintf(alt_recipient, "cn=%s@mit.edu,%s,%s", user_name, contact_ou,
4140 sprintf(search_string, "@%s", uppercase(ldap_domain));
4144 if(contact_create(ldap_handle, dn_path, contact_mail, contact_ou))
4146 com_err(whoami, 0, "Unable to create user contact %s", contact_mail);
4153 memset(displayName, '\0', sizeof(displayName));
4155 if (strlen(MoiraId) != 0)
4159 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
4164 "(&(objectClass=mitPerson)(mitMoiraId=%s))", MoiraId);
4167 attr_array[0] = "cn";
4168 attr_array[1] = NULL;
4169 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4170 &group_base, &group_count,
4171 LDAP_SCOPE_SUBTREE)) != 0)
4173 com_err(whoami, 0, "Unable to process user %s : %s",
4174 user_name, ldap_err2string(rc));
4179 if (group_count != 1)
4181 linklist_free(group_base);
4184 sprintf(filter, "(sAMAccountName=%s)", user_name);
4185 attr_array[0] = "cn";
4186 attr_array[1] = NULL;
4187 sprintf(temp, "%s,%s", user_ou, dn_path);
4188 if ((rc = linklist_build(ldap_handle, temp, filter, attr_array,
4189 &group_base, &group_count,
4190 LDAP_SCOPE_SUBTREE)) != 0)
4192 com_err(whoami, 0, "Unable to process user %s : %s",
4193 user_name, ldap_err2string(rc));
4198 if (group_count != 1)
4200 com_err(whoami, 0, "Unable to find user %s in directory",
4202 linklist_free(group_base);
4203 return(AD_NO_USER_FOUND);
4206 strcpy(distinguished_name, group_base->dn);
4208 linklist_free(group_base);
4211 if(!ActiveDirectory)
4213 if (rc = moira_connect())
4215 critical_alert("Ldap incremental",
4216 "Error contacting Moira server : %s",
4221 argv[0] = user_name;
4223 if (!(rc = mr_query("get_pobox", 1, argv, save_query_info, save_argv)))
4226 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_REPLACE);
4228 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
4230 if (rc == LDAP_ALREADY_EXISTS || rc == LDAP_TYPE_OR_VALUE_EXISTS)
4235 "Unable to set the mailRoutingAddress for %s : %s",
4236 user_name, ldap_err2string(rc));
4238 p = strdup(save_argv[3]);
4240 if((c = strchr(p, ',')) != NULL)
4245 if ((c = strchr(q, '@')) == NULL)
4246 sprintf(temp, "%s@mit.edu", q);
4248 sprintf(temp, "%s", q);
4250 if(email_isvalid(temp) && State != US_DELETED)
4252 mail_routing_v[0] = temp;
4255 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
4257 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
4259 if (rc == LDAP_ALREADY_EXISTS ||
4260 rc == LDAP_TYPE_OR_VALUE_EXISTS)
4265 "Unable to set the mailRoutingAddress for %s : %s",
4266 user_name, ldap_err2string(rc));
4269 while((q = strtok(NULL, ",")) != NULL) {
4272 if((c = strchr(q, '@')) == NULL)
4273 sprintf(temp, "%s@mit.edu", q);
4275 sprintf(temp, "%s", q);
4277 if(email_isvalid(temp) && State != US_DELETED)
4279 mail_routing_v[0] = temp;
4282 ADD_ATTR("mailRoutingAddress", mail_routing_v,
4285 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
4287 if (rc == LDAP_ALREADY_EXISTS ||
4288 rc == LDAP_TYPE_OR_VALUE_EXISTS)
4293 "Unable to set the mailRoutingAddress for "
4295 user_name, ldap_err2string(rc));
4301 if((c = strchr(p, '@')) == NULL)
4302 sprintf(temp, "%s@mit.edu", p);
4304 sprintf(temp, "%s", p);
4306 if(email_isvalid(temp) && State != US_DELETED)
4308 mail_routing_v[0] = temp;
4311 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
4313 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
4315 if (rc == LDAP_ALREADY_EXISTS ||
4316 rc == LDAP_TYPE_OR_VALUE_EXISTS)
4321 "Unable to set the mailRoutingAddress for %s : %s",
4322 user_name, ldap_err2string(rc));
4329 if ((strlen(MitId) != 0) && (MitId[0] == '9'))
4330 rc = attribute_update(ldap_handle, distinguished_name, MitId,
4331 "employeeID", user_name);
4333 rc = attribute_update(ldap_handle, distinguished_name, "none",
4334 "employeeID", user_name);
4337 strcat(displayName, first);
4340 if(strlen(middle)) {
4342 strcat(displayName, " ");
4344 strcat(displayName, middle);
4348 if(strlen(middle) || strlen(first))
4349 strcat(displayName, " ");
4351 strcat(displayName, last);
4354 if(strlen(displayName))
4355 rc = attribute_update(ldap_handle, distinguished_name, displayName,
4356 "displayName", user_name);
4358 rc = attribute_update(ldap_handle, distinguished_name, user_name,
4359 "displayName", user_name);
4361 if(!ActiveDirectory)
4363 if(strlen(displayName))
4364 rc = attribute_update(ldap_handle, distinguished_name, displayName,
4367 rc = attribute_update(ldap_handle, distinguished_name, user_name,
4371 if(!ActiveDirectory)
4373 rc = attribute_update(ldap_handle, distinguished_name, displayName,
4374 "eduPersonNickname", user_name);
4378 rc = attribute_update(ldap_handle, distinguished_name, first,
4379 "givenName", user_name);
4381 rc = attribute_update(ldap_handle, distinguished_name, "",
4382 "givenName", user_name);
4384 if(strlen(middle) == 1)
4385 rc = attribute_update(ldap_handle, distinguished_name, middle,
4386 "initials", user_name);
4388 rc = attribute_update(ldap_handle, distinguished_name, "",
4389 "initials", user_name);
4392 rc = attribute_update(ldap_handle, distinguished_name, last,
4395 rc = attribute_update(ldap_handle, distinguished_name, "",
4400 rc = attribute_update(ldap_handle, distinguished_name, Uid, "uid",
4405 rc = attribute_update(ldap_handle, distinguished_name, user_name, "uid",
4409 rc = attribute_update(ldap_handle, distinguished_name, MoiraId,
4410 "mitMoiraId", user_name);
4419 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_REPLACE);
4423 ADD_ATTR("msSFU30UidNumber", uid_v, LDAP_MOD_REPLACE);
4428 sprintf(principal, "%s@%s", user_name, PRIMARY_REALM);
4429 sprintf(status, "%d", State);
4430 principal_v[0] = principal;
4431 loginshell_v[0] = shell;
4432 mitMoiraClass_v[0] = class;
4433 mitMoiraStatus_v[0] = status;
4435 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_REPLACE);
4436 ADD_ATTR("gidNumber", gid_v, LDAP_MOD_REPLACE);
4437 ADD_ATTR("loginShell", loginshell_v, LDAP_MOD_REPLACE);
4438 ADD_ATTR("eduPersonPrincipalName", mail_v, LDAP_MOD_REPLACE);
4439 ADD_ATTR("mitMoiraClass", mitMoiraClass_v, LDAP_MOD_REPLACE);
4440 ADD_ATTR("mitMoiraStatus", mitMoiraStatus_v, LDAP_MOD_REPLACE);
4443 if ((State != US_NO_PASSWD) && (State != US_REGISTERED))
4445 userAccountControl |= UF_ACCOUNTDISABLE;
4449 hide_address_lists_v[0] = "TRUE";
4450 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
4458 hide_address_lists_v[0] = NULL;
4459 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
4464 sprintf(userAccountControlStr, "%ld", userAccountControl);
4465 userAccountControl_v[0] = userAccountControlStr;
4466 ADD_ATTR("userAccountControl", userAccountControl_v, LDAP_MOD_REPLACE);
4470 if (rc = moira_connect())
4472 critical_alert("Ldap incremental",
4473 "Error contacting Moira server : %s",
4478 argv[0] = user_name;
4480 if (!(rc = mr_query("get_pobox", 1, argv, save_query_info, save_argv)))
4482 if(!strcmp(save_argv[1], "EXCHANGE") ||
4483 (strstr(save_argv[3], search_string) != NULL))
4485 alt_recipient_v[0] = NULL;
4486 ADD_ATTR("altRecipient", alt_recipient_v, LDAP_MOD_REPLACE);
4488 argv[0] = exchange_acl;
4490 argv[2] = user_name;
4492 rc = mr_query("add_member_to_list", 3, argv, NULL, NULL);
4494 if ((rc) && (rc != MR_EXISTS))
4496 com_err(whoami, 0, "Unable to add user %s to %s: %s",
4497 user_name, exchange_acl, error_message(rc));
4502 alt_recipient_v[0] = alt_recipient;
4503 ADD_ATTR("altRecipient", alt_recipient_v, LDAP_MOD_REPLACE);
4505 argv[0] = exchange_acl;
4507 argv[2] = user_name;
4509 rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL);
4511 if ((rc) && (rc != MR_NO_MATCH))
4514 "Unable to remove user %s from %s: %s, %d",
4515 user_name, exchange_acl, error_message(rc), rc);
4521 alt_recipient_v[0] = alt_recipient;
4522 ADD_ATTR("altRecipient", alt_recipient_v, LDAP_MOD_REPLACE);
4524 argv[0] = exchange_acl;
4526 argv[2] = user_name;
4528 rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL);
4530 if ((rc) && (rc != MR_NO_MATCH))
4533 "Unable to remove user %s from %s: %s, %d",
4534 user_name, exchange_acl, error_message(rc), rc);
4542 mail_v[0] = contact_mail;
4543 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
4546 n = SetHomeDirectory(ldap_handle, user_name, distinguished_name, WinHomeDir,
4547 WinProfileDir, homedir_v, winProfile_v,
4548 drives_v, mods, LDAP_MOD_REPLACE, n);
4552 sprintf(filter_exp, "(sAMAccountName=%s)", "UserTemplate.u");
4553 sprintf(search_path, "%s,%s", security_template_ou, dn_path);
4554 attr_array[0] = "sAMAccountName";
4555 attr_array[1] = NULL;
4559 if ((rc = linklist_build(ldap_handle, search_path, filter_exp,
4561 &group_base, &group_count,
4562 LDAP_SCOPE_SUBTREE) != 0))
4565 if (group_count != 1)
4567 com_err(whoami, 0, "Unable to process user security template: %s - "
4568 "security not set", "UserTemplate.u");
4572 strcpy(TemplateDn, group_base->dn);
4573 strcpy(TemplateSamName, group_base->value);
4574 linklist_free(group_base);
4578 rc = ldap_search_ext_s(ldap_handle, search_path, LDAP_SCOPE_SUBTREE,
4579 filter_exp, NULL, 0, apsServerControls, NULL,
4582 if ((psMsg = ldap_first_entry(ldap_handle, psMsg)) == NULL)
4584 com_err(whoami, 0, "Unable to find user security template: %s - "
4585 "security not set", "UserTemplate.u");
4589 ppsValues = ldap_get_values_len(ldap_handle, psMsg,
4590 "ntSecurityDescriptor");
4592 if (ppsValues == NULL)
4594 com_err(whoami, 0, "Unable to find user security template: %s - "
4595 "security not set", "UserTemplate.u");
4599 ADD_ATTR("ntSecurityDescriptor", (char **)ppsValues,
4600 LDAP_MOD_REPLACE | LDAP_MOD_BVALUES);
4605 if ((rc = ldap_modify_s(ldap_handle, distinguished_name,
4606 mods)) != LDAP_SUCCESS)
4608 OldUseSFU30 = UseSFU30;
4609 SwitchSFU(mods, &UseSFU30, n);
4610 if (OldUseSFU30 != UseSFU30)
4611 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
4614 com_err(whoami, 0, "Unable to modify user data for %s : %s",
4615 user_name, ldap_err2string(rc));
4619 for (i = 0; i < n; i++)
4625 int user_rename(LDAP *ldap_handle, char *dn_path, char *before_user_name,
4633 char contact_mail[256];
4634 char proxy_address[256];
4635 char query_base_dn[256];
4637 char *userPrincipalName_v[] = {NULL, NULL};
4638 char *altSecurityIdentities_v[] = {NULL, NULL};
4639 char *name_v[] = {NULL, NULL};
4640 char *samAccountName_v[] = {NULL, NULL};
4641 char *mail_v[] = {NULL, NULL};
4642 char *mail_nickname_v[] = {NULL, NULL};
4643 char *proxy_address_v[] = {NULL, NULL};
4644 char *query_base_dn_v[] = {NULL, NULL};
4645 char *principal_v[] = {NULL, NULL};
4646 char principal[256];
4651 if (!check_string(before_user_name))
4654 "Unable to process invalid LDAP user name %s", before_user_name);
4655 return(AD_INVALID_NAME);
4658 if (!check_string(user_name))
4661 "Unable to process invalid LDAP user name %s", user_name);
4662 return(AD_INVALID_NAME);
4665 strcpy(user_name, user_name);
4668 sprintf(old_dn, "cn=%s,%s,%s", before_user_name, user_ou, dn_path);
4670 sprintf(old_dn, "uid=%s,%s,%s", before_user_name, user_ou, dn_path);
4673 sprintf(new_dn, "cn=%s", user_name);
4675 sprintf(new_dn, "uid=%s", user_name);
4677 sprintf(mail, "%s@%s", user_name, lowercase(ldap_domain));
4678 sprintf(contact_mail, "%s@mit.edu", user_name);
4679 sprintf(proxy_address, "SMTP:%s@%s", user_name, lowercase(ldap_domain));
4680 sprintf(principal, "%s@%s", user_name, PRIMARY_REALM);
4682 if ((rc = ldap_rename_s(ldap_handle, old_dn, new_dn, NULL, TRUE,
4683 NULL, NULL)) != LDAP_SUCCESS)
4685 com_err(whoami, 0, "Unable to rename user from %s to %s : %s",
4686 before_user_name, user_name, ldap_err2string(rc));
4692 sprintf(temp, "cn=%s@mit.edu,%s,%s", before_user_name, contact_ou,
4695 if(rc = ldap_delete_s(ldap_handle, temp))
4697 com_err(whoami, 0, "Unable to delete user contact for %s",
4701 if(contact_create(ldap_handle, dn_path, contact_mail, contact_ou))
4703 com_err(whoami, 0, "Unable to create user contact %s", contact_mail);
4707 name_v[0] = user_name;
4708 sprintf(upn, "%s@%s", user_name, ldap_domain);
4709 userPrincipalName_v[0] = upn;
4710 principal_v[0] = principal;
4711 sprintf(temp, "Kerberos:%s@%s", user_name, PRIMARY_REALM);
4712 sprintf(query_base_dn, "%s%s", ADDRESS_LIST_PREFIX, dn_path);
4713 altSecurityIdentities_v[0] = temp;
4714 samAccountName_v[0] = user_name;
4716 mail_nickname_v[0] = user_name;
4717 proxy_address_v[0] = proxy_address;
4718 query_base_dn_v[0] = query_base_dn;
4721 ADD_ATTR("altSecurityIdentities", altSecurityIdentities_v, LDAP_MOD_REPLACE);
4722 ADD_ATTR("userPrincipalName", userPrincipalName_v, LDAP_MOD_REPLACE);
4723 ADD_ATTR("displayName", name_v, LDAP_MOD_REPLACE);
4724 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_REPLACE);
4726 if(!ActiveDirectory)
4728 ADD_ATTR("uid", samAccountName_v, LDAP_MOD_REPLACE);
4729 ADD_ATTR("eduPersonPrincipalName", mail_v, LDAP_MOD_REPLACE);
4730 ADD_ATTR("displayName", name_v, LDAP_MOD_REPLACE);
4731 ADD_ATTR("eduPersonNickname", name_v, LDAP_MOD_REPLACE);
4736 ADD_ATTR("msExchQueryBaseDN", query_base_dn_v, LDAP_MOD_REPLACE);
4737 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_REPLACE);
4738 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
4739 ADD_ATTR("proxyAddresses", proxy_address_v, LDAP_MOD_REPLACE);
4743 mail_v[0] = contact_mail;
4744 ADD_ATTR("mail", mail_v, LDAP_MOD_REPLACE);
4750 sprintf(new_dn, "cn=%s,%s,%s", user_name, user_ou, dn_path);
4752 sprintf(new_dn, "uid=%s,%s,%s", user_name, user_ou, dn_path);
4754 if ((rc = ldap_modify_s(ldap_handle, new_dn, mods)) != LDAP_SUCCESS)
4757 "Unable to modify user data for %s after renaming : %s",
4758 user_name, ldap_err2string(rc));
4761 for (i = 0; i < n; i++)
4767 int user_create(int ac, char **av, void *ptr)
4771 char user_name[256];
4775 char contact_mail[256];
4776 char proxy_address[256];
4777 char mail_nickname[256];
4778 char query_base_dn[256];
4779 char displayName[256];
4780 char address_book[256];
4781 char alt_recipient[256];
4782 char *cn_v[] = {NULL, NULL};
4783 char *objectClass_v[] = {"top", "person", "organizationalPerson",
4785 char *objectClass_ldap_v[] = {"top",
4786 "eduPerson", "posixAccount",
4787 "apple-user", "shadowAccount",
4788 "microsoftComTop", "securityPrincipal",
4789 "inetOrgPerson", "user",
4790 "organizationalPerson", "person",
4791 "mailRecipient", NULL};
4793 char *samAccountName_v[] = {NULL, NULL};
4794 char *altSecurityIdentities_v[] = {NULL, NULL};
4795 char *mitMoiraId_v[] = {NULL, NULL};
4796 char *mitMoiraClass_v[] = {NULL, NULL};
4797 char *mitMoiraStatus_v[] = {NULL, NULL};
4798 char *name_v[] = {NULL, NULL};
4799 char *desc_v[] = {NULL, NULL};
4800 char *userPrincipalName_v[] = {NULL, NULL};
4801 char *userAccountControl_v[] = {NULL, NULL};
4802 char *uid_v[] = {NULL, NULL};
4803 char *gid_v[] = {NULL, NULL};
4804 char *mitid_v[] = {NULL, NULL};
4805 char *homedir_v[] = {NULL, NULL};
4806 char *winProfile_v[] = {NULL, NULL};
4807 char *drives_v[] = {NULL, NULL};
4808 char *mail_v[] = {NULL, NULL};
4809 char *givenName_v[] = {NULL, NULL};
4810 char *sn_v[] = {NULL, NULL};
4811 char *initials_v[] = {NULL, NULL};
4812 char *displayName_v[] = {NULL, NULL};
4813 char *proxy_address_v[] = {NULL, NULL};
4814 char *mail_nickname_v[] = {NULL, NULL};
4815 char *query_base_dn_v[] = {NULL, NULL};
4816 char *address_book_v[] = {NULL, NULL};
4817 char *homeMDB_v[] = {NULL, NULL};
4818 char *homeServerName_v[] = {NULL, NULL};
4819 char *mdbUseDefaults_v[] = {NULL, NULL};
4820 char *mailbox_guid_v[] = {NULL, NULL};
4821 char *user_culture_v[] = {NULL, NULL};
4822 char *user_account_control_v[] = {NULL, NULL};
4823 char *msexch_version_v[] = {NULL, NULL};
4824 char *alt_recipient_v[] = {NULL, NULL};
4825 char *hide_address_lists_v[] = {NULL, NULL};
4826 char *principal_v[] = {NULL, NULL};
4827 char *loginshell_v[] = {NULL, NULL};
4828 char userAccountControlStr[80];
4830 char principal[256];
4831 char filter_exp[1024];
4832 char search_path[512];
4833 char *attr_array[3];
4834 u_int userAccountControl = UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD |
4835 UF_PASSWD_CANT_CHANGE;
4841 char WinHomeDir[1024];
4842 char WinProfileDir[1024];
4844 char *homeServerName;
4846 char acBERBuf[N_SD_BER_BYTES];
4847 LK_ENTRY *group_base;
4849 char TemplateDn[512];
4850 char TemplateSamName[128];
4851 LDAP_BERVAL **ppsValues;
4852 LDAPControl sControl = {"1.2.840.113556.1.4.801",
4853 { N_SD_BER_BYTES, acBERBuf },
4855 LDAPControl *apsServerControls[] = {&sControl, NULL};
4859 char search_string[256];
4860 char *o_v[] = {NULL, NULL};
4862 char *mail_routing_v[] = {NULL, NULL};
4867 dwInfo = OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION |
4868 DACL_SECURITY_INFORMATION | SACL_SECURITY_INFORMATION;
4869 BEREncodeSecurityBits(dwInfo, acBERBuf);
4871 if (!check_string(av[U_NAME]))
4873 callback_rc = AD_INVALID_NAME;
4874 com_err(whoami, 0, "Unable to process invalid LDAP user name %s",
4876 return(AD_INVALID_NAME);
4879 memset(WinHomeDir, '\0', sizeof(WinHomeDir));
4880 memset(WinProfileDir, '\0', sizeof(WinProfileDir));
4881 memset(displayName, '\0', sizeof(displayName));
4882 memset(query_base_dn, '\0', sizeof(query_base_dn));
4883 strcpy(WinHomeDir, av[U_WINHOMEDIR]);
4884 strcpy(WinProfileDir, av[U_WINPROFILEDIR]);
4885 strcpy(user_name, av[U_NAME]);
4886 sprintf(upn, "%s@%s", user_name, ldap_domain);
4887 sprintf(sam_name, "%s", av[U_NAME]);
4889 if(strlen(av[U_FIRST])) {
4890 strcat(displayName, av[U_FIRST]);
4893 if(strlen(av[U_MIDDLE])) {
4894 if(strlen(av[U_FIRST]))
4895 strcat(displayName, " ");
4897 strcat(displayName, av[U_MIDDLE]);
4900 if(strlen(av[U_LAST])) {
4901 if(strlen(av[U_FIRST]) || strlen(av[U_MIDDLE]))
4902 strcat(displayName, " ");
4904 strcat(displayName, av[U_LAST]);
4907 samAccountName_v[0] = sam_name;
4908 if ((atoi(av[U_STATE]) != US_NO_PASSWD) &&
4909 (atoi(av[U_STATE]) != US_REGISTERED))
4911 userAccountControl |= UF_ACCOUNTDISABLE;
4915 hide_address_lists_v[0] = "TRUE";
4916 ADD_ATTR("msExchHideFromAddressLists", hide_address_lists_v,
4921 sprintf(userAccountControlStr, "%ld", userAccountControl);
4922 userAccountControl_v[0] = userAccountControlStr;
4923 userPrincipalName_v[0] = upn;
4926 cn_v[0] = user_name;
4928 cn_v[0] = displayName;
4930 name_v[0] = user_name;
4931 desc_v[0] = "Auto account created by Moira";
4933 givenName_v[0] = av[U_FIRST];
4936 sn_v[0] = av[U_LAST];
4938 if(strlen(av[U_LAST]))
4939 sn_v[0] = av[U_LAST];
4941 sn_v[0] = av[U_NAME];
4943 displayName_v[0] = displayName;
4944 mail_nickname_v[0] = user_name;
4945 o_v[0] = "Massachusetts Institute of Technology";
4947 sprintf(temp, "Kerberos:%s@%s", user_name, PRIMARY_REALM);
4948 sprintf(principal, "%s@%s", user_name, PRIMARY_REALM);
4949 altSecurityIdentities_v[0] = temp;
4950 principal_v[0] = principal;
4953 sprintf(new_dn, "cn=%s,%s,%s", user_name, user_ou, call_args[1]);
4955 sprintf(new_dn, "uid=%s,%s,%s", user_name, user_ou, call_args[1]);
4957 sprintf(mail,"%s@%s", user_name, lowercase(ldap_domain));
4958 sprintf(contact_mail, "%s@mit.edu", user_name);
4959 sprintf(query_base_dn, "%s%s", ADDRESS_LIST_PREFIX, call_args[1]);
4960 query_base_dn_v[0] = query_base_dn;
4961 sprintf(alt_recipient, "cn=%s@mit.edu,%s,%s", user_name, contact_ou,
4963 sprintf(search_string, "@%s", uppercase(ldap_domain));
4967 if(contact_create((LDAP *)call_args[0], call_args[1], contact_mail,
4970 com_err(whoami, 0, "Unable to create user contact %s",
4974 if(find_homeMDB((LDAP *)call_args[0], call_args[1], &homeMDB,
4977 com_err(whoami, 0, "Unable to locate homeMB and homeServerName");
4981 com_err(whoami, 0, "homeMDB:%s", homeMDB);
4982 com_err(whoami, 0, "homeServerName:%s", homeServerName);
4984 homeMDB_v[0] = homeMDB;
4985 homeServerName_v[0] = homeServerName;
4990 ADD_ATTR("cn", cn_v, LDAP_MOD_ADD);
4994 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
4998 ADD_ATTR("objectClass", objectClass_ldap_v, LDAP_MOD_ADD);
5001 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_ADD);
5002 ADD_ATTR("userPrincipalName", userPrincipalName_v, LDAP_MOD_ADD);
5003 ADD_ATTR("userAccountControl", userAccountControl_v, LDAP_MOD_ADD);
5004 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
5005 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
5009 ADD_ATTR("msExchQueryBaseDN", query_base_dn_v, LDAP_MOD_ADD);
5010 ADD_ATTR("mailNickName", mail_nickname_v, LDAP_MOD_ADD);
5011 ADD_ATTR("homeMDB", homeMDB_v, LDAP_MOD_ADD);
5012 mdbUseDefaults_v[0] = "TRUE";
5013 ADD_ATTR("mdbUseDefaults", mdbUseDefaults_v, LDAP_MOD_ADD);
5014 ADD_ATTR("msExchHomeServerName", homeServerName_v, LDAP_MOD_ADD);
5016 argv[0] = user_name;
5018 if (!(rc = mr_query("get_pobox", 1, argv, save_query_info, save_argv)))
5020 if(!strcmp(save_argv[1], "EXCHANGE") ||
5021 (strstr(save_argv[3], search_string) != NULL))
5023 argv[0] = exchange_acl;
5025 argv[2] = user_name;
5027 rc = mr_query("add_member_to_list", 3, argv, NULL, NULL);
5029 if ((rc) && (rc != MR_EXISTS))
5031 com_err(whoami, 0, "Unable to add user %s to %s: %s",
5032 user_name, exchange_acl, error_message(rc));
5037 alt_recipient_v[0] = alt_recipient;
5038 ADD_ATTR("altRecipient", alt_recipient_v, LDAP_MOD_ADD);
5043 alt_recipient_v[0] = alt_recipient;
5044 ADD_ATTR("altRecipient", alt_recipient_v, LDAP_MOD_ADD);
5046 com_err(whoami, 0, "Unable to fetch pobox for %s", user_name);
5051 mail_v[0] = contact_mail;
5052 ADD_ATTR("mail", mail_v, LDAP_MOD_ADD);
5055 if(strlen(av[U_FIRST])) {
5056 ADD_ATTR("givenName", givenName_v, LDAP_MOD_ADD);
5059 if(strlen(av[U_LAST]) || strlen(av[U_NAME])) {
5060 ADD_ATTR("sn", sn_v, LDAP_MOD_ADD);
5063 if(strlen(av[U_FIRST]) || strlen(av[U_MIDDLE]) || strlen(av[U_LAST])) {
5064 ADD_ATTR("displayName", displayName_v, LDAP_MOD_ADD);
5066 if(!ActiveDirectory)
5068 ADD_ATTR("eduPersonNickname", displayName_v, LDAP_MOD_ADD);
5071 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
5073 if(!ActiveDirectory)
5075 ADD_ATTR("eduPersonNickname", name_v, LDAP_MOD_ADD);
5079 if (strlen(av[U_MIDDLE]) == 1) {
5080 initials_v[0] = av[U_MIDDLE];
5081 ADD_ATTR("initials", initials_v, LDAP_MOD_ADD);
5084 if (strlen(call_args[2]) != 0)
5086 mitMoiraId_v[0] = call_args[2];
5087 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_ADD);
5090 ADD_ATTR("altSecurityIdentities", altSecurityIdentities_v, LDAP_MOD_ADD);
5092 if(!ActiveDirectory)
5094 loginshell_v[0] = av[U_SHELL];
5095 mitMoiraClass_v[0] = av[U_CLASS];
5096 mitMoiraStatus_v[0] = av[U_STATE];
5097 ADD_ATTR("loginShell", loginshell_v, LDAP_MOD_ADD);
5098 ADD_ATTR("uid", samAccountName_v, LDAP_MOD_ADD);
5099 ADD_ATTR("eduPersonPrincipalName", mail_v, LDAP_MOD_ADD);
5100 ADD_ATTR("o", o_v, LDAP_MOD_ADD);
5101 ADD_ATTR("mitMoiraClass", mitMoiraClass_v, LDAP_MOD_ADD);
5102 ADD_ATTR("mitMoiraStatus", mitMoiraStatus_v, LDAP_MOD_ADD);
5105 if (strlen(av[U_UID]) != 0)
5107 uid_v[0] = av[U_UID];
5111 ADD_ATTR("uid", uid_v, LDAP_MOD_ADD);
5116 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_ADD);
5117 ADD_ATTR("gidNumber", gid_v, LDAP_MOD_ADD);
5124 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_ADD);
5128 ADD_ATTR("msSFU30UidNumber", uid_v, LDAP_MOD_ADD);
5133 if ((strlen(av[U_MITID]) != 0) && (av[U_MITID][0] == '9'))
5134 mitid_v[0] = av[U_MITID];
5136 mitid_v[0] = "none";
5138 ADD_ATTR("employeeID", mitid_v, LDAP_MOD_ADD);
5140 n = SetHomeDirectory((LDAP *)call_args[0], user_name, new_dn,
5141 WinHomeDir, WinProfileDir, homedir_v, winProfile_v,
5142 drives_v, mods, LDAP_MOD_ADD, n);
5146 sprintf(filter_exp, "(sAMAccountName=%s)", "UserTemplate.u");
5147 sprintf(search_path, "%s,%s", security_template_ou, call_args[1]);
5148 attr_array[0] = "sAMAccountName";
5149 attr_array[1] = NULL;
5153 if ((rc = linklist_build((LDAP *)call_args[0], search_path, filter_exp,
5154 attr_array, &group_base, &group_count,
5155 LDAP_SCOPE_SUBTREE) != 0))
5158 if (group_count != 1)
5160 com_err(whoami, 0, "Unable to process user security template: %s - "
5161 "security not set", "UserTemplate.u");
5165 strcpy(TemplateDn, group_base->dn);
5166 strcpy(TemplateSamName, group_base->value);
5167 linklist_free(group_base);
5171 rc = ldap_search_ext_s((LDAP *)call_args[0], search_path,
5172 LDAP_SCOPE_SUBTREE, filter_exp, NULL, 0,
5173 apsServerControls, NULL,
5176 if ((psMsg = ldap_first_entry((LDAP *)call_args[0], psMsg)) == NULL)
5178 com_err(whoami, 0, "Unable to find user security template: %s - "
5179 "security not set", "UserTemplate.u");
5183 ppsValues = ldap_get_values_len((LDAP *)call_args[0], psMsg,
5184 "ntSecurityDescriptor");
5185 if (ppsValues == NULL)
5187 com_err(whoami, 0, "Unable to find user security template: %s - "
5188 "security not set", "UserTemplate.u");
5192 ADD_ATTR("ntSecurityDescriptor", (char **)ppsValues,
5193 LDAP_MOD_REPLACE | LDAP_MOD_BVALUES);
5198 rc = ldap_add_ext_s((LDAP *)call_args[0], new_dn, mods, NULL, NULL);
5200 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
5202 OldUseSFU30 = UseSFU30;
5203 SwitchSFU(mods, &UseSFU30, n);
5204 if (OldUseSFU30 != UseSFU30)
5205 rc = ldap_add_ext_s((LDAP *)call_args[0], new_dn, mods, NULL, NULL);
5208 for (i = 0; i < n; i++)
5211 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
5213 com_err(whoami, 0, "Unable to create user %s : %s",
5214 user_name, ldap_err2string(rc));
5219 if ((rc == LDAP_SUCCESS) && (SetPassword))
5221 if ((rc = set_password(sam_name, "", ldap_domain)) != 0)
5223 ad_kdc_disconnect();
5224 if (!ad_server_connect(default_server, ldap_domain))
5226 com_err(whoami, 0, "Unable to set password for user %s : %s",
5228 "cannot get changepw ticket from windows domain");
5232 if ((rc = set_password(sam_name, "", ldap_domain)) != 0)
5234 com_err(whoami, 0, "Unable to set password for user %s "
5235 ": %ld", user_name, rc);
5241 if(!ActiveDirectory)
5243 if (rc = moira_connect())
5245 critical_alert("Ldap incremental",
5246 "Error contacting Moira server : %s",
5251 argv[0] = user_name;
5253 if (!(rc = mr_query("get_pobox", 1, argv, save_query_info, save_argv)))
5256 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_REPLACE);
5258 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
5260 if (rc == LDAP_ALREADY_EXISTS || rc == LDAP_TYPE_OR_VALUE_EXISTS)
5265 "Unable to set the mailRoutingAddress for %s : %s",
5266 user_name, ldap_err2string(rc));
5268 p = strdup(save_argv[3]);
5270 if((c = strchr(p, ',')) != NULL) {
5274 if ((c = strchr(q, '@')) == NULL)
5275 sprintf(temp, "%s@mit.edu", q);
5277 sprintf(temp, "%s", q);
5279 if(email_isvalid(temp) && atoi(av[U_STATE]) != US_DELETED)
5281 mail_routing_v[0] = temp;
5284 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
5286 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
5288 if (rc == LDAP_ALREADY_EXISTS ||
5289 rc == LDAP_TYPE_OR_VALUE_EXISTS)
5294 "Unable to set the mailRoutingAddress for %s : %s",
5295 user_name, ldap_err2string(rc));
5298 while((q = strtok(NULL, ",")) != NULL) {
5301 if((c = strchr(q, '@')) == NULL)
5302 sprintf(temp, "%s@mit.edu", q);
5304 sprintf(temp, "%s", q);
5306 if(email_isvalid(temp) && atoi(av[U_STATE]) != US_DELETED)
5308 mail_routing_v[0] = temp;
5311 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
5313 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
5315 if (rc == LDAP_ALREADY_EXISTS ||
5316 rc == LDAP_TYPE_OR_VALUE_EXISTS)
5321 "Unable to set the mailRoutingAddress for %s : %s",
5322 user_name, ldap_err2string(rc));
5328 if((c = strchr(p, '@')) == NULL)
5329 sprintf(temp, "%s@mit.edu", p);
5331 sprintf(temp, "%s", p);
5333 if(email_isvalid(temp) && atoi(av[U_STATE]) != US_DELETED)
5335 mail_routing_v[0] = temp;
5338 ADD_ATTR("mailRoutingAddress", mail_routing_v, LDAP_MOD_ADD);
5340 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
5342 if (rc == LDAP_ALREADY_EXISTS ||
5343 rc == LDAP_TYPE_OR_VALUE_EXISTS)
5348 "Unable to set the mailRoutingAddress for %s : %s",
5349 user_name, ldap_err2string(rc));
5359 int user_change_status(LDAP *ldap_handle, char *dn_path,
5360 char *user_name, char *MoiraId,
5364 char *attr_array[3];
5366 char distinguished_name[1024];
5368 char *mitMoiraId_v[] = {NULL, NULL};
5370 LK_ENTRY *group_base;
5377 if (!check_string(user_name))
5379 com_err(whoami, 0, "Unable to process invalid LDAP user name %s",
5381 return(AD_INVALID_NAME);
5387 if (strlen(MoiraId) != 0)
5389 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
5390 attr_array[0] = "UserAccountControl";
5391 attr_array[1] = NULL;
5392 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
5393 &group_base, &group_count,
5394 LDAP_SCOPE_SUBTREE)) != 0)
5396 com_err(whoami, 0, "Unable to process user %s : %s",
5397 user_name, ldap_err2string(rc));
5402 if (group_count != 1)
5404 linklist_free(group_base);
5407 sprintf(filter, "(sAMAccountName=%s)", user_name);
5408 attr_array[0] = "UserAccountControl";
5409 attr_array[1] = NULL;
5410 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
5411 &group_base, &group_count,
5412 LDAP_SCOPE_SUBTREE)) != 0)
5414 com_err(whoami, 0, "Unable to process user %s : %s",
5415 user_name, ldap_err2string(rc));
5420 if (group_count != 1)
5422 linklist_free(group_base);
5423 com_err(whoami, 0, "Unable to find user %s in directory",
5425 return(LDAP_NO_SUCH_OBJECT);
5428 strcpy(distinguished_name, group_base->dn);
5429 ulongValue = atoi((*group_base).value);
5431 if (operation == MEMBER_DEACTIVATE)
5432 ulongValue |= UF_ACCOUNTDISABLE;
5434 ulongValue &= ~UF_ACCOUNTDISABLE;
5436 sprintf(temp, "%ld", ulongValue);
5438 if ((rc = construct_newvalues(group_base, group_count, (*group_base).value,
5439 temp, &modvalues, REPLACE)) == 1)
5442 linklist_free(group_base);
5446 ADD_ATTR("UserAccountControl", modvalues, LDAP_MOD_REPLACE);
5448 if (strlen(MoiraId) != 0)
5450 mitMoiraId_v[0] = MoiraId;
5451 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
5455 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
5457 for (i = 0; i < n; i++)
5460 free_values(modvalues);
5462 if (rc != LDAP_SUCCESS)
5464 com_err(whoami, 0, "Unable to change status of user %s : %s",
5465 user_name, ldap_err2string(rc));
5472 int user_delete(LDAP *ldap_handle, char *dn_path,
5473 char *u_name, char *MoiraId)
5476 char *attr_array[3];
5477 char distinguished_name[1024];
5478 char user_name[512];
5479 LK_ENTRY *group_base;
5484 if (!check_string(u_name))
5485 return(AD_INVALID_NAME);
5487 strcpy(user_name, u_name);
5491 if (strlen(MoiraId) != 0)
5493 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
5494 attr_array[0] = "name";
5495 attr_array[1] = NULL;
5496 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
5497 &group_base, &group_count,
5498 LDAP_SCOPE_SUBTREE)) != 0)
5500 com_err(whoami, 0, "Unable to process user %s : %s",
5501 user_name, ldap_err2string(rc));
5506 if (group_count != 1)
5508 linklist_free(group_base);
5511 sprintf(filter, "(sAMAccountName=%s)", user_name);
5512 attr_array[0] = "name";
5513 attr_array[1] = NULL;
5514 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
5515 &group_base, &group_count,
5516 LDAP_SCOPE_SUBTREE)) != 0)
5518 com_err(whoami, 0, "Unable to process user %s : %s",
5519 user_name, ldap_err2string(rc));
5524 if (group_count != 1)
5526 com_err(whoami, 0, "Unable to find user %s in directory",
5531 strcpy(distinguished_name, group_base->dn);
5533 if (rc = ldap_delete_s(ldap_handle, distinguished_name))
5535 com_err(whoami, 0, "Unable to process user %s : %s",
5536 user_name, ldap_err2string(rc));
5539 /* Need to add code to delete mit.edu contact */
5543 sprintf(temp, "cn=%s@mit.edu,%s,%s", user_name, contact_ou, dn_path);
5545 if(rc = ldap_delete_s(ldap_handle, temp))
5547 com_err(whoami, 0, "Unable to delete user contact for %s",
5553 linklist_free(group_base);
5558 void linklist_free(LK_ENTRY *linklist_base)
5560 LK_ENTRY *linklist_previous;
5562 while (linklist_base != NULL)
5564 if (linklist_base->dn != NULL)
5565 free(linklist_base->dn);
5567 if (linklist_base->attribute != NULL)
5568 free(linklist_base->attribute);
5570 if (linklist_base->value != NULL)
5571 free(linklist_base->value);
5573 if (linklist_base->member != NULL)
5574 free(linklist_base->member);
5576 if (linklist_base->type != NULL)
5577 free(linklist_base->type);
5579 if (linklist_base->list != NULL)
5580 free(linklist_base->list);
5582 linklist_previous = linklist_base;
5583 linklist_base = linklist_previous->next;
5584 free(linklist_previous);
5588 void free_values(char **modvalues)
5594 if (modvalues != NULL)
5596 while (modvalues[i] != NULL)
5599 modvalues[i] = NULL;
5606 static int illegalchars[] = {
5607 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^@ - ^O */
5608 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^P - ^_ */
5609 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, /* SPACE - / */
5610 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, /* 0 - ? */
5611 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* @ - O */
5612 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, /* P - _ */
5613 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* ` - o */
5614 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, /* p - ^? */
5615 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5616 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5617 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5618 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5619 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5620 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5621 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5622 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5625 static int illegalchars_ldap[] = {
5626 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^@ - ^O */
5627 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^P - ^_ */
5628 0, 1, 0, 0, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, /* SPACE - / */
5629 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 0, 0, 0, 0, 1, /* 0 - ? */
5630 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* @ - O */
5631 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, 1, 1, 0, /* P - _ */
5632 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* ` - o */
5633 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, /* p - ^? */
5634 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5635 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5636 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5637 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5638 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5639 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5640 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5641 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
5644 int check_string(char *s)
5652 if (isupper(character))
5653 character = tolower(character);
5657 if (illegalchars[(unsigned) character])
5662 if (illegalchars_ldap[(unsigned) character])
5670 int check_container_name(char *s)
5678 if (isupper(character))
5679 character = tolower(character);
5681 if (character == ' ')
5684 if (illegalchars[(unsigned) character])
5691 int mr_connect_cl(char *server, char *client, int version, int auth)
5697 status = mr_connect(server);
5701 com_err(whoami, status, "while connecting to Moira");
5705 status = mr_motd(&motd);
5710 com_err(whoami, status, "while checking server status");
5716 sprintf(temp, "The Moira server is currently unavailable: %s", motd);
5717 com_err(whoami, status, temp);
5722 status = mr_version(version);
5726 if (status == MR_UNKNOWN_PROC)
5729 status = MR_VERSION_HIGH;
5731 status = MR_SUCCESS;
5734 if (status == MR_VERSION_HIGH)
5736 com_err(whoami, 0, "Warning: This client is running newer code "
5737 "than the server.");
5738 com_err(whoami, 0, "Some operations may not work.");
5740 else if (status && status != MR_VERSION_LOW)
5742 com_err(whoami, status, "while setting query version number.");
5750 status = mr_krb5_auth(client);
5753 com_err(whoami, status, "while authenticating to Moira.");
5762 void AfsToWinAfs(char* path, char* winPath)
5766 strcpy(winPath, WINAFS);
5767 pathPtr = path + strlen(AFS);
5768 winPathPtr = winPath + strlen(WINAFS);
5772 if (*pathPtr == '/')
5775 *winPathPtr = *pathPtr;
5782 int GetAceInfo(int ac, char **av, void *ptr)
5789 strcpy(call_args[0], av[L_ACE_TYPE]);
5790 strcpy(call_args[1], av[L_ACE_NAME]);
5792 get_group_membership(call_args[2], call_args[3], &security_flag, av);
5793 return(LDAP_SUCCESS);
5796 int checkADname(LDAP *ldap_handle, char *dn_path, char *Name)
5799 char *attr_array[3];
5802 LK_ENTRY *group_base;
5807 sprintf(filter, "(sAMAccountName=%s)", Name);
5808 attr_array[0] = "sAMAccountName";
5809 attr_array[1] = NULL;
5811 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
5812 &group_base, &group_count,
5813 LDAP_SCOPE_SUBTREE)) != 0)
5815 com_err(whoami, 0, "Unable to process ACE name %s : %s",
5816 Name, ldap_err2string(rc));
5820 linklist_free(group_base);
5823 if (group_count == 0)
5831 int ProcessAce(LDAP *ldap_handle, char *dn_path, char *Name, char *Type,
5832 int UpdateGroup, int *ProcessGroup, char *maillist)
5835 char GroupName[256];
5841 char AceMembership[2];
5844 char *save_argv[U_END];
5848 com_err(whoami, 0, "ProcessAce disabled, skipping");
5852 strcpy(GroupName, Name);
5854 if (strcasecmp(Type, "LIST"))
5860 AceInfo[0] = AceType;
5861 AceInfo[1] = AceName;
5862 AceInfo[2] = AceMembership;
5864 memset(AceType, '\0', sizeof(AceType));
5865 memset(AceName, '\0', sizeof(AceName));
5866 memset(AceMembership, '\0', sizeof(AceMembership));
5867 memset(AceOu, '\0', sizeof(AceOu));
5870 if (rc = mr_query("get_list_info", 1, av, GetAceInfo, AceInfo))
5872 com_err(whoami, 0, "Unable to get ACE info for list %s : %s",
5873 GroupName, error_message(rc));
5879 com_err(whoami, 0, "Unable to get ACE info for list %s", GroupName);
5883 if ((strcasecmp(AceType, "USER")) && (strcasecmp(AceType, "LIST")))
5886 strcpy(temp, AceName);
5888 if (!strcasecmp(AceType, "LIST"))
5889 sprintf(temp, "%s%s", AceName, group_suffix);
5893 if (checkADname(ldap_handle, dn_path, temp))
5896 (*ProcessGroup) = 1;
5899 if (!strcasecmp(AceInfo[0], "LIST"))
5901 if (make_new_group(ldap_handle, dn_path, "", AceName, AceOu,
5902 AceMembership, 0, UpdateGroup, maillist))
5905 populate_group(ldap_handle, dn_path, AceName, AceOu, AceMembership,
5908 else if (!strcasecmp(AceInfo[0], "USER"))
5911 call_args[0] = (char *)ldap_handle;
5912 call_args[1] = dn_path;
5914 call_args[3] = NULL;
5917 if (rc = mr_query("get_user_account_by_login", 1, av,
5918 save_query_info, save_argv))
5920 com_err(whoami, 0, "Unable to process user ACE %s for group %s.",
5925 if (rc = user_create(U_END, save_argv, call_args))
5927 com_err(whoami, 0, "Unable to process user ACE %s for group %s.",
5934 com_err(whoami, 0, "Unable to process user Ace %s for group %s",
5944 if (!strcasecmp(AceType, "LIST"))
5946 if (!strcasecmp(GroupName, AceName))
5950 strcpy(GroupName, AceName);
5956 int make_new_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
5957 char *group_name, char *group_ou, char *group_membership,
5958 int group_security_flag, int updateGroup, char *maillist)
5963 LK_ENTRY *group_base;
5966 char *attr_array[3];
5969 call_args[0] = (char *)ldap_handle;
5970 call_args[1] = dn_path;
5971 call_args[2] = group_name;
5972 call_args[3] = (char *)(MOIRA_USERS | MOIRA_KERBEROS | MOIRA_STRINGS);
5973 call_args[4] = (char *)updateGroup;
5974 call_args[5] = MoiraId;
5976 call_args[7] = NULL;
5982 if (rc = mr_query("get_list_info", 1, av, group_create, call_args))
5985 com_err(whoami, 0, "Unable to create list %s : %s", group_name,
5993 com_err(whoami, 0, "Unable to create list %s", group_name);
5994 return(callback_rc);
6000 int populate_group(LDAP *ldap_handle, char *dn_path, char *group_name,
6001 char *group_ou, char *group_membership,
6002 int group_security_flag, char *MoiraId)
6017 char *member_v[] = {NULL, NULL};
6018 char *save_argv[U_END];
6019 char machine_ou[256];
6020 char NewMachineName[1024];
6022 com_err(whoami, 0, "Populating group %s", group_name);
6024 call_args[0] = (char *)ldap_handle;
6025 call_args[1] = dn_path;
6026 call_args[2] = group_name;
6027 call_args[3] = (char *)(MOIRA_USERS | MOIRA_KERBEROS | MOIRA_STRINGS |
6029 call_args[4] = NULL;
6032 if (rc = mr_query("get_end_members_of_list", 1, av,
6033 member_list_build, call_args))
6035 com_err(whoami, 0, "Unable to populate list %s : %s",
6036 group_name, error_message(rc));
6040 members = (char **)malloc(sizeof(char *) * 2);
6042 if (member_base != NULL)
6048 if (!strcasecmp(ptr->type, "LIST"))
6054 if (!strcasecmp(ptr->type, "MACHINE") && !ProcessMachineContainer)
6060 if(!strcasecmp(ptr->type, "USER"))
6062 if(!strcasecmp(ptr->member, PRODUCTION_PRINCIPAL) ||
6063 !strcasecmp(ptr->member, TEST_PRINCIPAL))
6069 if ((rc = check_user(ldap_handle, dn_path, ptr->member,
6070 "")) == AD_NO_USER_FOUND)
6072 com_err(whoami, 0, "creating user %s", ptr->member);
6074 av[0] = ptr->member;
6075 call_args[0] = (char *)ldap_handle;
6076 call_args[1] = dn_path;
6078 call_args[3] = NULL;
6081 if (rc = mr_query("get_user_account_by_login", 1, av,
6082 save_query_info, save_argv))
6084 com_err(whoami, 0, "Unable to create user %s "
6085 "while populating group %s.", ptr->member,
6091 if (rc = user_create(U_END, save_argv, call_args))
6093 com_err(whoami, 0, "Unable to create user %s "
6094 "while populating group %s.", ptr->member,
6102 com_err(whoami, 0, "Unable to create user %s "
6103 "while populating group %s", ptr->member,
6114 sprintf(member, "cn=%s,%s,%s", ptr->member, pUserOu,
6119 sprintf(member, "uid=%s,%s,%s", ptr->member, pUserOu,
6124 else if (!strcasecmp(ptr->type, "STRING"))
6126 if (contact_create(ldap_handle, dn_path, ptr->member,
6130 pUserOu = contact_ou;
6131 sprintf(member, "cn=%s,%s,%s", escape_string(ptr->member),
6134 else if (!strcasecmp(ptr->type, "KERBEROS"))
6136 if (contact_create(ldap_handle, dn_path, ptr->member,
6140 pUserOu = kerberos_ou;
6141 sprintf(member, "cn=%s,%s,%s", escape_string(ptr->member),
6144 else if (!strcasecmp(ptr->type, "MACHINE"))
6146 memset(machine_ou, '\0', sizeof(machine_ou));
6147 memset(NewMachineName, '\0', sizeof(NewMachineName));
6149 if (!get_machine_ou(ldap_handle, dn_path, ptr->member,
6150 machine_ou, NewMachineName))
6152 pUserOu = machine_ou;
6153 sprintf(member, "cn=%s,%s,%s", NewMachineName, pUserOu,
6164 members = (char **)realloc(members, ((i + 2) * sizeof(char *)));
6165 members[i++] = strdup(member);
6170 linklist_free(member_base);
6176 sprintf(group_dn, "cn=%s,%s,%s", group_name, group_ou, dn_path);
6178 if(GroupPopulateDelete)
6181 ADD_ATTR("member", member_v, LDAP_MOD_REPLACE);
6184 if ((rc = ldap_modify_s(ldap_handle, group_dn,
6185 mods)) != LDAP_SUCCESS)
6188 "Unable to populate group membership for %s: %s",
6189 group_dn, ldap_err2string(rc));
6192 for (i = 0; i < n; i++)
6197 ADD_ATTR("member", members, LDAP_MOD_REPLACE);
6200 if ((rc = ldap_modify_s(ldap_handle, group_dn,
6201 mods)) != LDAP_SUCCESS)
6204 "Unable to populate group membership for %s: %s",
6205 group_dn, ldap_err2string(rc));
6208 for (i = 0; i < n; i++)
6216 int process_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
6217 char *group_name, char *group_ou, char *group_membership,
6218 int group_security_flag, int type, char *maillist)
6220 char before_desc[512];
6221 char before_name[256];
6222 char before_group_ou[256];
6223 char before_group_membership[2];
6224 char distinguishedName[256];
6225 char ad_distinguishedName[256];
6227 char *attr_array[3];
6228 int before_security_flag;
6231 LK_ENTRY *group_base;
6234 char ou_security[512];
6235 char ou_distribution[512];
6236 char ou_neither[512];
6239 memset(ad_distinguishedName, '\0', sizeof(ad_distinguishedName));
6240 sprintf(distinguishedName, "CN=%s,%s,%s", group_name, group_ou, dn_path);
6242 memset(filter, '\0', sizeof(filter));
6246 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
6248 "samAccountName", &group_base,
6249 &group_count, filter))
6252 if (type == CHECK_GROUPS)
6254 if (group_count == 1)
6256 strcpy(group_dn, group_base->dn);
6258 if (!strcasecmp(group_dn, distinguishedName))
6260 linklist_free(group_base);
6265 linklist_free(group_base);
6267 if (group_count == 0)
6268 return(AD_NO_GROUPS_FOUND);
6270 if (group_count == 1)
6271 return(AD_WRONG_GROUP_DN_FOUND);
6273 return(AD_MULTIPLE_GROUPS_FOUND);
6276 if (group_count == 0)
6278 return(AD_NO_GROUPS_FOUND);
6281 if (group_count > 1)
6285 strcpy(group_dn, ptr->dn);
6289 if (!strcasecmp(group_dn, ptr->value))
6297 com_err(whoami, 0, "%d groups with moira id = %s", group_count,
6303 com_err(whoami, 0, "%s with moira id = %s", ptr->value, MoiraId);
6307 linklist_free(group_base);
6308 return(AD_MULTIPLE_GROUPS_FOUND);
6315 strcpy(group_dn, ptr->dn);
6317 if (strcasecmp(group_dn, ptr->value))
6318 rc = ldap_delete_s(ldap_handle, ptr->value);
6323 linklist_free(group_base);
6324 memset(filter, '\0', sizeof(filter));
6328 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
6330 "samAccountName", &group_base,
6331 &group_count, filter))
6334 if (group_count == 0)
6335 return(AD_NO_GROUPS_FOUND);
6337 if (group_count > 1)
6338 return(AD_MULTIPLE_GROUPS_FOUND);
6341 strcpy(ad_distinguishedName, group_base->dn);
6342 linklist_free(group_base);
6346 attr_array[0] = "sAMAccountName";
6347 attr_array[1] = NULL;
6349 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6350 &group_base, &group_count,
6351 LDAP_SCOPE_SUBTREE)) != 0)
6353 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6354 MoiraId, ldap_err2string(rc));
6358 sprintf(filter, "(sAMAccountName=%s)", group_base->value);
6360 if (!strcasecmp(ad_distinguishedName, distinguishedName))
6362 linklist_free(group_base);
6368 linklist_free(group_base);
6371 memset(ou_both, '\0', sizeof(ou_both));
6372 memset(ou_security, '\0', sizeof(ou_security));
6373 memset(ou_distribution, '\0', sizeof(ou_distribution));
6374 memset(ou_neither, '\0', sizeof(ou_neither));
6375 memset(before_name, '\0', sizeof(before_name));
6376 memset(before_desc, '\0', sizeof(before_desc));
6377 memset(before_group_membership, '\0', sizeof(before_group_membership));
6379 attr_array[0] = "name";
6380 attr_array[1] = NULL;
6382 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6383 &group_base, &group_count,
6384 LDAP_SCOPE_SUBTREE)) != 0)
6386 com_err(whoami, 0, "Unable to get list name with MoiraId = %s: %s",
6387 MoiraId, ldap_err2string(rc));
6391 strcpy(before_name, group_base->value);
6392 linklist_free(group_base);
6396 attr_array[0] = "description";
6397 attr_array[1] = NULL;
6399 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6400 &group_base, &group_count,
6401 LDAP_SCOPE_SUBTREE)) != 0)
6404 "Unable to get list description with MoiraId = %s: %s",
6405 MoiraId, ldap_err2string(rc));
6409 if (group_count != 0)
6411 strcpy(before_desc, group_base->value);
6412 linklist_free(group_base);
6417 change_to_lower_case(ad_distinguishedName);
6418 strcpy(ou_both, group_ou_both);
6419 change_to_lower_case(ou_both);
6420 strcpy(ou_security, group_ou_security);
6421 change_to_lower_case(ou_security);
6422 strcpy(ou_distribution, group_ou_distribution);
6423 change_to_lower_case(ou_distribution);
6424 strcpy(ou_neither, group_ou_neither);
6425 change_to_lower_case(ou_neither);
6427 if (strstr(ad_distinguishedName, ou_both))
6429 strcpy(before_group_ou, group_ou_both);
6430 before_group_membership[0] = 'B';
6431 before_security_flag = 1;
6433 else if (strstr(ad_distinguishedName, ou_security))
6435 strcpy(before_group_ou, group_ou_security);
6436 before_group_membership[0] = 'S';
6437 before_security_flag = 1;
6439 else if (strstr(ad_distinguishedName, ou_distribution))
6441 strcpy(before_group_ou, group_ou_distribution);
6442 before_group_membership[0] = 'D';
6443 before_security_flag = 0;
6445 else if (strstr(ad_distinguishedName, ou_neither))
6447 strcpy(before_group_ou, group_ou_neither);
6448 before_group_membership[0] = 'N';
6449 before_security_flag = 0;
6452 return(AD_NO_OU_FOUND);
6454 rc = group_rename(ldap_handle, dn_path, before_name,
6455 before_group_membership,
6456 before_group_ou, before_security_flag, before_desc,
6457 group_name, group_membership, group_ou,
6458 group_security_flag,
6459 before_desc, MoiraId, filter, maillist);
6464 void change_to_lower_case(char *ptr)
6468 for (i = 0; i < (int)strlen(ptr); i++)
6470 ptr[i] = tolower(ptr[i]);
6474 int ad_get_group(LDAP *ldap_handle, char *dn_path,
6475 char *group_name, char *group_membership,
6476 char *MoiraId, char *attribute,
6477 LK_ENTRY **linklist_base, int *linklist_count,
6482 char *attr_array[3];
6486 (*linklist_base) = NULL;
6487 (*linklist_count) = 0;
6489 if (strlen(rFilter) != 0)
6491 strcpy(filter, rFilter);
6492 attr_array[0] = attribute;
6493 attr_array[1] = NULL;
6495 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6496 linklist_base, linklist_count,
6497 LDAP_SCOPE_SUBTREE)) != 0)
6499 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6500 MoiraId, ldap_err2string(rc));
6504 if ((*linklist_count) == 1)
6506 strcpy(rFilter, filter);
6511 linklist_free((*linklist_base));
6512 (*linklist_base) = NULL;
6513 (*linklist_count) = 0;
6515 if (strlen(MoiraId) != 0)
6517 sprintf(filter, "(&(objectClass=group)(mitMoiraId=%s))", MoiraId);
6519 attr_array[0] = attribute;
6520 attr_array[1] = NULL;
6522 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6523 linklist_base, linklist_count,
6524 LDAP_SCOPE_SUBTREE)) != 0)
6526 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6527 MoiraId, ldap_err2string(rc));
6532 if ((*linklist_count) > 1)
6534 com_err(whoami, 0, "multiple groups with mitMoiraId = %s", MoiraId);
6535 pPtr = (*linklist_base);
6539 com_err(whoami, 0, "groups %s has mitMoiraId = %s", pPtr->value,
6544 linklist_free((*linklist_base));
6545 (*linklist_base) = NULL;
6546 (*linklist_count) = 0;
6549 if ((*linklist_count) == 1)
6552 pPtr = (*linklist_base);
6553 dn = strdup(pPtr->dn);
6556 if (!memcmp(dn, group_name, strlen(group_name)))
6558 strcpy(rFilter, filter);
6563 linklist_free((*linklist_base));
6564 (*linklist_base) = NULL;
6565 (*linklist_count) = 0;
6566 sprintf(filter, "(sAMAccountName=%s%s)", group_name, group_suffix);
6568 attr_array[0] = attribute;
6569 attr_array[1] = NULL;
6571 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6572 linklist_base, linklist_count,
6573 LDAP_SCOPE_SUBTREE)) != 0)
6575 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6576 MoiraId, ldap_err2string(rc));
6580 if ((*linklist_count) == 1)
6582 strcpy(rFilter, filter);
6589 int check_user(LDAP *ldap_handle, char *dn_path, char *UserName, char *MoiraId)
6592 char *attr_array[3];
6593 char SamAccountName[64];
6596 LK_ENTRY *group_base;
6602 if (strlen(MoiraId) != 0)
6604 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
6606 attr_array[0] = "sAMAccountName";
6607 attr_array[1] = NULL;
6608 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6609 &group_base, &group_count,
6610 LDAP_SCOPE_SUBTREE)) != 0)
6612 com_err(whoami, 0, "Unable to process user %s : %s",
6613 UserName, ldap_err2string(rc));
6617 if (group_count > 1)
6619 com_err(whoami, 0, "multiple users exist with MoiraId = %s",
6625 com_err(whoami, 0, "user %s exist with MoiraId = %s",
6626 gPtr->value, MoiraId);
6632 if (group_count != 1)
6634 linklist_free(group_base);
6637 sprintf(filter, "(sAMAccountName=%s)", UserName);
6638 attr_array[0] = "sAMAccountName";
6639 attr_array[1] = NULL;
6641 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6642 &group_base, &group_count,
6643 LDAP_SCOPE_SUBTREE)) != 0)
6645 com_err(whoami, 0, "Unable to process user %s : %s",
6646 UserName, ldap_err2string(rc));
6651 if (group_count != 1)
6653 linklist_free(group_base);
6654 return(AD_NO_USER_FOUND);
6657 strcpy(SamAccountName, group_base->value);
6658 linklist_free(group_base);
6662 if (strcmp(SamAccountName, UserName))
6665 "User object %s with MoiraId %s has mismatched usernames "
6666 "(LDAP username %s, Moira username %s)", SamAccountName,
6667 MoiraId, SamAccountName, UserName);
6673 void container_get_dn(char *src, char *dest)
6680 memset(array, '\0', 20 * sizeof(array[0]));
6682 if (strlen(src) == 0)
6704 strcpy(dest, "OU=");
6708 strcat(dest, array[n-1]);
6712 strcat(dest, ",OU=");
6719 void container_get_name(char *src, char *dest)
6724 if (strlen(src) == 0)
6744 void container_check(LDAP *ldap_handle, char *dn_path, char *name)
6751 strcpy(cName, name);
6753 for (i = 0; i < (int)strlen(cName); i++)
6755 if (cName[i] == '/')
6758 av[CONTAINER_NAME] = cName;
6759 av[CONTAINER_DESC] = "";
6760 av[CONTAINER_LOCATION] = "";
6761 av[CONTAINER_CONTACT] = "";
6762 av[CONTAINER_TYPE] = "";
6763 av[CONTAINER_ID] = "";
6764 av[CONTAINER_ROWID] = "";
6765 rc = container_create(ldap_handle, dn_path, 7, av);
6767 if (rc == LDAP_SUCCESS)
6769 com_err(whoami, 0, "container %s created without a mitMoiraId",
6778 int container_rename(LDAP *ldap_handle, char *dn_path, int beforec,
6779 char **before, int afterc, char **after)
6784 char new_dn_path[256];
6786 char distinguishedName[256];
6791 memset(cName, '\0', sizeof(cName));
6792 container_get_name(after[CONTAINER_NAME], cName);
6794 if (!check_container_name(cName))
6796 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6798 return(AD_INVALID_NAME);
6801 memset(distinguishedName, '\0', sizeof(distinguishedName));
6803 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
6804 distinguishedName, beforec, before))
6807 if (strlen(distinguishedName) == 0)
6809 rc = container_create(ldap_handle, dn_path, afterc, after);
6813 strcpy(temp, after[CONTAINER_NAME]);
6816 for (i = 0; i < (int)strlen(temp); i++)
6826 container_get_dn(temp, dName);
6828 if (strlen(temp) != 0)
6829 sprintf(new_dn_path, "%s,%s", dName, dn_path);
6831 sprintf(new_dn_path, "%s", dn_path);
6833 sprintf(new_cn, "OU=%s", cName);
6835 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
6837 if ((rc = ldap_rename_s(ldap_handle, distinguishedName, new_cn, new_dn_path,
6838 TRUE, NULL, NULL)) != LDAP_SUCCESS)
6840 com_err(whoami, 0, "Unable to rename container from %s to %s : %s",
6841 before[CONTAINER_NAME], after[CONTAINER_NAME],
6842 ldap_err2string(rc));
6846 memset(dName, '\0', sizeof(dName));
6847 container_get_dn(after[CONTAINER_NAME], dName);
6848 rc = container_adupdate(ldap_handle, dn_path, dName, "", afterc, after);
6853 int container_delete(LDAP *ldap_handle, char *dn_path, int count, char **av)
6855 char distinguishedName[256];
6858 memset(distinguishedName, '\0', sizeof(distinguishedName));
6860 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
6861 distinguishedName, count, av))
6864 if (strlen(distinguishedName) == 0)
6867 if ((rc = ldap_delete_s(ldap_handle, distinguishedName)) != LDAP_SUCCESS)
6869 if (rc == LDAP_NOT_ALLOWED_ON_NONLEAF)
6870 container_move_objects(ldap_handle, dn_path, distinguishedName);
6872 com_err(whoami, 0, "Unable to delete container %s from directory : %s",
6873 av[CONTAINER_NAME], ldap_err2string(rc));
6879 int container_create(LDAP *ldap_handle, char *dn_path, int count, char **av)
6881 char *attr_array[3];
6882 LK_ENTRY *group_base;
6885 char *objectClass_v[] = {"top",
6886 "organizationalUnit",
6889 char *ou_v[] = {NULL, NULL};
6890 char *name_v[] = {NULL, NULL};
6891 char *moiraId_v[] = {NULL, NULL};
6892 char *desc_v[] = {NULL, NULL};
6893 char *managedBy_v[] = {NULL, NULL};
6896 char managedByDN[256];
6903 memset(filter, '\0', sizeof(filter));
6904 memset(dName, '\0', sizeof(dName));
6905 memset(cName, '\0', sizeof(cName));
6906 memset(managedByDN, '\0', sizeof(managedByDN));
6907 container_get_dn(av[CONTAINER_NAME], dName);
6908 container_get_name(av[CONTAINER_NAME], cName);
6910 if ((strlen(cName) == 0) || (strlen(dName) == 0))
6912 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6914 return(AD_INVALID_NAME);
6917 if (!check_container_name(cName))
6919 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6921 return(AD_INVALID_NAME);
6925 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
6927 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
6929 ADD_ATTR("ou", ou_v, LDAP_MOD_ADD);
6931 if (strlen(av[CONTAINER_ROWID]) != 0)
6933 moiraId_v[0] = av[CONTAINER_ROWID];
6934 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_ADD);
6937 if (strlen(av[CONTAINER_DESC]) != 0)
6939 desc_v[0] = av[CONTAINER_DESC];
6940 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
6943 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
6945 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
6947 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID],
6950 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID],
6951 kerberos_ou, dn_path);
6952 managedBy_v[0] = managedByDN;
6953 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
6958 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
6960 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)"
6961 "(objectClass=user)))", av[CONTAINER_ID]);
6964 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
6966 sprintf(filter, "(&(objectClass=group)(cn=%s))",
6970 if (strlen(filter) != 0)
6972 attr_array[0] = "distinguishedName";
6973 attr_array[1] = NULL;
6976 if ((rc = linklist_build(ldap_handle, dn_path, filter,
6978 &group_base, &group_count,
6979 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
6981 if (group_count == 1)
6983 strcpy(managedByDN, group_base->value);
6984 managedBy_v[0] = managedByDN;
6985 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
6987 linklist_free(group_base);
6997 sprintf(temp, "%s,%s", dName, dn_path);
6998 rc = ldap_add_ext_s(ldap_handle, temp, mods, NULL, NULL);
7000 for (i = 0; i < n; i++)
7003 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
7005 com_err(whoami, 0, "Unable to create container %s : %s",
7006 cName, ldap_err2string(rc));
7010 if (rc == LDAP_ALREADY_EXISTS)
7012 if (strlen(av[CONTAINER_ROWID]) != 0)
7013 rc = container_adupdate(ldap_handle, dn_path, dName, "", count, av);
7019 int container_update(LDAP *ldap_handle, char *dn_path, int beforec,
7020 char **before, int afterc, char **after)
7022 char distinguishedName[256];
7025 memset(distinguishedName, '\0', sizeof(distinguishedName));
7027 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
7028 distinguishedName, afterc, after))
7031 if (strlen(distinguishedName) == 0)
7033 rc = container_create(ldap_handle, dn_path, afterc, after);
7037 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
7038 rc = container_adupdate(ldap_handle, dn_path, "", distinguishedName, afterc,
7044 int container_get_distinguishedName(LDAP *ldap_handle, char *dn_path,
7045 char *distinguishedName, int count,
7048 char *attr_array[3];
7049 LK_ENTRY *group_base;
7056 memset(filter, '\0', sizeof(filter));
7057 memset(dName, '\0', sizeof(dName));
7058 memset(cName, '\0', sizeof(cName));
7059 container_get_dn(av[CONTAINER_NAME], dName);
7060 container_get_name(av[CONTAINER_NAME], cName);
7062 if (strlen(dName) == 0)
7064 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
7065 av[CONTAINER_NAME]);
7066 return(AD_INVALID_NAME);
7069 if (!check_container_name(cName))
7071 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
7073 return(AD_INVALID_NAME);
7076 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))",
7077 av[CONTAINER_ROWID]);
7078 attr_array[0] = "distinguishedName";
7079 attr_array[1] = NULL;
7083 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7084 &group_base, &group_count,
7085 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7087 if (group_count == 1)
7089 strcpy(distinguishedName, group_base->value);
7092 linklist_free(group_base);
7097 if (strlen(distinguishedName) == 0)
7099 sprintf(filter, "(&(objectClass=organizationalUnit)"
7100 "(distinguishedName=%s,%s))", dName, dn_path);
7101 attr_array[0] = "distinguishedName";
7102 attr_array[1] = NULL;
7106 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7107 &group_base, &group_count,
7108 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7110 if (group_count == 1)
7112 strcpy(distinguishedName, group_base->value);
7115 linklist_free(group_base);
7124 int container_adupdate(LDAP *ldap_handle, char *dn_path, char *dName,
7125 char *distinguishedName, int count, char **av)
7127 char *attr_array[5];
7128 LK_ENTRY *group_base;
7133 char *moiraId_v[] = {NULL, NULL};
7134 char *desc_v[] = {NULL, NULL};
7135 char *managedBy_v[] = {NULL, NULL};
7136 char managedByDN[256];
7145 strcpy(ad_path, distinguishedName);
7147 if (strlen(dName) != 0)
7148 sprintf(ad_path, "%s,%s", dName, dn_path);
7150 sprintf(filter, "(&(objectClass=organizationalUnit)(distinguishedName=%s))",
7153 if (strlen(av[CONTAINER_ID]) != 0)
7154 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))",
7155 av[CONTAINER_ROWID]);
7157 attr_array[0] = "mitMoiraId";
7158 attr_array[1] = "description";
7159 attr_array[2] = "managedBy";
7160 attr_array[3] = NULL;
7164 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7165 &group_base, &group_count,
7166 LDAP_SCOPE_SUBTREE)) != LDAP_SUCCESS)
7168 com_err(whoami, 0, "Unable to retreive container info for %s : %s",
7169 av[CONTAINER_NAME], ldap_err2string(rc));
7173 memset(managedByDN, '\0', sizeof(managedByDN));
7174 memset(moiraId, '\0', sizeof(moiraId));
7175 memset(desc, '\0', sizeof(desc));
7180 if (!strcasecmp(pPtr->attribute, "description"))
7181 strcpy(desc, pPtr->value);
7182 else if (!strcasecmp(pPtr->attribute, "managedBy"))
7183 strcpy(managedByDN, pPtr->value);
7184 else if (!strcasecmp(pPtr->attribute, "mitMoiraId"))
7185 strcpy(moiraId, pPtr->value);
7189 linklist_free(group_base);
7194 if (strlen(av[CONTAINER_ROWID]) != 0)
7196 moiraId_v[0] = av[CONTAINER_ROWID];
7197 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_REPLACE);
7200 if (strlen(av[CONTAINER_DESC]) != 0)
7202 attribute_update(ldap_handle, ad_path, av[CONTAINER_DESC], "description",
7207 if (strlen(desc) != 0)
7209 attribute_update(ldap_handle, ad_path, "", "description", dName);
7213 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
7215 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
7217 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID],
7220 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID],
7221 kerberos_ou, dn_path);
7222 managedBy_v[0] = managedByDN;
7223 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
7227 if (strlen(managedByDN) != 0)
7229 attribute_update(ldap_handle, ad_path, "", "managedBy",
7236 memset(filter, '\0', sizeof(filter));
7238 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
7240 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)"
7241 "(objectClass=user)))", av[CONTAINER_ID]);
7244 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
7246 sprintf(filter, "(&(objectClass=group)(cn=%s))",
7250 if (strlen(filter) != 0)
7252 attr_array[0] = "distinguishedName";
7253 attr_array[1] = NULL;
7256 if ((rc = linklist_build(ldap_handle, dn_path, filter,
7257 attr_array, &group_base, &group_count,
7258 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7260 if (group_count == 1)
7262 strcpy(managedByDN, group_base->value);
7263 managedBy_v[0] = managedByDN;
7264 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
7268 if (strlen(managedByDN) != 0)
7270 attribute_update(ldap_handle, ad_path, "",
7271 "managedBy", dName);
7275 linklist_free(group_base);
7282 if (strlen(managedByDN) != 0)
7284 attribute_update(ldap_handle, ad_path, "", "managedBy",
7294 return(LDAP_SUCCESS);
7296 rc = ldap_modify_s(ldap_handle, ad_path, mods);
7298 for (i = 0; i < n; i++)
7301 if (rc != LDAP_SUCCESS)
7303 com_err(whoami, 0, "Unable to modify container info for %s : %s",
7304 av[CONTAINER_NAME], ldap_err2string(rc));
7311 int container_move_objects(LDAP *ldap_handle, char *dn_path, char *dName)
7313 char *attr_array[3];
7314 LK_ENTRY *group_base;
7321 int NumberOfEntries = 10;
7325 rc = ldap_set_option(ldap_handle, LDAP_OPT_SIZELIMIT, &NumberOfEntries);
7327 for (i = 0; i < 3; i++)
7329 memset(filter, '\0', sizeof(filter));
7333 strcpy(filter, "(!(|(objectClass=computer)"
7334 "(objectClass=organizationalUnit)))");
7335 attr_array[0] = "cn";
7336 attr_array[1] = NULL;
7340 strcpy(filter, "(objectClass=computer)");
7341 attr_array[0] = "cn";
7342 attr_array[1] = NULL;
7346 strcpy(filter, "(objectClass=organizationalUnit)");
7347 attr_array[0] = "ou";
7348 attr_array[1] = NULL;
7353 if ((rc = linklist_build(ldap_handle, dName, filter, attr_array,
7354 &group_base, &group_count,
7355 LDAP_SCOPE_SUBTREE)) != LDAP_SUCCESS)
7360 if (group_count == 0)
7367 if (!strcasecmp(pPtr->attribute, "cn"))
7369 sprintf(new_cn, "cn=%s", pPtr->value);
7371 sprintf(temp, "%s,%s", orphans_other_ou, dn_path);
7373 sprintf(temp, "%s,%s", orphans_machines_ou, dn_path);
7378 rc = ldap_rename_s(ldap_handle, pPtr->dn, new_cn, temp,
7380 if (rc == LDAP_ALREADY_EXISTS)
7382 sprintf(new_cn, "cn=%s_%d", pPtr->value, count);
7389 else if (!strcasecmp(pPtr->attribute, "ou"))
7391 rc = ldap_delete_s(ldap_handle, pPtr->dn);
7397 linklist_free(group_base);
7406 int get_machine_ou(LDAP *ldap_handle, char *dn_path, char *member,
7407 char *machine_ou, char *NewMachineName)
7409 LK_ENTRY *group_base;
7413 char *attr_array[3];
7420 strcpy(NewMachineName, member);
7421 rc = moira_connect();
7422 rc = GetMachineName(NewMachineName);
7425 if (strlen(NewMachineName) == 0)
7427 com_err(whoami, 0, "Unable to find alais for machine %s in Moira",
7433 pPtr = strchr(NewMachineName, '.');
7440 sprintf(filter, "(sAMAccountName=%s$)", NewMachineName);
7441 attr_array[0] = "cn";
7442 attr_array[1] = NULL;
7443 sprintf(temp, "%s", dn_path);
7445 if ((rc = linklist_build(ldap_handle, temp, filter, attr_array,
7446 &group_base, &group_count,
7447 LDAP_SCOPE_SUBTREE)) != 0)
7449 com_err(whoami, 0, "Unable to process machine %s : %s",
7450 member, ldap_err2string(rc));
7454 if (group_count != 1)
7459 strcpy(dn, group_base->dn);
7460 strcpy(cn, group_base->value);
7462 for (i = 0; i < (int)strlen(dn); i++)
7463 dn[i] = tolower(dn[i]);
7465 for (i = 0; i < (int)strlen(cn); i++)
7466 cn[i] = tolower(cn[i]);
7468 linklist_free(group_base);
7470 pPtr = strstr(dn, cn);
7474 com_err(whoami, 0, "Unable to process machine %s",
7479 pPtr += strlen(cn) + 1;
7480 strcpy(machine_ou, pPtr);
7482 pPtr = strstr(machine_ou, "dc=");
7486 com_err(whoami, 0, "Unable to process machine %s",
7497 int machine_move_to_ou(LDAP *ldap_handle, char * dn_path,
7498 char *MoiraMachineName, char *DestinationOu)
7502 char MachineName[128];
7504 char *attr_array[3];
7509 LK_ENTRY *group_base;
7514 strcpy(MachineName, MoiraMachineName);
7515 rc = GetMachineName(MachineName);
7517 if (strlen(MachineName) == 0)
7519 com_err(whoami, 0, "Unable to find alais for machine %s in Moira",
7524 cPtr = strchr(MachineName, '.');
7529 sprintf(filter, "(sAMAccountName=%s$)", MachineName);
7530 attr_array[0] = "sAMAccountName";
7531 attr_array[1] = NULL;
7533 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7535 &group_count, LDAP_SCOPE_SUBTREE)) != 0)
7537 com_err(whoami, 0, "Unable to process machine %s : %s",
7538 MoiraMachineName, ldap_err2string(rc));
7542 if (group_count == 1)
7543 strcpy(OldDn, group_base->dn);
7545 linklist_free(group_base);
7548 if (group_count != 1)
7550 com_err(whoami, 0, "Unable to find machine %s in directory: %s",
7555 sprintf(NewOu, "%s,%s", DestinationOu, dn_path);
7556 cPtr = strchr(OldDn, ',');
7561 if (!strcasecmp(cPtr, NewOu))
7565 sprintf(NewCn, "CN=%s", MachineName);
7566 rc = ldap_rename_s(ldap_handle, OldDn, NewCn, NewOu, TRUE, NULL, NULL);
7571 int machine_check(LDAP *ldap_handle, char *dn_path, char *machine_name)
7577 memset(Name, '\0', sizeof(Name));
7578 strcpy(Name, machine_name);
7580 pPtr = strchr(Name, '.');
7586 return(!(rc = checkADname(ldap_handle, dn_path, Name)));
7589 int machine_get_moira_container(LDAP *ldap_handle, char *dn_path,
7590 char *machine_name, char *container_name)
7596 av[0] = machine_name;
7597 call_args[0] = (char *)container_name;
7598 rc = mr_query("get_machine_to_container_map", 1, av,
7599 machine_GetMoiraContainer, call_args);
7603 int machine_GetMoiraContainer(int ac, char **av, void *ptr)
7608 strcpy(call_args[0], av[1]);
7612 int Moira_container_group_create(char **after)
7618 memset(GroupName, '\0', sizeof(GroupName));
7619 rc = Moira_groupname_create(GroupName, after[CONTAINER_NAME],
7620 after[CONTAINER_ROWID]);
7624 argv[L_NAME] = GroupName;
7625 argv[L_ACTIVE] = "1";
7626 argv[L_PUBLIC] = "0";
7627 argv[L_HIDDEN] = "0";
7628 argv[L_MAILLIST] = "0";
7629 argv[L_GROUP] = "1";
7630 argv[L_GID] = UNIQUE_GID;
7631 argv[L_NFSGROUP] = "0";
7632 argv[L_MAILMAN] = "0";
7633 argv[L_MAILMAN_SERVER] = "[NONE]";
7634 argv[L_DESC] = "auto created container group";
7635 argv[L_ACE_TYPE] = "USER";
7636 argv[L_MEMACE_TYPE] = "USER";
7637 argv[L_ACE_NAME] = "sms";
7638 argv[L_MEMACE_NAME] = "sms";
7640 if (rc = mr_query("add_list", 15, argv, NULL, NULL))
7643 "Unable to create container group %s for container %s: %s",
7644 GroupName, after[CONTAINER_NAME], error_message(rc));
7647 Moira_setContainerGroup(after[CONTAINER_NAME], GroupName);
7648 Moira_addGroupToParent(after[CONTAINER_NAME], GroupName);
7653 int Moira_container_group_update(char **before, char **after)
7656 char BeforeGroupName[64];
7657 char AfterGroupName[64];
7660 if (!strcasecmp(after[CONTAINER_NAME], before[CONTAINER_NAME]))
7663 memset(BeforeGroupName, '\0', sizeof(BeforeGroupName));
7664 Moira_getGroupName(after[CONTAINER_NAME], BeforeGroupName, 0);
7665 if (strlen(BeforeGroupName) == 0)
7668 memset(AfterGroupName, '\0', sizeof(AfterGroupName));
7669 rc = Moira_groupname_create(AfterGroupName, after[CONTAINER_NAME],
7670 after[CONTAINER_ROWID]);
7674 if (strcasecmp(BeforeGroupName, AfterGroupName))
7676 argv[L_NAME] = BeforeGroupName;
7677 argv[L_NAME + 1] = AfterGroupName;
7678 argv[L_ACTIVE + 1] = "1";
7679 argv[L_PUBLIC + 1] = "0";
7680 argv[L_HIDDEN + 1] = "0";
7681 argv[L_MAILLIST + 1] = "0";
7682 argv[L_GROUP + 1] = "1";
7683 argv[L_GID + 1] = UNIQUE_GID;
7684 argv[L_NFSGROUP + 1] = "0";
7685 argv[L_MAILMAN + 1] = "0";
7686 argv[L_MAILMAN_SERVER + 1] = "[NONE]";
7687 argv[L_DESC + 1] = "auto created container group";
7688 argv[L_ACE_TYPE + 1] = "USER";
7689 argv[L_MEMACE_TYPE + 1] = "USER";
7690 argv[L_ACE_NAME + 1] = "sms";
7691 argv[L_MEMACE_NAME + 1] = "sms";
7693 if (rc = mr_query("update_list", 16, argv, NULL, NULL))
7696 "Unable to rename container group from %s to %s: %s",
7697 BeforeGroupName, AfterGroupName, error_message(rc));
7704 int Moira_container_group_delete(char **before)
7709 char ParentGroupName[64];
7711 memset(ParentGroupName, '\0', sizeof(ParentGroupName));
7712 Moira_getGroupName(before[CONTAINER_NAME], ParentGroupName, 1);
7714 memset(GroupName, '\0', sizeof(GroupName));
7716 if (strcmp(before[CONTAINER_GROUP_NAME], "[none]"))
7717 strcpy(GroupName, before[CONTAINER_GROUP_NAME]);
7719 if ((strlen(ParentGroupName) != 0) && (strlen(GroupName) != 0))
7721 argv[0] = ParentGroupName;
7723 argv[2] = GroupName;
7725 if (rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL))
7728 "Unable to delete container group %s from list: %s",
7729 GroupName, ParentGroupName, error_message(rc));
7733 if (strlen(GroupName) != 0)
7735 argv[0] = GroupName;
7737 if (rc = mr_query("delete_list", 1, argv, NULL, NULL))
7739 com_err(whoami, 0, "Unable to delete container group %s : %s",
7740 GroupName, error_message(rc));
7747 int Moira_groupname_create(char *GroupName, char *ContainerName,
7748 char *ContainerRowID)
7753 char newGroupName[64];
7754 char tempGroupName[64];
7760 strcpy(temp, ContainerName);
7762 ptr1 = strrchr(temp, '/');
7768 ptr1 = strrchr(temp, '/');
7772 sprintf(tempgname, "%s-%s", ++ptr1, ptr);
7775 strcpy(tempgname, ptr);
7778 strcpy(tempgname, temp);
7780 if (strlen(tempgname) > 25)
7781 tempgname[25] ='\0';
7783 sprintf(newGroupName, "cnt-%s", tempgname);
7785 /* change everything to lower case */
7791 *ptr = tolower(*ptr);
7799 strcpy(tempGroupName, newGroupName);
7802 /* append 0-9 then a-z if a duplicate is found */
7805 argv[0] = newGroupName;
7807 if (rc = mr_query("get_list_info", 1, argv, NULL, NULL))
7809 if (rc == MR_NO_MATCH)
7811 com_err(whoami, 0, "Moira error while creating group name for "
7812 "container %s : %s", ContainerName, error_message(rc));
7816 sprintf(newGroupName, "%s-%c", tempGroupName, i);
7820 com_err(whoami, 0, "Unable to find a unique group name for "
7821 "container %s: too many duplicate container names",
7832 strcpy(GroupName, newGroupName);
7836 int Moira_setContainerGroup(char *origContainerName, char *GroupName)
7841 argv[0] = origContainerName;
7842 argv[1] = GroupName;
7844 if ((rc = mr_query("set_container_list", 2, argv, NULL, NULL)))
7847 "Unable to set container group %s in container %s: %s",
7848 GroupName, origContainerName, error_message(rc));
7854 int Moira_addGroupToParent(char *origContainerName, char *GroupName)
7856 char ContainerName[64];
7857 char ParentGroupName[64];
7861 strcpy(ContainerName, origContainerName);
7863 Moira_getGroupName(ContainerName, ParentGroupName, 1);
7865 /* top-level container */
7866 if (strlen(ParentGroupName) == 0)
7869 argv[0] = ParentGroupName;
7871 argv[2] = GroupName;
7873 if ((rc = mr_query("add_member_to_list", 3, argv, NULL, NULL)))
7876 "Unable to add container group %s to parent group %s: %s",
7877 GroupName, ParentGroupName, error_message(rc));
7883 int Moira_getContainerGroup(int ac, char **av, void *ptr)
7888 strcpy(call_args[0], av[1]);
7893 int Moira_getGroupName(char *origContainerName, char *GroupName,
7896 char ContainerName[64];
7902 strcpy(ContainerName, origContainerName);
7906 ptr = strrchr(ContainerName, '/');
7914 argv[0] = ContainerName;
7916 call_args[0] = GroupName;
7917 call_args[1] = NULL;
7919 if (!(rc = mr_query("get_container_list", 1, argv, Moira_getContainerGroup,
7922 if (strlen(GroupName) != 0)
7927 com_err(whoami, 0, "Unable to get container group from container %s: %s",
7928 ContainerName, error_message(rc));
7930 com_err(whoami, 0, "Unable to get container group from container %s",
7936 int Moira_process_machine_container_group(char *MachineName, char* GroupName,
7942 if (strcmp(GroupName, "[none]") == 0)
7945 argv[0] = GroupName;
7946 argv[1] = "MACHINE";
7947 argv[2] = MachineName;
7950 rc = mr_query("add_member_to_list", 3, argv, NULL, NULL);
7952 rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL);
7956 com_err(whoami, 0, "Unable to add machine %s to container group%s: %s",
7957 MachineName, GroupName, error_message(rc));
7963 int GetMachineName(char *MachineName)
7966 char NewMachineName[1024];
7973 // If the address happens to be in the top-level MIT domain, great!
7974 strcpy(NewMachineName, MachineName);
7976 for (i = 0; i < (int)strlen(NewMachineName); i++)
7977 NewMachineName[i] = toupper(NewMachineName[i]);
7979 szDot = strchr(NewMachineName,'.');
7981 if ((szDot) && (!strcasecmp(szDot+1, DOMAIN_SUFFIX)))
7986 // If not, see if it has a Moira alias in the top-level MIT domain.
7987 memset(NewMachineName, '\0', sizeof(NewMachineName));
7989 args[1] = MachineName;
7990 call_args[0] = NewMachineName;
7991 call_args[1] = NULL;
7993 if (rc = mr_query("get_hostalias", 2, args, ProcessMachineName, call_args))
7995 com_err(whoami, 0, "Unable to resolve machine name %s : %s",
7996 MachineName, error_message(rc));
7997 strcpy(MachineName, "");
8001 if (strlen(NewMachineName) != 0)
8002 strcpy(MachineName, NewMachineName);
8004 strcpy(MachineName, "");
8009 int ProcessMachineName(int ac, char **av, void *ptr)
8012 char MachineName[1024];
8018 if (strlen(call_args[0]) == 0)
8020 strcpy(MachineName, av[0]);
8022 for (i = 0; i < (int)strlen(MachineName); i++)
8023 MachineName[i] = toupper(MachineName[i]);
8025 szDot = strchr(MachineName,'.');
8027 if ((szDot) && (!strcasecmp(szDot+1,DOMAIN_SUFFIX)))
8029 strcpy(call_args[0], MachineName);
8036 void SwitchSFU(LDAPMod **mods, int *UseSFU30, int n)
8042 for (i = 0; i < n; i++)
8044 if (!strcmp(mods[i]->mod_type, "msSFU30UidNumber"))
8045 mods[i]->mod_type = "uidNumber";
8052 for (i = 0; i < n; i++)
8054 if (!strcmp(mods[i]->mod_type, "uidNumber"))
8055 mods[i]->mod_type = "msSFU30UidNumber";
8062 int SetHomeDirectory(LDAP *ldap_handle, char *user_name,
8063 char *DistinguishedName,
8064 char *WinHomeDir, char *WinProfileDir,
8065 char **homedir_v, char **winProfile_v,
8066 char **drives_v, LDAPMod **mods,
8073 char winProfile[1024];
8076 char apple_homedir[1024];
8077 char *apple_homedir_v[] = {NULL, NULL};
8081 LDAPMod *DelMods[20];
8083 char *save_argv[FS_END];
8084 char *fsgroup_save_argv[2];
8086 memset(homeDrive, '\0', sizeof(homeDrive));
8087 memset(path, '\0', sizeof(path));
8088 memset(winPath, '\0', sizeof(winPath));
8089 memset(winProfile, '\0', sizeof(winProfile));
8091 if(!ActiveDirectory)
8093 if (rc = moira_connect())
8095 critical_alert("Ldap incremental",
8096 "Error contacting Moira server : %s",
8101 argv[0] = user_name;
8103 if (!(rc = mr_query("get_filesys_by_label", 1, argv, save_query_info,
8106 if(!strcmp(save_argv[FS_TYPE], "FSGROUP") ||
8107 !strcmp(save_argv[FS_TYPE], "MUL"))
8110 argv[0] = save_argv[FS_NAME];
8113 if (!(rc = mr_query("get_fsgroup_members", 1, argv,
8114 save_fsgroup_info, fsgroup_save_argv)))
8118 argv[0] = fsgroup_save_argv[0];
8120 if (!(rc = mr_query("get_filesys_by_label", 1, argv,
8121 save_query_info, save_argv)))
8123 strcpy(path, save_argv[FS_PACK]);
8130 strcpy(path, save_argv[FS_PACK]);
8138 if (!strnicmp(path, AFS, strlen(AFS)))
8140 sprintf(homedir, "%s", path);
8141 sprintf(apple_homedir, "%s/MacData", path);
8142 homedir_v[0] = homedir;
8143 apple_homedir_v[0] = apple_homedir;
8144 ADD_ATTR("homeDirectory", homedir_v, OpType);
8145 ADD_ATTR("apple-user-homeDirectory", apple_homedir_v,
8151 homedir_v[0] = "NONE";
8152 apple_homedir_v[0] = "NONE";
8153 ADD_ATTR("homeDirectory", homedir_v, OpType);
8154 ADD_ATTR("apple-user-homeDirectory", apple_homedir_v,
8161 if ((!strcasecmp(WinHomeDir, "[afs]")) ||
8162 (!strcasecmp(WinProfileDir, "[afs]")))
8164 if (rc = moira_connect())
8166 critical_alert("Ldap incremental",
8167 "Error contacting Moira server : %s",
8172 argv[0] = user_name;
8174 if (!(rc = mr_query("get_filesys_by_label", 1, argv, save_query_info,
8177 if(!strcmp(save_argv[FS_TYPE], "FSGROUP") ||
8178 !strcmp(save_argv[FS_TYPE], "MUL"))
8181 argv[0] = save_argv[FS_NAME];
8184 if (!(rc = mr_query("get_fsgroup_members", 1, argv,
8185 save_fsgroup_info, fsgroup_save_argv)))
8189 argv[0] = fsgroup_save_argv[0];
8191 if (!(rc = mr_query("get_filesys_by_label", 1, argv,
8192 save_query_info, save_argv)))
8194 strcpy(path, save_argv[FS_PACK]);
8201 strcpy(path, save_argv[FS_PACK]);
8209 if (!strnicmp(path, AFS, strlen(AFS)))
8211 AfsToWinAfs(path, winPath);
8212 strcpy(winProfile, winPath);
8213 strcat(winProfile, "\\.winprofile");
8220 if ((!strcasecmp(WinHomeDir, "[dfs]")) ||
8221 (!strcasecmp(WinProfileDir, "[dfs]")))
8223 sprintf(path, "\\\\%s\\dfs\\profiles\\%c\\%s", ldap_domain,
8224 user_name[0], user_name);
8226 if (!strcasecmp(WinProfileDir, "[dfs]"))
8228 strcpy(winProfile, path);
8229 strcat(winProfile, "\\.winprofile");
8232 if (!strcasecmp(WinHomeDir, "[dfs]"))
8233 strcpy(winPath, path);
8236 if (!strcasecmp(WinHomeDir, "[local]"))
8237 memset(winPath, '\0', sizeof(winPath));
8238 else if (!strcasecmp(WinHomeDir, "[afs]") ||
8239 !strcasecmp(WinHomeDir, "[dfs]"))
8241 strcpy(homeDrive, "H:");
8245 strcpy(winPath, WinHomeDir);
8246 if (!strncmp(WinHomeDir, "\\\\", 2))
8248 strcpy(homeDrive, "H:");
8252 // nothing needs to be done if WinProfileDir is [afs].
8253 if (!strcasecmp(WinProfileDir, "[local]"))
8254 memset(winProfile, '\0', sizeof(winProfile));
8255 else if (strcasecmp(WinProfileDir, "[afs]") &&
8256 strcasecmp(WinProfileDir, "[dfs]"))
8258 strcpy(winProfile, WinProfileDir);
8261 if (strlen(winProfile) != 0)
8263 if (winProfile[strlen(winProfile) - 1] == '\\')
8264 winProfile[strlen(winProfile) - 1] = '\0';
8267 if (strlen(winPath) != 0)
8269 if (winPath[strlen(winPath) - 1] == '\\')
8270 winPath[strlen(winPath) - 1] = '\0';
8273 if ((winProfile[1] == ':') && (strlen(winProfile) == 2))
8274 strcat(winProfile, "\\");
8276 if ((winPath[1] == ':') && (strlen(winPath) == 2))
8277 strcat(winPath, "\\");
8279 if (strlen(winPath) == 0)
8281 if (OpType == LDAP_MOD_REPLACE)
8284 DEL_ATTR("homeDirectory", LDAP_MOD_DELETE);
8286 //unset homeDirectory attribute for user.
8287 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8293 homedir_v[0] = strdup(winPath);
8294 ADD_ATTR("homeDirectory", homedir_v, OpType);
8297 if (strlen(winProfile) == 0)
8299 if (OpType == LDAP_MOD_REPLACE)
8302 DEL_ATTR("profilePath", LDAP_MOD_DELETE);
8304 //unset profilePate attribute for user.
8305 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8311 winProfile_v[0] = strdup(winProfile);
8312 ADD_ATTR("profilePath", winProfile_v, OpType);
8315 if (strlen(homeDrive) == 0)
8317 if (OpType == LDAP_MOD_REPLACE)
8320 DEL_ATTR("homeDrive", LDAP_MOD_DELETE);
8322 //unset homeDrive attribute for user
8323 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8329 drives_v[0] = strdup(homeDrive);
8330 ADD_ATTR("homeDrive", drives_v, OpType);
8336 int attribute_update(LDAP *ldap_handle, char *distinguished_name,
8337 char *attribute_value, char *attribute, char *user_name)
8339 char *mod_v[] = {NULL, NULL};
8340 LDAPMod *DelMods[20];
8346 if (strlen(attribute_value) == 0)
8349 DEL_ATTR(attribute, LDAP_MOD_DELETE);
8351 rc = ldap_modify_s(ldap_handle, distinguished_name, DelMods);
8357 mod_v[0] = attribute_value;
8358 ADD_ATTR(attribute, mod_v, LDAP_MOD_REPLACE);
8361 if ((rc = ldap_modify_s(ldap_handle, distinguished_name,
8362 mods)) != LDAP_SUCCESS)
8366 mod_v[0] = attribute_value;
8367 ADD_ATTR(attribute, mod_v, LDAP_MOD_ADD);
8370 if ((rc = ldap_modify_s(ldap_handle, distinguished_name,
8371 mods)) != LDAP_SUCCESS)
8373 com_err(whoami, 0, "Unable to change the %s attribute for %s "
8374 "in the directory : %s",
8375 attribute, user_name, ldap_err2string(rc));
8385 void StringTrim(char *StringToTrim)
8390 save = strdup(StringToTrim);
8397 /* skip to end of string */
8402 strcpy(StringToTrim, save);
8406 for (t = s; *t; t++)
8422 strcpy(StringToTrim, s);
8426 int ReadConfigFile(char *DomainName)
8437 sprintf(temp, "%s%s.cfg", CFG_PATH, DomainName);
8439 if ((fptr = fopen(temp, "r")) != NULL)
8441 while (fgets(temp, sizeof(temp), fptr) != 0)
8443 for (i = 0; i < (int)strlen(temp); i++)
8444 temp[i] = toupper(temp[i]);
8446 if (temp[strlen(temp) - 1] == '\n')
8447 temp[strlen(temp) - 1] = '\0';
8451 if (strlen(temp) == 0)
8454 if (!strncmp(temp, DOMAIN, strlen(DOMAIN)))
8456 if (strlen(temp) > (strlen(DOMAIN)))
8458 strcpy(ldap_domain, &temp[strlen(DOMAIN)]);
8459 StringTrim(ldap_domain);
8462 else if (!strncmp(temp, REALM, strlen(REALM)))
8464 if (strlen(temp) > (strlen(REALM)))
8466 strcpy(ldap_realm, &temp[strlen(REALM)]);
8467 StringTrim(ldap_realm);
8470 else if (!strncmp(temp, PORT, strlen(PORT)))
8472 if (strlen(temp) > (strlen(PORT)))
8474 strcpy(ldap_port, &temp[strlen(PORT)]);
8475 StringTrim(ldap_port);
8478 else if (!strncmp(temp, PRINCIPALNAME, strlen(PRINCIPALNAME)))
8480 if (strlen(temp) > (strlen(PRINCIPALNAME)))
8482 strcpy(PrincipalName, &temp[strlen(PRINCIPALNAME)]);
8483 StringTrim(PrincipalName);
8486 else if (!strncmp(temp, SERVER, strlen(SERVER)))
8488 if (strlen(temp) > (strlen(SERVER)))
8490 ServerList[Count] = calloc(1, 256);
8491 strcpy(ServerList[Count], &temp[strlen(SERVER)]);
8492 StringTrim(ServerList[Count]);
8496 else if (!strncmp(temp, MSSFU, strlen(MSSFU)))
8498 if (strlen(temp) > (strlen(MSSFU)))
8500 strcpy(temp1, &temp[strlen(MSSFU)]);
8502 if (!strcmp(temp1, SFUTYPE))
8506 else if (!strncmp(temp, GROUP_SUFFIX, strlen(GROUP_SUFFIX)))
8508 if (strlen(temp) > (strlen(GROUP_SUFFIX)))
8510 strcpy(temp1, &temp[strlen(GROUP_SUFFIX)]);
8512 if (!strcasecmp(temp1, "NO"))
8515 memset(group_suffix, '\0', sizeof(group_suffix));
8519 else if (!strncmp(temp, GROUP_TYPE, strlen(GROUP_TYPE)))
8521 if (strlen(temp) > (strlen(GROUP_TYPE)))
8523 strcpy(temp1, &temp[strlen(GROUP_TYPE)]);
8525 if (!strcasecmp(temp1, "UNIVERSAL"))
8526 UseGroupUniversal = 1;
8529 else if (!strncmp(temp, SET_GROUP_ACE, strlen(SET_GROUP_ACE)))
8531 if (strlen(temp) > (strlen(SET_GROUP_ACE)))
8533 strcpy(temp1, &temp[strlen(SET_GROUP_ACE)]);
8535 if (!strcasecmp(temp1, "NO"))
8539 else if (!strncmp(temp, SET_PASSWORD, strlen(SET_PASSWORD)))
8541 if (strlen(temp) > (strlen(SET_PASSWORD)))
8543 strcpy(temp1, &temp[strlen(SET_PASSWORD)]);
8545 if (!strcasecmp(temp1, "NO"))
8549 else if (!strncmp(temp, EXCHANGE, strlen(EXCHANGE)))
8551 if (strlen(temp) > (strlen(EXCHANGE)))
8553 strcpy(temp1, &temp[strlen(EXCHANGE)]);
8555 if (!strcasecmp(temp1, "YES"))
8559 else if (!strncmp(temp, PROCESS_MACHINE_CONTAINER,
8560 strlen(PROCESS_MACHINE_CONTAINER)))
8562 if (strlen(temp) > (strlen(PROCESS_MACHINE_CONTAINER)))
8564 strcpy(temp1, &temp[strlen(PROCESS_MACHINE_CONTAINER)]);
8566 if (!strcasecmp(temp1, "NO"))
8567 ProcessMachineContainer = 0;
8570 else if (!strncmp(temp, ACTIVE_DIRECTORY,
8571 strlen(ACTIVE_DIRECTORY)))
8573 if (strlen(temp) > (strlen(ACTIVE_DIRECTORY)))
8575 strcpy(temp1, &temp[strlen(ACTIVE_DIRECTORY)]);
8577 if (!strcasecmp(temp1, "NO"))
8578 ActiveDirectory = 0;
8581 else if (!strncmp(temp, GROUP_POPULATE_MEMBERS,
8582 strlen(GROUP_POPULATE_MEMBERS)))
8584 if (strlen(temp) > (strlen(GROUP_POPULATE_MEMBERS)))
8586 strcpy(temp1, &temp[strlen(GROUP_POPULATE_MEMBERS)]);
8588 if (!strcasecmp(temp1, "DELETE"))
8590 GroupPopulateDelete = 1;
8596 if (strlen(ldap_domain) != 0)
8598 memset(ldap_domain, '\0', sizeof(ldap_domain));
8602 if (strlen(temp) != 0)
8603 strcpy(ldap_domain, temp);
8609 if (strlen(ldap_domain) == 0)
8611 strcpy(ldap_domain, DomainName);
8617 for (i = 0; i < Count; i++)
8619 if (ServerList[i] != 0)
8621 for (k = 0; k < (int)strlen(ServerList[i]); k++)
8622 ServerList[i][k] = toupper(ServerList[i][k]);
8629 int ReadDomainList()
8636 unsigned char c[11];
8637 unsigned char stuff[256];
8642 sprintf(temp, "%s%s", CFG_PATH, WINADCFG);
8644 if ((fptr = fopen(temp, "r")) != NULL)
8646 while (fgets(temp, sizeof(temp), fptr) != 0)
8648 for (i = 0; i < (int)strlen(temp); i++)
8649 temp[i] = toupper(temp[i]);
8651 if (temp[strlen(temp) - 1] == '\n')
8652 temp[strlen(temp) - 1] = '\0';
8656 if (strlen(temp) == 0)
8659 if (!strncmp(temp, DOMAIN, strlen(DOMAIN)))
8661 if (strlen(temp) > (strlen(DOMAIN)))
8663 strcpy(temp1, &temp[strlen(DOMAIN)]);
8665 strcpy(temp, temp1);
8669 strcpy(DomainNames[Count], temp);
8670 StringTrim(DomainNames[Count]);
8679 critical_alert("incremental", "%s", "ldap.incr cannot run due to a "
8680 "configuration error in ldap.cfg");
8687 int email_isvalid(const char *address) {
8689 const char *c, *domain;
8690 static char *rfc822_specials = "()<>@,;:\\\"[]";
8692 if(address[strlen(address) - 1] == '.')
8695 /* first we validate the name portion (name@domain) */
8696 for (c = address; *c; c++) {
8697 if (*c == '\"' && (c == address || *(c - 1) == '.' || *(c - 1) ==
8702 if (*c == '\\' && (*++c == ' '))
8704 if (*c <= ' ' || *c >= 127)
8719 if (*c <= ' ' || *c >= 127)
8721 if (strchr(rfc822_specials, *c))
8725 if (c == address || *(c - 1) == '.')
8728 /* next we validate the domain portion (name@domain) */
8729 if (!*(domain = ++c)) return 0;
8732 if (c == domain || *(c - 1) == '.')
8736 if (*c <= ' ' || *c >= 127)
8738 if (strchr(rfc822_specials, *c))
8742 return (count >= 1);
8745 int find_homeMDB(LDAP *ldap_handle, char *dn_path, char **homeMDB,
8746 char **homeServerName)
8748 LK_ENTRY *group_base;
8749 LK_ENTRY *sub_group_base;
8753 int sub_group_count;
8755 char sub_filter[1024];
8756 char search_path[1024];
8758 char *attr_array[3];
8760 int homeMDB_count = -1;
8764 int rangeStep = 1500;
8766 int rangeHigh = rangeLow + (rangeStep - 1);
8769 /* Grumble..... microsoft not making it searchable from the root *grr* */
8771 memset(filter, '\0', sizeof(filter));
8772 memset(search_path, '\0', sizeof(search_path));
8774 sprintf(filter, "(objectClass=msExchMDB)");
8775 sprintf(search_path, "CN=Configuration,%s", dn_path);
8776 attr_array[0] = "distinguishedName";
8777 attr_array[1] = NULL;
8782 if ((rc = linklist_build(ldap_handle, search_path, filter, attr_array,
8783 &group_base, &group_count,
8784 LDAP_SCOPE_SUBTREE)) != 0)
8786 com_err(whoami, 0, "Unable to find msExchMDB %s",
8787 ldap_err2string(rc));
8796 if (((s = strstr(gPtr->dn, "Public")) != (char *) NULL) ||
8797 ((s = strstr(gPtr->dn, "Recover")) != (char *) NULL) ||
8798 ((s = strstr(gPtr->dn, "Reserve")) != (char *) NULL))
8805 * Due to limits in active directory we need to use the LDAP
8806 * range semantics to query and return all the values in
8807 * large lists, we will stop increasing the range when
8808 * the result count is 0.
8816 memset(sub_filter, '\0', sizeof(sub_filter));
8817 memset(range, '\0', sizeof(range));
8818 sprintf(sub_filter, "(objectClass=msExchMDB)");
8821 sprintf(range, "homeMDBBL;Range=%d-*", rangeLow);
8823 sprintf(range, "homeMDBBL;Range=%d-%d", rangeLow, rangeHigh);
8825 attr_array[0] = range;
8826 attr_array[1] = NULL;
8828 sub_group_base = NULL;
8829 sub_group_count = 0;
8831 if ((rc = linklist_build(ldap_handle, gPtr->dn, sub_filter,
8832 attr_array, &sub_group_base,
8834 LDAP_SCOPE_SUBTREE)) != 0)
8836 com_err(whoami, 0, "Unable to find homeMDBBL %s",
8837 ldap_err2string(rc));
8841 if(!sub_group_count)
8847 rangeHigh = rangeLow + (rangeStep - 1);
8854 mdbbl_count += sub_group_count;
8855 rangeLow = rangeHigh + 1;
8856 rangeHigh = rangeLow + (rangeStep - 1);
8859 /* First time through, need to initialize or update the least used */
8861 com_err(whoami, 0, "Mail store %s, count %d", gPtr->dn,
8864 if(mdbbl_count < homeMDB_count || homeMDB_count == -1)
8866 homeMDB_count = mdbbl_count;
8867 *homeMDB = strdup(gPtr->dn);
8871 linklist_free(sub_group_base);
8875 linklist_free(group_base);
8878 * Ok found the server least allocated need to now query to get its
8879 * msExchHomeServerName so we can set it as a user attribute
8882 attr_array[0] = "legacyExchangeDN";
8883 attr_array[1] = NULL;
8888 if ((rc = linklist_build(ldap_handle, *homeMDB, filter,
8889 attr_array, &group_base,
8891 LDAP_SCOPE_SUBTREE)) != 0)
8893 com_err(whoami, 0, "Unable to find msExchHomeServerName %s",
8894 ldap_err2string(rc));
8900 *homeServerName = strdup(group_base->value);
8901 if((s = strrchr(*homeServerName, '/')) != (char *) NULL)
8907 linklist_free(group_base);
8912 char *lowercase(char *s)
8916 for (p = s; *p; p++)
8924 char *uppercase(char *s)
8928 for (p = s; *p; p++)
8936 char *escape_string(char *s)
8944 memset(string, '\0', sizeof(string));
8948 /* Escape any special characters */
8950 for(; *q != '\0'; q++) {
8973 return strdup(string);
8976 int save_query_info(int argc, char **argv, void *hint)
8979 char **nargv = hint;
8981 for(i = 0; i < argc; i++)
8982 nargv[i] = strdup(argv[i]);
8987 int save_fsgroup_info(int argc, char **argv, void *hint)
8990 char **nargv = hint;
8994 for(i = 0; i < argc; i++)
8995 nargv[i] = strdup(argv[i]);