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))
6038 com_err(whoami, 0, "Unable to populate list %s : %s",
6039 group_name, error_message(rc));
6043 members = (char **)malloc(sizeof(char *) * 2);
6045 if (member_base != NULL)
6051 if (!strcasecmp(ptr->type, "LIST"))
6057 if (!strcasecmp(ptr->type, "MACHINE") && !ProcessMachineContainer)
6063 if(!strcasecmp(ptr->type, "USER"))
6065 if(!strcasecmp(ptr->member, PRODUCTION_PRINCIPAL) ||
6066 !strcasecmp(ptr->member, TEST_PRINCIPAL))
6072 if ((rc = check_user(ldap_handle, dn_path, ptr->member,
6073 "")) == AD_NO_USER_FOUND)
6075 com_err(whoami, 0, "creating user %s", ptr->member);
6077 av[0] = ptr->member;
6078 call_args[0] = (char *)ldap_handle;
6079 call_args[1] = dn_path;
6081 call_args[3] = NULL;
6084 if (rc = mr_query("get_user_account_by_login", 1, av,
6085 save_query_info, save_argv))
6087 com_err(whoami, 0, "Unable to create user %s "
6088 "while populating group %s.", ptr->member,
6094 if (rc = user_create(U_END, save_argv, call_args))
6096 com_err(whoami, 0, "Unable to create user %s "
6097 "while populating group %s.", ptr->member,
6105 com_err(whoami, 0, "Unable to create user %s "
6106 "while populating group %s", ptr->member,
6117 sprintf(member, "cn=%s,%s,%s", ptr->member, pUserOu,
6122 sprintf(member, "uid=%s,%s,%s", ptr->member, pUserOu,
6127 else if (!strcasecmp(ptr->type, "STRING"))
6129 if (contact_create(ldap_handle, dn_path, ptr->member,
6133 pUserOu = contact_ou;
6134 sprintf(member, "cn=%s,%s,%s", escape_string(ptr->member),
6137 else if (!strcasecmp(ptr->type, "KERBEROS"))
6139 if (contact_create(ldap_handle, dn_path, ptr->member,
6143 pUserOu = kerberos_ou;
6144 sprintf(member, "cn=%s,%s,%s", escape_string(ptr->member),
6147 else if (!strcasecmp(ptr->type, "MACHINE"))
6149 memset(machine_ou, '\0', sizeof(machine_ou));
6150 memset(NewMachineName, '\0', sizeof(NewMachineName));
6152 if (!get_machine_ou(ldap_handle, dn_path, ptr->member,
6153 machine_ou, NewMachineName))
6155 pUserOu = machine_ou;
6156 sprintf(member, "cn=%s,%s,%s", NewMachineName, pUserOu,
6167 members = (char **)realloc(members, ((i + 2) * sizeof(char *)));
6168 members[i++] = strdup(member);
6173 linklist_free(member_base);
6179 sprintf(group_dn, "cn=%s,%s,%s", group_name, group_ou, dn_path);
6181 if(GroupPopulateDelete)
6184 ADD_ATTR("member", member_v, LDAP_MOD_REPLACE);
6187 if ((rc = ldap_modify_s(ldap_handle, group_dn,
6188 mods)) != LDAP_SUCCESS)
6191 "Unable to populate group membership for %s: %s",
6192 group_dn, ldap_err2string(rc));
6195 for (i = 0; i < n; i++)
6200 ADD_ATTR("member", members, LDAP_MOD_REPLACE);
6203 if ((rc = ldap_modify_s(ldap_handle, group_dn,
6204 mods)) != LDAP_SUCCESS)
6207 "Unable to populate group membership for %s: %s",
6208 group_dn, ldap_err2string(rc));
6211 for (i = 0; i < n; i++)
6219 int process_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
6220 char *group_name, char *group_ou, char *group_membership,
6221 int group_security_flag, int type, char *maillist)
6223 char before_desc[512];
6224 char before_name[256];
6225 char before_group_ou[256];
6226 char before_group_membership[2];
6227 char distinguishedName[256];
6228 char ad_distinguishedName[256];
6230 char *attr_array[3];
6231 int before_security_flag;
6234 LK_ENTRY *group_base;
6237 char ou_security[512];
6238 char ou_distribution[512];
6239 char ou_neither[512];
6242 memset(ad_distinguishedName, '\0', sizeof(ad_distinguishedName));
6243 sprintf(distinguishedName, "CN=%s,%s,%s", group_name, group_ou, dn_path);
6245 memset(filter, '\0', sizeof(filter));
6249 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
6251 "samAccountName", &group_base,
6252 &group_count, filter))
6255 if (type == CHECK_GROUPS)
6257 if (group_count == 1)
6259 strcpy(group_dn, group_base->dn);
6261 if (!strcasecmp(group_dn, distinguishedName))
6263 linklist_free(group_base);
6268 linklist_free(group_base);
6270 if (group_count == 0)
6271 return(AD_NO_GROUPS_FOUND);
6273 if (group_count == 1)
6274 return(AD_WRONG_GROUP_DN_FOUND);
6276 return(AD_MULTIPLE_GROUPS_FOUND);
6279 if (group_count == 0)
6281 return(AD_NO_GROUPS_FOUND);
6284 if (group_count > 1)
6288 strcpy(group_dn, ptr->dn);
6292 if (!strcasecmp(group_dn, ptr->value))
6300 com_err(whoami, 0, "%d groups with moira id = %s", group_count,
6306 com_err(whoami, 0, "%s with moira id = %s", ptr->value, MoiraId);
6310 linklist_free(group_base);
6311 return(AD_MULTIPLE_GROUPS_FOUND);
6318 strcpy(group_dn, ptr->dn);
6320 if (strcasecmp(group_dn, ptr->value))
6321 rc = ldap_delete_s(ldap_handle, ptr->value);
6326 linklist_free(group_base);
6327 memset(filter, '\0', sizeof(filter));
6331 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
6333 "samAccountName", &group_base,
6334 &group_count, filter))
6337 if (group_count == 0)
6338 return(AD_NO_GROUPS_FOUND);
6340 if (group_count > 1)
6341 return(AD_MULTIPLE_GROUPS_FOUND);
6344 strcpy(ad_distinguishedName, group_base->dn);
6345 linklist_free(group_base);
6349 attr_array[0] = "sAMAccountName";
6350 attr_array[1] = NULL;
6352 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6353 &group_base, &group_count,
6354 LDAP_SCOPE_SUBTREE)) != 0)
6356 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6357 MoiraId, ldap_err2string(rc));
6361 sprintf(filter, "(sAMAccountName=%s)", group_base->value);
6363 if (!strcasecmp(ad_distinguishedName, distinguishedName))
6365 linklist_free(group_base);
6371 linklist_free(group_base);
6374 memset(ou_both, '\0', sizeof(ou_both));
6375 memset(ou_security, '\0', sizeof(ou_security));
6376 memset(ou_distribution, '\0', sizeof(ou_distribution));
6377 memset(ou_neither, '\0', sizeof(ou_neither));
6378 memset(before_name, '\0', sizeof(before_name));
6379 memset(before_desc, '\0', sizeof(before_desc));
6380 memset(before_group_membership, '\0', sizeof(before_group_membership));
6382 attr_array[0] = "name";
6383 attr_array[1] = NULL;
6385 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6386 &group_base, &group_count,
6387 LDAP_SCOPE_SUBTREE)) != 0)
6389 com_err(whoami, 0, "Unable to get list name with MoiraId = %s: %s",
6390 MoiraId, ldap_err2string(rc));
6394 strcpy(before_name, group_base->value);
6395 linklist_free(group_base);
6399 attr_array[0] = "description";
6400 attr_array[1] = NULL;
6402 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6403 &group_base, &group_count,
6404 LDAP_SCOPE_SUBTREE)) != 0)
6407 "Unable to get list description with MoiraId = %s: %s",
6408 MoiraId, ldap_err2string(rc));
6412 if (group_count != 0)
6414 strcpy(before_desc, group_base->value);
6415 linklist_free(group_base);
6420 change_to_lower_case(ad_distinguishedName);
6421 strcpy(ou_both, group_ou_both);
6422 change_to_lower_case(ou_both);
6423 strcpy(ou_security, group_ou_security);
6424 change_to_lower_case(ou_security);
6425 strcpy(ou_distribution, group_ou_distribution);
6426 change_to_lower_case(ou_distribution);
6427 strcpy(ou_neither, group_ou_neither);
6428 change_to_lower_case(ou_neither);
6430 if (strstr(ad_distinguishedName, ou_both))
6432 strcpy(before_group_ou, group_ou_both);
6433 before_group_membership[0] = 'B';
6434 before_security_flag = 1;
6436 else if (strstr(ad_distinguishedName, ou_security))
6438 strcpy(before_group_ou, group_ou_security);
6439 before_group_membership[0] = 'S';
6440 before_security_flag = 1;
6442 else if (strstr(ad_distinguishedName, ou_distribution))
6444 strcpy(before_group_ou, group_ou_distribution);
6445 before_group_membership[0] = 'D';
6446 before_security_flag = 0;
6448 else if (strstr(ad_distinguishedName, ou_neither))
6450 strcpy(before_group_ou, group_ou_neither);
6451 before_group_membership[0] = 'N';
6452 before_security_flag = 0;
6455 return(AD_NO_OU_FOUND);
6457 rc = group_rename(ldap_handle, dn_path, before_name,
6458 before_group_membership,
6459 before_group_ou, before_security_flag, before_desc,
6460 group_name, group_membership, group_ou,
6461 group_security_flag,
6462 before_desc, MoiraId, filter, maillist);
6467 void change_to_lower_case(char *ptr)
6471 for (i = 0; i < (int)strlen(ptr); i++)
6473 ptr[i] = tolower(ptr[i]);
6477 int ad_get_group(LDAP *ldap_handle, char *dn_path,
6478 char *group_name, char *group_membership,
6479 char *MoiraId, char *attribute,
6480 LK_ENTRY **linklist_base, int *linklist_count,
6485 char *attr_array[3];
6489 (*linklist_base) = NULL;
6490 (*linklist_count) = 0;
6492 if (strlen(rFilter) != 0)
6494 strcpy(filter, rFilter);
6495 attr_array[0] = attribute;
6496 attr_array[1] = NULL;
6498 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6499 linklist_base, linklist_count,
6500 LDAP_SCOPE_SUBTREE)) != 0)
6502 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6503 MoiraId, ldap_err2string(rc));
6507 if ((*linklist_count) == 1)
6509 strcpy(rFilter, filter);
6514 linklist_free((*linklist_base));
6515 (*linklist_base) = NULL;
6516 (*linklist_count) = 0;
6518 if (strlen(MoiraId) != 0)
6520 sprintf(filter, "(&(objectClass=group)(mitMoiraId=%s))", MoiraId);
6522 attr_array[0] = attribute;
6523 attr_array[1] = NULL;
6525 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6526 linklist_base, linklist_count,
6527 LDAP_SCOPE_SUBTREE)) != 0)
6529 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6530 MoiraId, ldap_err2string(rc));
6535 if ((*linklist_count) > 1)
6537 com_err(whoami, 0, "multiple groups with mitMoiraId = %s", MoiraId);
6538 pPtr = (*linklist_base);
6542 com_err(whoami, 0, "groups %s has mitMoiraId = %s", pPtr->value,
6547 linklist_free((*linklist_base));
6548 (*linklist_base) = NULL;
6549 (*linklist_count) = 0;
6552 if ((*linklist_count) == 1)
6555 pPtr = (*linklist_base);
6556 dn = strdup(pPtr->dn);
6559 if (!memcmp(dn, group_name, strlen(group_name)))
6561 strcpy(rFilter, filter);
6566 linklist_free((*linklist_base));
6567 (*linklist_base) = NULL;
6568 (*linklist_count) = 0;
6569 sprintf(filter, "(sAMAccountName=%s%s)", group_name, group_suffix);
6571 attr_array[0] = attribute;
6572 attr_array[1] = NULL;
6574 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6575 linklist_base, linklist_count,
6576 LDAP_SCOPE_SUBTREE)) != 0)
6578 com_err(whoami, 0, "Unable to get list info with MoiraId = %s: %s",
6579 MoiraId, ldap_err2string(rc));
6583 if ((*linklist_count) == 1)
6585 strcpy(rFilter, filter);
6592 int check_user(LDAP *ldap_handle, char *dn_path, char *UserName, char *MoiraId)
6595 char *attr_array[3];
6596 char SamAccountName[64];
6599 LK_ENTRY *group_base;
6605 if (strlen(MoiraId) != 0)
6607 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
6609 attr_array[0] = "sAMAccountName";
6610 attr_array[1] = NULL;
6611 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6612 &group_base, &group_count,
6613 LDAP_SCOPE_SUBTREE)) != 0)
6615 com_err(whoami, 0, "Unable to process user %s : %s",
6616 UserName, ldap_err2string(rc));
6620 if (group_count > 1)
6622 com_err(whoami, 0, "multiple users exist with MoiraId = %s",
6628 com_err(whoami, 0, "user %s exist with MoiraId = %s",
6629 gPtr->value, MoiraId);
6635 if (group_count != 1)
6637 linklist_free(group_base);
6640 sprintf(filter, "(sAMAccountName=%s)", UserName);
6641 attr_array[0] = "sAMAccountName";
6642 attr_array[1] = NULL;
6644 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6645 &group_base, &group_count,
6646 LDAP_SCOPE_SUBTREE)) != 0)
6648 com_err(whoami, 0, "Unable to process user %s : %s",
6649 UserName, ldap_err2string(rc));
6654 if (group_count != 1)
6656 linklist_free(group_base);
6657 return(AD_NO_USER_FOUND);
6660 strcpy(SamAccountName, group_base->value);
6661 linklist_free(group_base);
6665 if (strcmp(SamAccountName, UserName))
6668 "User object %s with MoiraId %s has mismatched usernames "
6669 "(LDAP username %s, Moira username %s)", SamAccountName,
6670 MoiraId, SamAccountName, UserName);
6676 void container_get_dn(char *src, char *dest)
6683 memset(array, '\0', 20 * sizeof(array[0]));
6685 if (strlen(src) == 0)
6707 strcpy(dest, "OU=");
6711 strcat(dest, array[n-1]);
6715 strcat(dest, ",OU=");
6722 void container_get_name(char *src, char *dest)
6727 if (strlen(src) == 0)
6747 void container_check(LDAP *ldap_handle, char *dn_path, char *name)
6754 strcpy(cName, name);
6756 for (i = 0; i < (int)strlen(cName); i++)
6758 if (cName[i] == '/')
6761 av[CONTAINER_NAME] = cName;
6762 av[CONTAINER_DESC] = "";
6763 av[CONTAINER_LOCATION] = "";
6764 av[CONTAINER_CONTACT] = "";
6765 av[CONTAINER_TYPE] = "";
6766 av[CONTAINER_ID] = "";
6767 av[CONTAINER_ROWID] = "";
6768 rc = container_create(ldap_handle, dn_path, 7, av);
6770 if (rc == LDAP_SUCCESS)
6772 com_err(whoami, 0, "container %s created without a mitMoiraId",
6781 int container_rename(LDAP *ldap_handle, char *dn_path, int beforec,
6782 char **before, int afterc, char **after)
6787 char new_dn_path[256];
6789 char distinguishedName[256];
6794 memset(cName, '\0', sizeof(cName));
6795 container_get_name(after[CONTAINER_NAME], cName);
6797 if (!check_container_name(cName))
6799 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6801 return(AD_INVALID_NAME);
6804 memset(distinguishedName, '\0', sizeof(distinguishedName));
6806 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
6807 distinguishedName, beforec, before))
6810 if (strlen(distinguishedName) == 0)
6812 rc = container_create(ldap_handle, dn_path, afterc, after);
6816 strcpy(temp, after[CONTAINER_NAME]);
6819 for (i = 0; i < (int)strlen(temp); i++)
6829 container_get_dn(temp, dName);
6831 if (strlen(temp) != 0)
6832 sprintf(new_dn_path, "%s,%s", dName, dn_path);
6834 sprintf(new_dn_path, "%s", dn_path);
6836 sprintf(new_cn, "OU=%s", cName);
6838 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
6840 if ((rc = ldap_rename_s(ldap_handle, distinguishedName, new_cn, new_dn_path,
6841 TRUE, NULL, NULL)) != LDAP_SUCCESS)
6843 com_err(whoami, 0, "Unable to rename container from %s to %s : %s",
6844 before[CONTAINER_NAME], after[CONTAINER_NAME],
6845 ldap_err2string(rc));
6849 memset(dName, '\0', sizeof(dName));
6850 container_get_dn(after[CONTAINER_NAME], dName);
6851 rc = container_adupdate(ldap_handle, dn_path, dName, "", afterc, after);
6856 int container_delete(LDAP *ldap_handle, char *dn_path, int count, char **av)
6858 char distinguishedName[256];
6861 memset(distinguishedName, '\0', sizeof(distinguishedName));
6863 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
6864 distinguishedName, count, av))
6867 if (strlen(distinguishedName) == 0)
6870 if ((rc = ldap_delete_s(ldap_handle, distinguishedName)) != LDAP_SUCCESS)
6872 if (rc == LDAP_NOT_ALLOWED_ON_NONLEAF)
6873 container_move_objects(ldap_handle, dn_path, distinguishedName);
6875 com_err(whoami, 0, "Unable to delete container %s from directory : %s",
6876 av[CONTAINER_NAME], ldap_err2string(rc));
6882 int container_create(LDAP *ldap_handle, char *dn_path, int count, char **av)
6884 char *attr_array[3];
6885 LK_ENTRY *group_base;
6888 char *objectClass_v[] = {"top",
6889 "organizationalUnit",
6892 char *ou_v[] = {NULL, NULL};
6893 char *name_v[] = {NULL, NULL};
6894 char *moiraId_v[] = {NULL, NULL};
6895 char *desc_v[] = {NULL, NULL};
6896 char *managedBy_v[] = {NULL, NULL};
6899 char managedByDN[256];
6906 memset(filter, '\0', sizeof(filter));
6907 memset(dName, '\0', sizeof(dName));
6908 memset(cName, '\0', sizeof(cName));
6909 memset(managedByDN, '\0', sizeof(managedByDN));
6910 container_get_dn(av[CONTAINER_NAME], dName);
6911 container_get_name(av[CONTAINER_NAME], cName);
6913 if ((strlen(cName) == 0) || (strlen(dName) == 0))
6915 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6917 return(AD_INVALID_NAME);
6920 if (!check_container_name(cName))
6922 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
6924 return(AD_INVALID_NAME);
6928 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
6930 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
6932 ADD_ATTR("ou", ou_v, LDAP_MOD_ADD);
6934 if (strlen(av[CONTAINER_ROWID]) != 0)
6936 moiraId_v[0] = av[CONTAINER_ROWID];
6937 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_ADD);
6940 if (strlen(av[CONTAINER_DESC]) != 0)
6942 desc_v[0] = av[CONTAINER_DESC];
6943 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
6946 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
6948 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
6950 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID],
6953 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID],
6954 kerberos_ou, dn_path);
6955 managedBy_v[0] = managedByDN;
6956 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
6961 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
6963 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)"
6964 "(objectClass=user)))", av[CONTAINER_ID]);
6967 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
6969 sprintf(filter, "(&(objectClass=group)(cn=%s))",
6973 if (strlen(filter) != 0)
6975 attr_array[0] = "distinguishedName";
6976 attr_array[1] = NULL;
6979 if ((rc = linklist_build(ldap_handle, dn_path, filter,
6981 &group_base, &group_count,
6982 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
6984 if (group_count == 1)
6986 strcpy(managedByDN, group_base->value);
6987 managedBy_v[0] = managedByDN;
6988 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
6990 linklist_free(group_base);
7000 sprintf(temp, "%s,%s", dName, dn_path);
7001 rc = ldap_add_ext_s(ldap_handle, temp, mods, NULL, NULL);
7003 for (i = 0; i < n; i++)
7006 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
7008 com_err(whoami, 0, "Unable to create container %s : %s",
7009 cName, ldap_err2string(rc));
7013 if (rc == LDAP_ALREADY_EXISTS)
7015 if (strlen(av[CONTAINER_ROWID]) != 0)
7016 rc = container_adupdate(ldap_handle, dn_path, dName, "", count, av);
7022 int container_update(LDAP *ldap_handle, char *dn_path, int beforec,
7023 char **before, int afterc, char **after)
7025 char distinguishedName[256];
7028 memset(distinguishedName, '\0', sizeof(distinguishedName));
7030 if (rc = container_get_distinguishedName(ldap_handle, dn_path,
7031 distinguishedName, afterc, after))
7034 if (strlen(distinguishedName) == 0)
7036 rc = container_create(ldap_handle, dn_path, afterc, after);
7040 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
7041 rc = container_adupdate(ldap_handle, dn_path, "", distinguishedName, afterc,
7047 int container_get_distinguishedName(LDAP *ldap_handle, char *dn_path,
7048 char *distinguishedName, int count,
7051 char *attr_array[3];
7052 LK_ENTRY *group_base;
7059 memset(filter, '\0', sizeof(filter));
7060 memset(dName, '\0', sizeof(dName));
7061 memset(cName, '\0', sizeof(cName));
7062 container_get_dn(av[CONTAINER_NAME], dName);
7063 container_get_name(av[CONTAINER_NAME], cName);
7065 if (strlen(dName) == 0)
7067 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
7068 av[CONTAINER_NAME]);
7069 return(AD_INVALID_NAME);
7072 if (!check_container_name(cName))
7074 com_err(whoami, 0, "Unable to process invalid LDAP container name %s",
7076 return(AD_INVALID_NAME);
7079 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))",
7080 av[CONTAINER_ROWID]);
7081 attr_array[0] = "distinguishedName";
7082 attr_array[1] = NULL;
7086 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7087 &group_base, &group_count,
7088 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7090 if (group_count == 1)
7092 strcpy(distinguishedName, group_base->value);
7095 linklist_free(group_base);
7100 if (strlen(distinguishedName) == 0)
7102 sprintf(filter, "(&(objectClass=organizationalUnit)"
7103 "(distinguishedName=%s,%s))", dName, dn_path);
7104 attr_array[0] = "distinguishedName";
7105 attr_array[1] = NULL;
7109 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7110 &group_base, &group_count,
7111 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7113 if (group_count == 1)
7115 strcpy(distinguishedName, group_base->value);
7118 linklist_free(group_base);
7127 int container_adupdate(LDAP *ldap_handle, char *dn_path, char *dName,
7128 char *distinguishedName, int count, char **av)
7130 char *attr_array[5];
7131 LK_ENTRY *group_base;
7136 char *moiraId_v[] = {NULL, NULL};
7137 char *desc_v[] = {NULL, NULL};
7138 char *managedBy_v[] = {NULL, NULL};
7139 char managedByDN[256];
7148 strcpy(ad_path, distinguishedName);
7150 if (strlen(dName) != 0)
7151 sprintf(ad_path, "%s,%s", dName, dn_path);
7153 sprintf(filter, "(&(objectClass=organizationalUnit)(distinguishedName=%s))",
7156 if (strlen(av[CONTAINER_ID]) != 0)
7157 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))",
7158 av[CONTAINER_ROWID]);
7160 attr_array[0] = "mitMoiraId";
7161 attr_array[1] = "description";
7162 attr_array[2] = "managedBy";
7163 attr_array[3] = NULL;
7167 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7168 &group_base, &group_count,
7169 LDAP_SCOPE_SUBTREE)) != LDAP_SUCCESS)
7171 com_err(whoami, 0, "Unable to retreive container info for %s : %s",
7172 av[CONTAINER_NAME], ldap_err2string(rc));
7176 memset(managedByDN, '\0', sizeof(managedByDN));
7177 memset(moiraId, '\0', sizeof(moiraId));
7178 memset(desc, '\0', sizeof(desc));
7183 if (!strcasecmp(pPtr->attribute, "description"))
7184 strcpy(desc, pPtr->value);
7185 else if (!strcasecmp(pPtr->attribute, "managedBy"))
7186 strcpy(managedByDN, pPtr->value);
7187 else if (!strcasecmp(pPtr->attribute, "mitMoiraId"))
7188 strcpy(moiraId, pPtr->value);
7192 linklist_free(group_base);
7197 if (strlen(av[CONTAINER_ROWID]) != 0)
7199 moiraId_v[0] = av[CONTAINER_ROWID];
7200 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_REPLACE);
7203 if (strlen(av[CONTAINER_DESC]) != 0)
7205 attribute_update(ldap_handle, ad_path, av[CONTAINER_DESC], "description",
7210 if (strlen(desc) != 0)
7212 attribute_update(ldap_handle, ad_path, "", "description", dName);
7216 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
7218 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
7220 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID],
7223 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID],
7224 kerberos_ou, dn_path);
7225 managedBy_v[0] = managedByDN;
7226 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
7230 if (strlen(managedByDN) != 0)
7232 attribute_update(ldap_handle, ad_path, "", "managedBy",
7239 memset(filter, '\0', sizeof(filter));
7241 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
7243 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)"
7244 "(objectClass=user)))", av[CONTAINER_ID]);
7247 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
7249 sprintf(filter, "(&(objectClass=group)(cn=%s))",
7253 if (strlen(filter) != 0)
7255 attr_array[0] = "distinguishedName";
7256 attr_array[1] = NULL;
7259 if ((rc = linklist_build(ldap_handle, dn_path, filter,
7260 attr_array, &group_base, &group_count,
7261 LDAP_SCOPE_SUBTREE)) == LDAP_SUCCESS)
7263 if (group_count == 1)
7265 strcpy(managedByDN, group_base->value);
7266 managedBy_v[0] = managedByDN;
7267 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
7271 if (strlen(managedByDN) != 0)
7273 attribute_update(ldap_handle, ad_path, "",
7274 "managedBy", dName);
7278 linklist_free(group_base);
7285 if (strlen(managedByDN) != 0)
7287 attribute_update(ldap_handle, ad_path, "", "managedBy",
7297 return(LDAP_SUCCESS);
7299 rc = ldap_modify_s(ldap_handle, ad_path, mods);
7301 for (i = 0; i < n; i++)
7304 if (rc != LDAP_SUCCESS)
7306 com_err(whoami, 0, "Unable to modify container info for %s : %s",
7307 av[CONTAINER_NAME], ldap_err2string(rc));
7314 int container_move_objects(LDAP *ldap_handle, char *dn_path, char *dName)
7316 char *attr_array[3];
7317 LK_ENTRY *group_base;
7324 int NumberOfEntries = 10;
7328 rc = ldap_set_option(ldap_handle, LDAP_OPT_SIZELIMIT, &NumberOfEntries);
7330 for (i = 0; i < 3; i++)
7332 memset(filter, '\0', sizeof(filter));
7336 strcpy(filter, "(!(|(objectClass=computer)"
7337 "(objectClass=organizationalUnit)))");
7338 attr_array[0] = "cn";
7339 attr_array[1] = NULL;
7343 strcpy(filter, "(objectClass=computer)");
7344 attr_array[0] = "cn";
7345 attr_array[1] = NULL;
7349 strcpy(filter, "(objectClass=organizationalUnit)");
7350 attr_array[0] = "ou";
7351 attr_array[1] = NULL;
7356 if ((rc = linklist_build(ldap_handle, dName, filter, attr_array,
7357 &group_base, &group_count,
7358 LDAP_SCOPE_SUBTREE)) != LDAP_SUCCESS)
7363 if (group_count == 0)
7370 if (!strcasecmp(pPtr->attribute, "cn"))
7372 sprintf(new_cn, "cn=%s", pPtr->value);
7374 sprintf(temp, "%s,%s", orphans_other_ou, dn_path);
7376 sprintf(temp, "%s,%s", orphans_machines_ou, dn_path);
7381 rc = ldap_rename_s(ldap_handle, pPtr->dn, new_cn, temp,
7383 if (rc == LDAP_ALREADY_EXISTS)
7385 sprintf(new_cn, "cn=%s_%d", pPtr->value, count);
7392 else if (!strcasecmp(pPtr->attribute, "ou"))
7394 rc = ldap_delete_s(ldap_handle, pPtr->dn);
7400 linklist_free(group_base);
7409 int get_machine_ou(LDAP *ldap_handle, char *dn_path, char *member,
7410 char *machine_ou, char *NewMachineName)
7412 LK_ENTRY *group_base;
7416 char *attr_array[3];
7423 strcpy(NewMachineName, member);
7424 rc = moira_connect();
7425 rc = GetMachineName(NewMachineName);
7428 if (strlen(NewMachineName) == 0)
7430 com_err(whoami, 0, "Unable to find alais for machine %s in Moira",
7436 pPtr = strchr(NewMachineName, '.');
7443 sprintf(filter, "(sAMAccountName=%s$)", NewMachineName);
7444 attr_array[0] = "cn";
7445 attr_array[1] = NULL;
7446 sprintf(temp, "%s", dn_path);
7448 if ((rc = linklist_build(ldap_handle, temp, filter, attr_array,
7449 &group_base, &group_count,
7450 LDAP_SCOPE_SUBTREE)) != 0)
7452 com_err(whoami, 0, "Unable to process machine %s : %s",
7453 member, ldap_err2string(rc));
7457 if (group_count != 1)
7462 strcpy(dn, group_base->dn);
7463 strcpy(cn, group_base->value);
7465 for (i = 0; i < (int)strlen(dn); i++)
7466 dn[i] = tolower(dn[i]);
7468 for (i = 0; i < (int)strlen(cn); i++)
7469 cn[i] = tolower(cn[i]);
7471 linklist_free(group_base);
7473 pPtr = strstr(dn, cn);
7477 com_err(whoami, 0, "Unable to process machine %s",
7482 pPtr += strlen(cn) + 1;
7483 strcpy(machine_ou, pPtr);
7485 pPtr = strstr(machine_ou, "dc=");
7489 com_err(whoami, 0, "Unable to process machine %s",
7500 int machine_move_to_ou(LDAP *ldap_handle, char * dn_path,
7501 char *MoiraMachineName, char *DestinationOu)
7505 char MachineName[128];
7507 char *attr_array[3];
7512 LK_ENTRY *group_base;
7517 strcpy(MachineName, MoiraMachineName);
7518 rc = GetMachineName(MachineName);
7520 if (strlen(MachineName) == 0)
7522 com_err(whoami, 0, "Unable to find alais for machine %s in Moira",
7527 cPtr = strchr(MachineName, '.');
7532 sprintf(filter, "(sAMAccountName=%s$)", MachineName);
7533 attr_array[0] = "sAMAccountName";
7534 attr_array[1] = NULL;
7536 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
7538 &group_count, LDAP_SCOPE_SUBTREE)) != 0)
7540 com_err(whoami, 0, "Unable to process machine %s : %s",
7541 MoiraMachineName, ldap_err2string(rc));
7545 if (group_count == 1)
7546 strcpy(OldDn, group_base->dn);
7548 linklist_free(group_base);
7551 if (group_count != 1)
7553 com_err(whoami, 0, "Unable to find machine %s in directory: %s",
7558 sprintf(NewOu, "%s,%s", DestinationOu, dn_path);
7559 cPtr = strchr(OldDn, ',');
7564 if (!strcasecmp(cPtr, NewOu))
7568 sprintf(NewCn, "CN=%s", MachineName);
7569 rc = ldap_rename_s(ldap_handle, OldDn, NewCn, NewOu, TRUE, NULL, NULL);
7574 int machine_check(LDAP *ldap_handle, char *dn_path, char *machine_name)
7580 memset(Name, '\0', sizeof(Name));
7581 strcpy(Name, machine_name);
7583 pPtr = strchr(Name, '.');
7589 return(!(rc = checkADname(ldap_handle, dn_path, Name)));
7592 int machine_get_moira_container(LDAP *ldap_handle, char *dn_path,
7593 char *machine_name, char *container_name)
7599 av[0] = machine_name;
7600 call_args[0] = (char *)container_name;
7601 rc = mr_query("get_machine_to_container_map", 1, av,
7602 machine_GetMoiraContainer, call_args);
7606 int machine_GetMoiraContainer(int ac, char **av, void *ptr)
7611 strcpy(call_args[0], av[1]);
7615 int Moira_container_group_create(char **after)
7621 memset(GroupName, '\0', sizeof(GroupName));
7622 rc = Moira_groupname_create(GroupName, after[CONTAINER_NAME],
7623 after[CONTAINER_ROWID]);
7627 argv[L_NAME] = GroupName;
7628 argv[L_ACTIVE] = "1";
7629 argv[L_PUBLIC] = "0";
7630 argv[L_HIDDEN] = "0";
7631 argv[L_MAILLIST] = "0";
7632 argv[L_GROUP] = "1";
7633 argv[L_GID] = UNIQUE_GID;
7634 argv[L_NFSGROUP] = "0";
7635 argv[L_MAILMAN] = "0";
7636 argv[L_MAILMAN_SERVER] = "[NONE]";
7637 argv[L_DESC] = "auto created container group";
7638 argv[L_ACE_TYPE] = "USER";
7639 argv[L_MEMACE_TYPE] = "USER";
7640 argv[L_ACE_NAME] = "sms";
7641 argv[L_MEMACE_NAME] = "sms";
7643 if (rc = mr_query("add_list", 15, argv, NULL, NULL))
7646 "Unable to create container group %s for container %s: %s",
7647 GroupName, after[CONTAINER_NAME], error_message(rc));
7650 Moira_setContainerGroup(after[CONTAINER_NAME], GroupName);
7651 Moira_addGroupToParent(after[CONTAINER_NAME], GroupName);
7656 int Moira_container_group_update(char **before, char **after)
7659 char BeforeGroupName[64];
7660 char AfterGroupName[64];
7663 if (!strcasecmp(after[CONTAINER_NAME], before[CONTAINER_NAME]))
7666 memset(BeforeGroupName, '\0', sizeof(BeforeGroupName));
7667 Moira_getGroupName(after[CONTAINER_NAME], BeforeGroupName, 0);
7668 if (strlen(BeforeGroupName) == 0)
7671 memset(AfterGroupName, '\0', sizeof(AfterGroupName));
7672 rc = Moira_groupname_create(AfterGroupName, after[CONTAINER_NAME],
7673 after[CONTAINER_ROWID]);
7677 if (strcasecmp(BeforeGroupName, AfterGroupName))
7679 argv[L_NAME] = BeforeGroupName;
7680 argv[L_NAME + 1] = AfterGroupName;
7681 argv[L_ACTIVE + 1] = "1";
7682 argv[L_PUBLIC + 1] = "0";
7683 argv[L_HIDDEN + 1] = "0";
7684 argv[L_MAILLIST + 1] = "0";
7685 argv[L_GROUP + 1] = "1";
7686 argv[L_GID + 1] = UNIQUE_GID;
7687 argv[L_NFSGROUP + 1] = "0";
7688 argv[L_MAILMAN + 1] = "0";
7689 argv[L_MAILMAN_SERVER + 1] = "[NONE]";
7690 argv[L_DESC + 1] = "auto created container group";
7691 argv[L_ACE_TYPE + 1] = "USER";
7692 argv[L_MEMACE_TYPE + 1] = "USER";
7693 argv[L_ACE_NAME + 1] = "sms";
7694 argv[L_MEMACE_NAME + 1] = "sms";
7696 if (rc = mr_query("update_list", 16, argv, NULL, NULL))
7699 "Unable to rename container group from %s to %s: %s",
7700 BeforeGroupName, AfterGroupName, error_message(rc));
7707 int Moira_container_group_delete(char **before)
7712 char ParentGroupName[64];
7714 memset(ParentGroupName, '\0', sizeof(ParentGroupName));
7715 Moira_getGroupName(before[CONTAINER_NAME], ParentGroupName, 1);
7717 memset(GroupName, '\0', sizeof(GroupName));
7719 if (strcmp(before[CONTAINER_GROUP_NAME], "[none]"))
7720 strcpy(GroupName, before[CONTAINER_GROUP_NAME]);
7722 if ((strlen(ParentGroupName) != 0) && (strlen(GroupName) != 0))
7724 argv[0] = ParentGroupName;
7726 argv[2] = GroupName;
7728 if (rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL))
7731 "Unable to delete container group %s from list: %s",
7732 GroupName, ParentGroupName, error_message(rc));
7736 if (strlen(GroupName) != 0)
7738 argv[0] = GroupName;
7740 if (rc = mr_query("delete_list", 1, argv, NULL, NULL))
7742 com_err(whoami, 0, "Unable to delete container group %s : %s",
7743 GroupName, error_message(rc));
7750 int Moira_groupname_create(char *GroupName, char *ContainerName,
7751 char *ContainerRowID)
7756 char newGroupName[64];
7757 char tempGroupName[64];
7763 strcpy(temp, ContainerName);
7765 ptr1 = strrchr(temp, '/');
7771 ptr1 = strrchr(temp, '/');
7775 sprintf(tempgname, "%s-%s", ++ptr1, ptr);
7778 strcpy(tempgname, ptr);
7781 strcpy(tempgname, temp);
7783 if (strlen(tempgname) > 25)
7784 tempgname[25] ='\0';
7786 sprintf(newGroupName, "cnt-%s", tempgname);
7788 /* change everything to lower case */
7794 *ptr = tolower(*ptr);
7802 strcpy(tempGroupName, newGroupName);
7805 /* append 0-9 then a-z if a duplicate is found */
7808 argv[0] = newGroupName;
7810 if (rc = mr_query("get_list_info", 1, argv, NULL, NULL))
7812 if (rc == MR_NO_MATCH)
7814 com_err(whoami, 0, "Moira error while creating group name for "
7815 "container %s : %s", ContainerName, error_message(rc));
7819 sprintf(newGroupName, "%s-%c", tempGroupName, i);
7823 com_err(whoami, 0, "Unable to find a unique group name for "
7824 "container %s: too many duplicate container names",
7835 strcpy(GroupName, newGroupName);
7839 int Moira_setContainerGroup(char *origContainerName, char *GroupName)
7844 argv[0] = origContainerName;
7845 argv[1] = GroupName;
7847 if ((rc = mr_query("set_container_list", 2, argv, NULL, NULL)))
7850 "Unable to set container group %s in container %s: %s",
7851 GroupName, origContainerName, error_message(rc));
7857 int Moira_addGroupToParent(char *origContainerName, char *GroupName)
7859 char ContainerName[64];
7860 char ParentGroupName[64];
7864 strcpy(ContainerName, origContainerName);
7866 Moira_getGroupName(ContainerName, ParentGroupName, 1);
7868 /* top-level container */
7869 if (strlen(ParentGroupName) == 0)
7872 argv[0] = ParentGroupName;
7874 argv[2] = GroupName;
7876 if ((rc = mr_query("add_member_to_list", 3, argv, NULL, NULL)))
7879 "Unable to add container group %s to parent group %s: %s",
7880 GroupName, ParentGroupName, error_message(rc));
7886 int Moira_getContainerGroup(int ac, char **av, void *ptr)
7891 strcpy(call_args[0], av[1]);
7896 int Moira_getGroupName(char *origContainerName, char *GroupName,
7899 char ContainerName[64];
7905 strcpy(ContainerName, origContainerName);
7909 ptr = strrchr(ContainerName, '/');
7917 argv[0] = ContainerName;
7919 call_args[0] = GroupName;
7920 call_args[1] = NULL;
7922 if (!(rc = mr_query("get_container_list", 1, argv, Moira_getContainerGroup,
7925 if (strlen(GroupName) != 0)
7930 com_err(whoami, 0, "Unable to get container group from container %s: %s",
7931 ContainerName, error_message(rc));
7933 com_err(whoami, 0, "Unable to get container group from container %s",
7939 int Moira_process_machine_container_group(char *MachineName, char* GroupName,
7945 if (strcmp(GroupName, "[none]") == 0)
7948 argv[0] = GroupName;
7949 argv[1] = "MACHINE";
7950 argv[2] = MachineName;
7953 rc = mr_query("add_member_to_list", 3, argv, NULL, NULL);
7955 rc = mr_query("delete_member_from_list", 3, argv, NULL, NULL);
7959 com_err(whoami, 0, "Unable to add machine %s to container group%s: %s",
7960 MachineName, GroupName, error_message(rc));
7966 int GetMachineName(char *MachineName)
7969 char NewMachineName[1024];
7976 // If the address happens to be in the top-level MIT domain, great!
7977 strcpy(NewMachineName, MachineName);
7979 for (i = 0; i < (int)strlen(NewMachineName); i++)
7980 NewMachineName[i] = toupper(NewMachineName[i]);
7982 szDot = strchr(NewMachineName,'.');
7984 if ((szDot) && (!strcasecmp(szDot+1, DOMAIN_SUFFIX)))
7989 // If not, see if it has a Moira alias in the top-level MIT domain.
7990 memset(NewMachineName, '\0', sizeof(NewMachineName));
7992 args[1] = MachineName;
7993 call_args[0] = NewMachineName;
7994 call_args[1] = NULL;
7996 if (rc = mr_query("get_hostalias", 2, args, ProcessMachineName, call_args))
7998 com_err(whoami, 0, "Unable to resolve machine name %s : %s",
7999 MachineName, error_message(rc));
8000 strcpy(MachineName, "");
8004 if (strlen(NewMachineName) != 0)
8005 strcpy(MachineName, NewMachineName);
8007 strcpy(MachineName, "");
8012 int ProcessMachineName(int ac, char **av, void *ptr)
8015 char MachineName[1024];
8021 if (strlen(call_args[0]) == 0)
8023 strcpy(MachineName, av[0]);
8025 for (i = 0; i < (int)strlen(MachineName); i++)
8026 MachineName[i] = toupper(MachineName[i]);
8028 szDot = strchr(MachineName,'.');
8030 if ((szDot) && (!strcasecmp(szDot+1,DOMAIN_SUFFIX)))
8032 strcpy(call_args[0], MachineName);
8039 void SwitchSFU(LDAPMod **mods, int *UseSFU30, int n)
8045 for (i = 0; i < n; i++)
8047 if (!strcmp(mods[i]->mod_type, "msSFU30UidNumber"))
8048 mods[i]->mod_type = "uidNumber";
8055 for (i = 0; i < n; i++)
8057 if (!strcmp(mods[i]->mod_type, "uidNumber"))
8058 mods[i]->mod_type = "msSFU30UidNumber";
8065 int SetHomeDirectory(LDAP *ldap_handle, char *user_name,
8066 char *DistinguishedName,
8067 char *WinHomeDir, char *WinProfileDir,
8068 char **homedir_v, char **winProfile_v,
8069 char **drives_v, LDAPMod **mods,
8076 char winProfile[1024];
8079 char apple_homedir[1024];
8080 char *apple_homedir_v[] = {NULL, NULL};
8084 LDAPMod *DelMods[20];
8086 char *save_argv[FS_END];
8087 char *fsgroup_save_argv[2];
8089 memset(homeDrive, '\0', sizeof(homeDrive));
8090 memset(path, '\0', sizeof(path));
8091 memset(winPath, '\0', sizeof(winPath));
8092 memset(winProfile, '\0', sizeof(winProfile));
8094 if(!ActiveDirectory)
8096 if (rc = moira_connect())
8098 critical_alert("Ldap incremental",
8099 "Error contacting Moira server : %s",
8104 argv[0] = user_name;
8106 if (!(rc = mr_query("get_filesys_by_label", 1, argv, save_query_info,
8109 if(!strcmp(save_argv[FS_TYPE], "FSGROUP") ||
8110 !strcmp(save_argv[FS_TYPE], "MUL"))
8113 argv[0] = save_argv[FS_NAME];
8116 if (!(rc = mr_query("get_fsgroup_members", 1, argv,
8117 save_fsgroup_info, fsgroup_save_argv)))
8121 argv[0] = fsgroup_save_argv[0];
8123 if (!(rc = mr_query("get_filesys_by_label", 1, argv,
8124 save_query_info, save_argv)))
8126 strcpy(path, save_argv[FS_PACK]);
8133 strcpy(path, save_argv[FS_PACK]);
8141 if (!strnicmp(path, AFS, strlen(AFS)))
8143 sprintf(homedir, "%s", path);
8144 sprintf(apple_homedir, "%s/MacData", path);
8145 homedir_v[0] = homedir;
8146 apple_homedir_v[0] = apple_homedir;
8147 ADD_ATTR("homeDirectory", homedir_v, OpType);
8148 ADD_ATTR("apple-user-homeDirectory", apple_homedir_v,
8154 homedir_v[0] = "NONE";
8155 apple_homedir_v[0] = "NONE";
8156 ADD_ATTR("homeDirectory", homedir_v, OpType);
8157 ADD_ATTR("apple-user-homeDirectory", apple_homedir_v,
8164 if ((!strcasecmp(WinHomeDir, "[afs]")) ||
8165 (!strcasecmp(WinProfileDir, "[afs]")))
8167 if (rc = moira_connect())
8169 critical_alert("Ldap incremental",
8170 "Error contacting Moira server : %s",
8175 argv[0] = user_name;
8177 if (!(rc = mr_query("get_filesys_by_label", 1, argv, save_query_info,
8180 if(!strcmp(save_argv[FS_TYPE], "FSGROUP") ||
8181 !strcmp(save_argv[FS_TYPE], "MUL"))
8184 argv[0] = save_argv[FS_NAME];
8187 if (!(rc = mr_query("get_fsgroup_members", 1, argv,
8188 save_fsgroup_info, fsgroup_save_argv)))
8192 argv[0] = fsgroup_save_argv[0];
8194 if (!(rc = mr_query("get_filesys_by_label", 1, argv,
8195 save_query_info, save_argv)))
8197 strcpy(path, save_argv[FS_PACK]);
8204 strcpy(path, save_argv[FS_PACK]);
8212 if (!strnicmp(path, AFS, strlen(AFS)))
8214 AfsToWinAfs(path, winPath);
8215 strcpy(winProfile, winPath);
8216 strcat(winProfile, "\\.winprofile");
8223 if ((!strcasecmp(WinHomeDir, "[dfs]")) ||
8224 (!strcasecmp(WinProfileDir, "[dfs]")))
8226 sprintf(path, "\\\\%s\\dfs\\profiles\\%c\\%s", ldap_domain,
8227 user_name[0], user_name);
8229 if (!strcasecmp(WinProfileDir, "[dfs]"))
8231 strcpy(winProfile, path);
8232 strcat(winProfile, "\\.winprofile");
8235 if (!strcasecmp(WinHomeDir, "[dfs]"))
8236 strcpy(winPath, path);
8239 if (!strcasecmp(WinHomeDir, "[local]"))
8240 memset(winPath, '\0', sizeof(winPath));
8241 else if (!strcasecmp(WinHomeDir, "[afs]") ||
8242 !strcasecmp(WinHomeDir, "[dfs]"))
8244 strcpy(homeDrive, "H:");
8248 strcpy(winPath, WinHomeDir);
8249 if (!strncmp(WinHomeDir, "\\\\", 2))
8251 strcpy(homeDrive, "H:");
8255 // nothing needs to be done if WinProfileDir is [afs].
8256 if (!strcasecmp(WinProfileDir, "[local]"))
8257 memset(winProfile, '\0', sizeof(winProfile));
8258 else if (strcasecmp(WinProfileDir, "[afs]") &&
8259 strcasecmp(WinProfileDir, "[dfs]"))
8261 strcpy(winProfile, WinProfileDir);
8264 if (strlen(winProfile) != 0)
8266 if (winProfile[strlen(winProfile) - 1] == '\\')
8267 winProfile[strlen(winProfile) - 1] = '\0';
8270 if (strlen(winPath) != 0)
8272 if (winPath[strlen(winPath) - 1] == '\\')
8273 winPath[strlen(winPath) - 1] = '\0';
8276 if ((winProfile[1] == ':') && (strlen(winProfile) == 2))
8277 strcat(winProfile, "\\");
8279 if ((winPath[1] == ':') && (strlen(winPath) == 2))
8280 strcat(winPath, "\\");
8282 if (strlen(winPath) == 0)
8284 if (OpType == LDAP_MOD_REPLACE)
8287 DEL_ATTR("homeDirectory", LDAP_MOD_DELETE);
8289 //unset homeDirectory attribute for user.
8290 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8296 homedir_v[0] = strdup(winPath);
8297 ADD_ATTR("homeDirectory", homedir_v, OpType);
8300 if (strlen(winProfile) == 0)
8302 if (OpType == LDAP_MOD_REPLACE)
8305 DEL_ATTR("profilePath", LDAP_MOD_DELETE);
8307 //unset profilePate attribute for user.
8308 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8314 winProfile_v[0] = strdup(winProfile);
8315 ADD_ATTR("profilePath", winProfile_v, OpType);
8318 if (strlen(homeDrive) == 0)
8320 if (OpType == LDAP_MOD_REPLACE)
8323 DEL_ATTR("homeDrive", LDAP_MOD_DELETE);
8325 //unset homeDrive attribute for user
8326 rc = ldap_modify_s(ldap_handle, DistinguishedName, DelMods);
8332 drives_v[0] = strdup(homeDrive);
8333 ADD_ATTR("homeDrive", drives_v, OpType);
8339 int attribute_update(LDAP *ldap_handle, char *distinguished_name,
8340 char *attribute_value, char *attribute, char *user_name)
8342 char *mod_v[] = {NULL, NULL};
8343 LDAPMod *DelMods[20];
8349 if (strlen(attribute_value) == 0)
8352 DEL_ATTR(attribute, LDAP_MOD_DELETE);
8354 rc = ldap_modify_s(ldap_handle, distinguished_name, DelMods);
8360 mod_v[0] = attribute_value;
8361 ADD_ATTR(attribute, mod_v, LDAP_MOD_REPLACE);
8364 if ((rc = ldap_modify_s(ldap_handle, distinguished_name,
8365 mods)) != LDAP_SUCCESS)
8369 mod_v[0] = attribute_value;
8370 ADD_ATTR(attribute, mod_v, LDAP_MOD_ADD);
8373 if ((rc = ldap_modify_s(ldap_handle, distinguished_name,
8374 mods)) != LDAP_SUCCESS)
8376 com_err(whoami, 0, "Unable to change the %s attribute for %s "
8377 "in the directory : %s",
8378 attribute, user_name, ldap_err2string(rc));
8388 void StringTrim(char *StringToTrim)
8393 save = strdup(StringToTrim);
8400 /* skip to end of string */
8405 strcpy(StringToTrim, save);
8409 for (t = s; *t; t++)
8425 strcpy(StringToTrim, s);
8429 int ReadConfigFile(char *DomainName)
8440 sprintf(temp, "%s%s.cfg", CFG_PATH, DomainName);
8442 if ((fptr = fopen(temp, "r")) != NULL)
8444 while (fgets(temp, sizeof(temp), fptr) != 0)
8446 for (i = 0; i < (int)strlen(temp); i++)
8447 temp[i] = toupper(temp[i]);
8449 if (temp[strlen(temp) - 1] == '\n')
8450 temp[strlen(temp) - 1] = '\0';
8454 if (strlen(temp) == 0)
8457 if (!strncmp(temp, DOMAIN, strlen(DOMAIN)))
8459 if (strlen(temp) > (strlen(DOMAIN)))
8461 strcpy(ldap_domain, &temp[strlen(DOMAIN)]);
8462 StringTrim(ldap_domain);
8465 else if (!strncmp(temp, REALM, strlen(REALM)))
8467 if (strlen(temp) > (strlen(REALM)))
8469 strcpy(ldap_realm, &temp[strlen(REALM)]);
8470 StringTrim(ldap_realm);
8473 else if (!strncmp(temp, PORT, strlen(PORT)))
8475 if (strlen(temp) > (strlen(PORT)))
8477 strcpy(ldap_port, &temp[strlen(PORT)]);
8478 StringTrim(ldap_port);
8481 else if (!strncmp(temp, PRINCIPALNAME, strlen(PRINCIPALNAME)))
8483 if (strlen(temp) > (strlen(PRINCIPALNAME)))
8485 strcpy(PrincipalName, &temp[strlen(PRINCIPALNAME)]);
8486 StringTrim(PrincipalName);
8489 else if (!strncmp(temp, SERVER, strlen(SERVER)))
8491 if (strlen(temp) > (strlen(SERVER)))
8493 ServerList[Count] = calloc(1, 256);
8494 strcpy(ServerList[Count], &temp[strlen(SERVER)]);
8495 StringTrim(ServerList[Count]);
8499 else if (!strncmp(temp, MSSFU, strlen(MSSFU)))
8501 if (strlen(temp) > (strlen(MSSFU)))
8503 strcpy(temp1, &temp[strlen(MSSFU)]);
8505 if (!strcmp(temp1, SFUTYPE))
8509 else if (!strncmp(temp, GROUP_SUFFIX, strlen(GROUP_SUFFIX)))
8511 if (strlen(temp) > (strlen(GROUP_SUFFIX)))
8513 strcpy(temp1, &temp[strlen(GROUP_SUFFIX)]);
8515 if (!strcasecmp(temp1, "NO"))
8518 memset(group_suffix, '\0', sizeof(group_suffix));
8522 else if (!strncmp(temp, GROUP_TYPE, strlen(GROUP_TYPE)))
8524 if (strlen(temp) > (strlen(GROUP_TYPE)))
8526 strcpy(temp1, &temp[strlen(GROUP_TYPE)]);
8528 if (!strcasecmp(temp1, "UNIVERSAL"))
8529 UseGroupUniversal = 1;
8532 else if (!strncmp(temp, SET_GROUP_ACE, strlen(SET_GROUP_ACE)))
8534 if (strlen(temp) > (strlen(SET_GROUP_ACE)))
8536 strcpy(temp1, &temp[strlen(SET_GROUP_ACE)]);
8538 if (!strcasecmp(temp1, "NO"))
8542 else if (!strncmp(temp, SET_PASSWORD, strlen(SET_PASSWORD)))
8544 if (strlen(temp) > (strlen(SET_PASSWORD)))
8546 strcpy(temp1, &temp[strlen(SET_PASSWORD)]);
8548 if (!strcasecmp(temp1, "NO"))
8552 else if (!strncmp(temp, EXCHANGE, strlen(EXCHANGE)))
8554 if (strlen(temp) > (strlen(EXCHANGE)))
8556 strcpy(temp1, &temp[strlen(EXCHANGE)]);
8558 if (!strcasecmp(temp1, "YES"))
8562 else if (!strncmp(temp, PROCESS_MACHINE_CONTAINER,
8563 strlen(PROCESS_MACHINE_CONTAINER)))
8565 if (strlen(temp) > (strlen(PROCESS_MACHINE_CONTAINER)))
8567 strcpy(temp1, &temp[strlen(PROCESS_MACHINE_CONTAINER)]);
8569 if (!strcasecmp(temp1, "NO"))
8570 ProcessMachineContainer = 0;
8573 else if (!strncmp(temp, ACTIVE_DIRECTORY,
8574 strlen(ACTIVE_DIRECTORY)))
8576 if (strlen(temp) > (strlen(ACTIVE_DIRECTORY)))
8578 strcpy(temp1, &temp[strlen(ACTIVE_DIRECTORY)]);
8580 if (!strcasecmp(temp1, "NO"))
8581 ActiveDirectory = 0;
8584 else if (!strncmp(temp, GROUP_POPULATE_MEMBERS,
8585 strlen(GROUP_POPULATE_MEMBERS)))
8587 if (strlen(temp) > (strlen(GROUP_POPULATE_MEMBERS)))
8589 strcpy(temp1, &temp[strlen(GROUP_POPULATE_MEMBERS)]);
8591 if (!strcasecmp(temp1, "DELETE"))
8593 GroupPopulateDelete = 1;
8599 if (strlen(ldap_domain) != 0)
8601 memset(ldap_domain, '\0', sizeof(ldap_domain));
8605 if (strlen(temp) != 0)
8606 strcpy(ldap_domain, temp);
8612 if (strlen(ldap_domain) == 0)
8614 strcpy(ldap_domain, DomainName);
8620 for (i = 0; i < Count; i++)
8622 if (ServerList[i] != 0)
8624 for (k = 0; k < (int)strlen(ServerList[i]); k++)
8625 ServerList[i][k] = toupper(ServerList[i][k]);
8632 int ReadDomainList()
8639 unsigned char c[11];
8640 unsigned char stuff[256];
8645 sprintf(temp, "%s%s", CFG_PATH, WINADCFG);
8647 if ((fptr = fopen(temp, "r")) != NULL)
8649 while (fgets(temp, sizeof(temp), fptr) != 0)
8651 for (i = 0; i < (int)strlen(temp); i++)
8652 temp[i] = toupper(temp[i]);
8654 if (temp[strlen(temp) - 1] == '\n')
8655 temp[strlen(temp) - 1] = '\0';
8659 if (strlen(temp) == 0)
8662 if (!strncmp(temp, DOMAIN, strlen(DOMAIN)))
8664 if (strlen(temp) > (strlen(DOMAIN)))
8666 strcpy(temp1, &temp[strlen(DOMAIN)]);
8668 strcpy(temp, temp1);
8672 strcpy(DomainNames[Count], temp);
8673 StringTrim(DomainNames[Count]);
8682 critical_alert("incremental", "%s", "ldap.incr cannot run due to a "
8683 "configuration error in ldap.cfg");
8690 int email_isvalid(const char *address) {
8692 const char *c, *domain;
8693 static char *rfc822_specials = "()<>@,;:\\\"[]";
8695 if(address[strlen(address) - 1] == '.')
8698 /* first we validate the name portion (name@domain) */
8699 for (c = address; *c; c++) {
8700 if (*c == '\"' && (c == address || *(c - 1) == '.' || *(c - 1) ==
8705 if (*c == '\\' && (*++c == ' '))
8707 if (*c <= ' ' || *c >= 127)
8722 if (*c <= ' ' || *c >= 127)
8724 if (strchr(rfc822_specials, *c))
8728 if (c == address || *(c - 1) == '.')
8731 /* next we validate the domain portion (name@domain) */
8732 if (!*(domain = ++c)) return 0;
8735 if (c == domain || *(c - 1) == '.')
8739 if (*c <= ' ' || *c >= 127)
8741 if (strchr(rfc822_specials, *c))
8745 return (count >= 1);
8748 int find_homeMDB(LDAP *ldap_handle, char *dn_path, char **homeMDB,
8749 char **homeServerName)
8751 LK_ENTRY *group_base;
8752 LK_ENTRY *sub_group_base;
8756 int sub_group_count;
8758 char sub_filter[1024];
8759 char search_path[1024];
8761 char *attr_array[3];
8763 int homeMDB_count = -1;
8767 int rangeStep = 1500;
8769 int rangeHigh = rangeLow + (rangeStep - 1);
8772 /* Grumble..... microsoft not making it searchable from the root *grr* */
8774 memset(filter, '\0', sizeof(filter));
8775 memset(search_path, '\0', sizeof(search_path));
8777 sprintf(filter, "(objectClass=msExchMDB)");
8778 sprintf(search_path, "CN=Configuration,%s", dn_path);
8779 attr_array[0] = "distinguishedName";
8780 attr_array[1] = NULL;
8785 if ((rc = linklist_build(ldap_handle, search_path, filter, attr_array,
8786 &group_base, &group_count,
8787 LDAP_SCOPE_SUBTREE)) != 0)
8789 com_err(whoami, 0, "Unable to find msExchMDB %s",
8790 ldap_err2string(rc));
8799 if (((s = strstr(gPtr->dn, "Public")) != (char *) NULL) ||
8800 ((s = strstr(gPtr->dn, "Recover")) != (char *) NULL) ||
8801 ((s = strstr(gPtr->dn, "Reserve")) != (char *) NULL))
8808 * Due to limits in active directory we need to use the LDAP
8809 * range semantics to query and return all the values in
8810 * large lists, we will stop increasing the range when
8811 * the result count is 0.
8819 memset(sub_filter, '\0', sizeof(sub_filter));
8820 memset(range, '\0', sizeof(range));
8821 sprintf(sub_filter, "(objectClass=msExchMDB)");
8824 sprintf(range, "homeMDBBL;Range=%d-*", rangeLow);
8826 sprintf(range, "homeMDBBL;Range=%d-%d", rangeLow, rangeHigh);
8828 attr_array[0] = range;
8829 attr_array[1] = NULL;
8831 sub_group_base = NULL;
8832 sub_group_count = 0;
8834 if ((rc = linklist_build(ldap_handle, gPtr->dn, sub_filter,
8835 attr_array, &sub_group_base,
8837 LDAP_SCOPE_SUBTREE)) != 0)
8839 com_err(whoami, 0, "Unable to find homeMDBBL %s",
8840 ldap_err2string(rc));
8844 if(!sub_group_count)
8850 rangeHigh = rangeLow + (rangeStep - 1);
8857 mdbbl_count += sub_group_count;
8858 rangeLow = rangeHigh + 1;
8859 rangeHigh = rangeLow + (rangeStep - 1);
8862 /* First time through, need to initialize or update the least used */
8864 com_err(whoami, 0, "Mail store %s, count %d", gPtr->dn,
8867 if(mdbbl_count < homeMDB_count || homeMDB_count == -1)
8869 homeMDB_count = mdbbl_count;
8870 *homeMDB = strdup(gPtr->dn);
8874 linklist_free(sub_group_base);
8878 linklist_free(group_base);
8881 * Ok found the server least allocated need to now query to get its
8882 * msExchHomeServerName so we can set it as a user attribute
8885 attr_array[0] = "legacyExchangeDN";
8886 attr_array[1] = NULL;
8891 if ((rc = linklist_build(ldap_handle, *homeMDB, filter,
8892 attr_array, &group_base,
8894 LDAP_SCOPE_SUBTREE)) != 0)
8896 com_err(whoami, 0, "Unable to find msExchHomeServerName %s",
8897 ldap_err2string(rc));
8903 *homeServerName = strdup(group_base->value);
8904 if((s = strrchr(*homeServerName, '/')) != (char *) NULL)
8910 linklist_free(group_base);
8915 char *lowercase(char *s)
8919 for (p = s; *p; p++)
8927 char *uppercase(char *s)
8931 for (p = s; *p; p++)
8939 char *escape_string(char *s)
8947 memset(string, '\0', sizeof(string));
8951 /* Escape any special characters */
8953 for(; *q != '\0'; q++) {
8976 return strdup(string);
8979 int save_query_info(int argc, char **argv, void *hint)
8982 char **nargv = hint;
8984 for(i = 0; i < argc; i++)
8985 nargv[i] = strdup(argv[i]);
8990 int save_fsgroup_info(int argc, char **argv, void *hint)
8993 char **nargv = hint;
8997 for(i = 0; i < argc; i++)
8998 nargv[i] = strdup(argv[i]);