]> andersk Git - moira.git/blame - incremental/winad/winad.c
Allow for queries on mcntmap table.
[moira.git] / incremental / winad / winad.c
CommitLineData
5d0a7127 1/* $Header$
89db421e 2/* winad.incr arguments examples
cd9e6b16 3 *
89db421e 4 * arguments when moira creates the account - ignored by winad.incr since the account is unusable.
5 * users 0 11 #45198 45198 /bin/cmd cmd Last First Middle 0 950000001 2000 121049
6 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
cd9e6b16 7 *
89db421e 8 * arguments for creating or updating a user account
9 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF 121058 username 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF 121058
10 * users 11 11 #45206 45206 /bin/cmd cmd Last First Middle 0 950000001 STAFF 121058 newuser 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF 121058
11 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
78af4e6e 12 *
89db421e 13 * arguments for deactivating/deleting a user account
14 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF 121058 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF 121058
15 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF 121058 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF 121058
16 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
cd9e6b16 17 *
89db421e 18 * arguments for reactivating a user account
19 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF 121058 username 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF 121058
20 * users 11 11 username 45206 /bin/cmd cmd Last First Middle 3 950000001 STAFF 121058 username 45206 /bin/cmd cmd Last First Middle 2 950000001 STAFF 121058
21 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
cd9e6b16 22 *
89db421e 23 * arguments for changing user name
24 * users 11 11 oldusername 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF 121058 newusername 45206 /bin/cmd cmd Last First Middle 1 950000001 STAFF 121058
25 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
cd9e6b16 26 *
89db421e 27 * arguments for expunging a user
28 * users 11 0 username 45198 /bin/cmd cmd Last First Middle 0 950000001 2000 121049
29 * login, unix_uid, shell, winconsoleshell, last, first, middle, status, mitid, type, moiraid
30 *
31 * arguments for creating a "special" group/list
32 * list 0 11 listname 1 1 0 0 0 -1 NONE 0 description 92616
33 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraid
9db0b148 34 *
89db421e 35 * arguments for creating a "mail" group/list
36 * list 0 11 listname 1 1 0 1 0 -1 NONE 0 description 92616
37 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraid
38 *
39 * arguments for creating a "group" group/list
40 * list 0 11 listname 1 1 0 0 1 -1 NONE 0 description 92616
41 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraid
42 *
43 * arguments for creating a "group/mail" group/list
44 * list 0 11 listname 1 1 0 1 1 -1 NONE 0 description 92616
45 * listname, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraid
46 *
47 * arguments to add a USER member to group/list
48 * imembers 0 12 listname USER userName 1 1 0 0 0 -1 1 92616 121047
49 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist, gid, userStatus, moiraListId, moiraUserId
50 *
51 * arguments to add a STRING or KERBEROS member to group/list
52 * imembers 0 10 listname STRING stringName 1 1 0 0 0 -1 92616
53 * imembers 0 10 listlistnameName KERBEROS kerberosName 1 1 0 0 0 -1 92616
54 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist, gid, moiraListId
55 *
56 * NOTE: group members of type LIST are ignored.
57 *
58 * arguments to remove a USER member to group/list
59 * imembers 12 0 listname USER userName 1 1 0 0 0 -1 1 92616 121047
60 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist, gid, userStatus, moiraListId, moiraUserId
61 *
62 * arguments to remove a STRING or KERBEROS member to group/list
63 * imembers 10 0 listname STRING stringName 1 1 0 0 0 -1 92616
64 * imembers 10 0 listname KERBEROS kerberosName 1 1 0 0 0 -1 92616
65 * list_name, user_type, name, active, publicflg, hidden, maillist, grouplist, gid, moiraListId
9db0b148 66 *
89db421e 67 * NOTE: group members of type LIST are ignored.
f75f605a 68 *
89db421e 69 * arguments for renaming a group/list
70 * list 11 11 oldlistname 1 1 0 0 0 -1 NONE 0 description 92616 newlistname 1 1 0 0 0 -1 description 0 92616
71 * name, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraListId
f75f605a 72 *
89db421e 73 * arguments for deleting a group/list
74 * list 11 0 listname 1 1 0 0 0 -1 NONE 0 description 92616
75 * name, active, publicflg, hidden, maillist, grouplist, gid, acl_type, acl_id, description, moiraListId
6c8f12af 76 *
89db421e 77 * arguments for adding a file system
78 * filesys 0 12 username AFS ATHENA.MIT.EDU /afs/athena.mit.edu/user/n/e/username /mit/username w descripton username wheel 1 HOMEDIR 101727
79 *
80 * arguments for deleting a file system
81 * filesys 12 0 username AFS ATHENA.MIT.EDU /afs/athena.mit.edu/user/n/e/username /mit/username w descripton username wheel 1 HOMEDIR 101727
6c8f12af 82 *
83 * arguments when moira creates a container (OU).
84 * containers 0 7 machines/test/bottom description location contact USER 105316 2222
85 *
86 * arguments when moira deletes a container (OU).
87 * containers 7 0 machines/test/bottom description location contact USER 105316 2222
9cfe334f 88 *
6c8f12af 89 * arguments when moira modifies a container information (OU).
9cfe334f 90 * containers 7 7 machines/test/bottom description location contact USER 105316 2222 machines/test/bottom description1 location contact USER 105316 2222
cd9e6b16 91*/
5d0a7127 92#include <mit-copyright.h>
93#ifdef _WIN32
94#include <windows.h>
95#include <stdlib.h>
96#include <malloc.h>
97#include <lmaccess.h>
98#endif
f78c7eaf 99#include <hesiod.h>
cd9e6b16 100#include <string.h>
5d0a7127 101#include <ldap.h>
102#include <stdio.h>
103#include <moira.h>
104#include <moira_site.h>
cd9e6b16 105#include <mrclient.h>
5d0a7127 106#include <krb5.h>
107#include <krb.h>
108#include <gsssasl.h>
109#include <gssldap.h>
cd9e6b16 110#include "kpasswd.h"
111
112#ifdef _WIN32
113#ifndef ECONNABORTED
114#define ECONNABORTED WSAECONNABORTED
115#endif
116#ifndef ECONNREFUSED
117#define ECONNREFUSED WSAECONNREFUSED
118#endif
119#ifndef EHOSTUNREACH
120#define EHOSTUNREACH WSAEHOSTUNREACH
121#endif
122#define krb5_xfree free
0d958b3c 123#define F_OK 0
124#define sleep(A) Sleep(A * 1000);
cd9e6b16 125#endif /* _WIN32 */
5d0a7127 126
127#ifndef _WIN32
f78c7eaf 128#include <sys/types.h>
129#include <netinet/in.h>
130#include <arpa/nameser.h>
131#include <resolv.h>
5d0a7127 132#include <sys/utsname.h>
0d958b3c 133#include <unistd.h>
5d0a7127 134
f75f605a 135#define WINADCFG "/moira/winad/winad.cfg"
f78c7eaf 136#define strnicmp(A,B,C) strncasecmp(A,B,C)
cd9e6b16 137#define UCHAR unsigned char
138
5d0a7127 139#define UF_SCRIPT 0x0001
140#define UF_ACCOUNTDISABLE 0x0002
141#define UF_HOMEDIR_REQUIRED 0x0008
142#define UF_LOCKOUT 0x0010
143#define UF_PASSWD_NOTREQD 0x0020
144#define UF_PASSWD_CANT_CHANGE 0x0040
cd9e6b16 145#define UF_DONT_EXPIRE_PASSWD 0x10000
5d0a7127 146
147#define UF_TEMP_DUPLICATE_ACCOUNT 0x0100
148#define UF_NORMAL_ACCOUNT 0x0200
149#define UF_INTERDOMAIN_TRUST_ACCOUNT 0x0800
150#define UF_WORKSTATION_TRUST_ACCOUNT 0x1000
151#define UF_SERVER_TRUST_ACCOUNT 0x2000
152
909e0dc3 153#define OWNER_SECURITY_INFORMATION (0x00000001L)
154#define GROUP_SECURITY_INFORMATION (0x00000002L)
155#define DACL_SECURITY_INFORMATION (0x00000004L)
156#define SACL_SECURITY_INFORMATION (0x00000008L)
157
5d0a7127 158#ifndef BYTE
159#define BYTE unsigned char
160#endif
161typedef unsigned int DWORD;
162typedef unsigned long ULONG;
163
164typedef struct _GUID
165{
166 unsigned long Data1;
167 unsigned short Data2;
168 unsigned short Data3;
169 unsigned char Data4[8];
170} GUID;
171
172typedef struct _SID_IDENTIFIER_AUTHORITY {
173 BYTE Value[6];
174} SID_IDENTIFIER_AUTHORITY, *PSID_IDENTIFIER_AUTHORITY;
175
176typedef struct _SID {
177 BYTE Revision;
178 BYTE SubAuthorityCount;
179 SID_IDENTIFIER_AUTHORITY IdentifierAuthority;
180 DWORD SubAuthority[512];
181} SID;
182#endif/*!WIN32*/
183
f75f605a 184#ifndef WINADCFG
185#define WINADCFG "winad.cfg"
186#endif
187
f78c7eaf 188#define AFS "/afs/"
189#define WINAFS "\\\\afs\\all\\"
190
cd9e6b16 191#define ADS_GROUP_TYPE_GLOBAL_GROUP 0x00000002
f78c7eaf 192#define ADS_GROUP_TYPE_DOMAIN_LOCAL_GROUP 0x00000004
193#define ADS_GROUP_TYPE_LOCAL_GROUP 0x00000004
194#define ADS_GROUP_TYPE_UNIVERSAL_GROUP 0x00000008
195#define ADS_GROUP_TYPE_SECURITY_ENABLED 0x80000000
cd9e6b16 196
197#define QUERY_VERSION -1
198#define PRIMARY_REALM "ATHENA.MIT.EDU"
199
5d0a7127 200#define SUBSTITUTE 1
201#define REPLACE 2
202
cd9e6b16 203#define USERS 0
204#define GROUPS 1
205
5d0a7127 206#define MEMBER_ADD 1
207#define MEMBER_REMOVE 2
208#define MEMBER_CHANGE_NAME 3
209#define MEMBER_ACTIVATE 4
210#define MEMBER_DEACTIVATE 5
cd9e6b16 211#define MEMBER_CREATE 6
5d0a7127 212
f78c7eaf 213#define MOIRA_ALL 0x0
214#define MOIRA_USERS 0x1
215#define MOIRA_KERBEROS 0x2
216#define MOIRA_STRINGS 0x4
217#define MOIRA_LISTS 0x8
218
89db421e 219#define CHECK_GROUPS 1
220#define CLEANUP_GROUPS 2
221
222#define AD_NO_GROUPS_FOUND -1
223#define AD_WRONG_GROUP_DN_FOUND -2
224#define AD_MULTIPLE_GROUPS_FOUND -3
225#define AD_INVALID_NAME -4
226#define AD_LDAP_FAILURE -5
227#define AD_INVALID_FILESYS -6
228#define AD_NO_ATTRIBUTE_FOUND -7
229#define AD_NO_OU_FOUND -8
230#define AD_NO_USER_FOUND -9
231
6c8f12af 232/* container arguments */
233#define CONTAINER_NAME 0
234#define CONTAINER_DESC 1
235#define CONTAINER_LOCATION 2
236#define CONTAINER_CONTACT 3
237#define CONTAINER_TYPE 4
238#define CONTAINER_ID 5
239#define CONTAINER_ROWID 6
240
5d0a7127 241typedef struct lk_entry {
242 int op;
243 int length;
244 int ber_value;
245 char *dn;
246 char *attribute;
247 char *value;
248 char *member;
249 char *type;
250 char *list;
251 struct lk_entry *next;
252} LK_ENTRY;
253
0d958b3c 254#define STOP_FILE "/moira/winad/nowinad"
255#define file_exists(file) (access((file), F_OK) == 0)
256
909e0dc3 257#define N_SD_BER_BYTES 5
5d0a7127 258#define LDAP_BERVAL struct berval
cd9e6b16 259#define MAX_SERVER_NAMES 32
260
909e0dc3 261#define HIDDEN_GROUP "HiddenGroup.g"
262#define HIDDEN_GROUP_WITH_ADMIN "HiddenGroupWithAdmin.g"
263#define NOT_HIDDEN_GROUP "NotHiddenGroup.g"
264#define NOT_HIDDEN_GROUP_WITH_ADMIN "NotHiddenGroupWithAdmin.g"
265
cd9e6b16 266#define ADD_ATTR(t, v, o) \
267 mods[n] = malloc(sizeof(LDAPMod)); \
268 mods[n]->mod_op = o; \
269 mods[n]->mod_type = t; \
270 mods[n++]->mod_values = v
5d0a7127 271
272LK_ENTRY *member_base = NULL;
cd9e6b16 273LK_ENTRY *sid_base = NULL;
274LK_ENTRY **sid_ptr = NULL;
0d958b3c 275static char tbl_buf[1024];
89db421e 276char kerberos_ou[] = "OU=kerberos,OU=moira";
277char contact_ou[] = "OU=strings,OU=moira";
278char user_ou[] = "OU=users,OU=moira";
279char group_ou_distribution[] = "OU=mail,OU=lists,OU=moira";
280char group_ou_root[] = "OU=lists,OU=moira";
281char group_ou_security[] = "OU=group,OU=lists,OU=moira";
282char group_ou_neither[] = "OU=special,OU=lists,OU=moira";
283char group_ou_both[] = "OU=mail,OU=group,OU=lists,OU=moira";
6c8f12af 284char orphans_machines_ou[] = "OU=Machines,OU=Orphans";
285char orphans_other_ou[] = "OU=Other,OU=Orphans";
909e0dc3 286char security_template_ou[] = "OU=security_templates";
5d0a7127 287char *whoami;
cd9e6b16 288char ldap_domain[256];
cd9e6b16 289int mr_connections = 0;
78af4e6e 290int callback_rc;
f78c7eaf 291char default_server[256];
bfb6f0ad 292static char tbl_buf[1024];
cd9e6b16 293
f78c7eaf 294extern int set_password(char *user, char *password, char *domain);
cd9e6b16 295
89db421e 296int ad_get_group(LDAP *ldap_handle, char *dn_path, char *group_name,
297 char *group_membership, char *MoiraId, char *attribute,
298 LK_ENTRY **linklist_base, int *linklist_count,
299 char *rFilter);
f78c7eaf 300void AfsToWinAfs(char* path, char* winPath);
301int ad_connect(LDAP **ldap_handle, char *ldap_domain, char *dn_path,
302 char *Win2kPassword, char *Win2kUser, char *default_server,
303 int connect_to_kdc);
304void ad_kdc_disconnect();
909e0dc3 305int BEREncodeSecurityBits(ULONG uBits, char *pBuffer);
306int checkAce(LDAP *ldap_handle, char *dn_path, char *Name);
0d958b3c 307void check_winad(void);
89db421e 308int check_user(LDAP *ldap_handle, char *dn_path, char *UserName, char *MoiraId);
6c8f12af 309/* containers */
310int container_adupdate(LDAP *ldap_handle, char *dn_path, char *dName,
311 char *distinguishedName, int count, char **av);
312void container_check(LDAP *ldap_handle, char *dn_path, char *name);
313int container_create(LDAP *ldap_handle, char *dn_path, int count, char **av);
314int container_delete(LDAP *ldap_handle, char *dn_path, int count, char **av);
315int container_get_distinguishedName(LDAP *ldap_handle, char *dn_path,
316 char *distinguishedName, int count, char **av);
317void container_get_dn(char *src, char *dest);
318void container_get_name(char *src, char *dest);
319int container_move_objects(LDAP *ldap_handle, char *dn_path, char *dName);
320int container_rename(LDAP *ldap_handle, char *dn_path, int beforec, char **before,
321 int afterc, char **after);
322int container_update(LDAP *ldap_handle, char *dn_path, int beforec, char **before,
323 int afterc, char **after);
324
f75f605a 325int filesys_process(LDAP *ldap_handle, char *dn_path, char *fs_name,
326 char *fs_type, char *fs_pack, int operation);
909e0dc3 327int GetAceInfo(int ac, char **av, void *ptr);
f75f605a 328int get_group_membership(char *group_membership, char *group_ou,
329 int *security_flag, char **av);
5f7b0741 330int get_machine_ou(LDAP *ldap_handle, char *dn_path, char *member, char *machine_ou);
909e0dc3 331int ProcessAce(LDAP *ldap_handle, char *dn_path, char *group_name, char *Type,
332 int UpdateGroup, int *ProcessGroup);
89db421e 333int process_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
334 char *group_name, char *group_ou, char *group_membership,
335 int group_security_flag, int type);
f75f605a 336int process_lists(int ac, char **av, void *ptr);
909e0dc3 337int ProcessGroupSecurity(LDAP *ldap_handle, char *dn_path, char *TargetGroupName,
338 int HiddenGroup, char *AceType, char *AceName);
cd9e6b16 339int user_create(int ac, char **av, void *ptr);
89db421e 340int user_change_status(LDAP *ldap_handle, char *dn_path,
341 char *user_name, char *MoiraId, int operation);
342int user_delete(LDAP *ldap_handle, char *dn_path,
343 char *u_name, char *MoiraId);
f75f605a 344int user_rename(LDAP *ldap_handle, char *dn_path, char *before_user_name,
89db421e 345 char *user_name);
f75f605a 346int user_update(LDAP *ldap_handle, char *dn_path, char *user_name,
89db421e 347 char *uid, char *MitId, char *MoiraId, int State);
348void change_to_lower_case(char *ptr);
cd9e6b16 349int contact_create(LDAP *ld, char *bind_path, char *user, char *group_ou);
cd9e6b16 350int group_create(int ac, char **av, void *ptr);
f75f605a 351int group_delete(LDAP *ldap_handle, char *dn_path,
89db421e 352 char *group_name, char *group_membership, char *MoiraId);
f75f605a 353int group_rename(LDAP *ldap_handle, char *dn_path,
354 char *before_group_name, char *before_group_membership,
5a775f54 355 char *before_group_ou, int before_security_flag, char *before_desc,
f75f605a 356 char *after_group_name, char *after_group_membership,
89db421e 357 char *after_group_ou, int after_security_flag, char *after_desc,
358 char *MoiraId, char *filter);
359int make_new_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
360 char *group_name, char *group_ou, char *group_membership,
361 int group_security_flag, int updateGroup);
cd9e6b16 362int member_list_build(int ac, char **av, void *ptr);
f75f605a 363int member_add(LDAP *ldap_handle, char *dn_path, char *group_name,
364 char *group_ou, char *group_membership,
89db421e 365 char *user_name, char *pUserOu, char *MoiraId);
78af4e6e 366int member_remove(LDAP *ldap_handle, char *dn_path, char *group_name,
f75f605a 367 char *group_ou, char *group_membership, char *user_name,
89db421e 368 char *pUserOu, char *MoiraId);
369int populate_group(LDAP *ldap_handle, char *dn_path, char *group_name,
370 char *group_ou, char *group_membership,
371 int group_security_flag, char *MoiraId);
cd9e6b16 372int sid_update(LDAP *ldap_handle, char *dn_path);
373int check_string(char *s);
bb52f279 374int check_container_name(char* s);
cd9e6b16 375void convert_b_to_a(char *string, UCHAR *binary, int length);
376int mr_connect_cl(char *server, char *client, int version, int auth);
377
6c8f12af 378void do_container(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
379 char **before, int beforec, char **after, int afterc);
f78c7eaf 380void do_filesys(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
381 char **before, int beforec, char **after, int afterc);
382void do_list(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
383 char **before, int beforec, char **after, int afterc);
384void do_user(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
cd9e6b16 385 char **before, int beforec, char **after, int afterc);
5d0a7127 386void do_member(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
cd9e6b16 387 char **before, int beforec, char **after, int afterc);
388int linklist_create_entry(char *attribute, char *value,
389 LK_ENTRY **linklist_entry);
5d0a7127 390int linklist_build(LDAP *ldap_handle, char *dn_path, char *search_exp,
cd9e6b16 391 char **attr_array, LK_ENTRY **linklist_base,
392 int *linklist_count);
5d0a7127 393void linklist_free(LK_ENTRY *linklist_base);
cd9e6b16 394
395int retrieve_attributes(LDAP *ldap_handle, LDAPMessage *ldap_entry,
396 char *distinguished_name, LK_ENTRY **linklist_current);
397int retrieve_entries(LDAP *ldap_handle, LDAPMessage *ldap_entry,
398 LK_ENTRY **linklist_base, int *linklist_count);
399int retrieve_values(LDAP *ldap_handle, LDAPMessage *ldap_entry,
400 char *Attribute, char *distinguished_name,
401 LK_ENTRY **linklist_current);
402
403int construct_newvalues(LK_ENTRY *linklist_base, int modvalue_count,
404 char *oldValue, char *newValue,
405 char ***modvalues, int type);
406void free_values(char **modvalues);
407
408int convert_domain_to_dn(char *domain, char **bind_path);
5d0a7127 409void get_distinguished_name(LDAP *ldap_handle, LDAPMessage *ldap_entry,
cd9e6b16 410 char *distinguished_name);
5d0a7127 411int moira_disconnect(void);
412int moira_connect(void);
413void print_to_screen(const char *fmt, ...);
5d0a7127 414
415int main(int argc, char **argv)
416{
cd9e6b16 417 unsigned long rc;
418 int beforec;
419 int afterc;
cd9e6b16 420 int i;
cd9e6b16 421 char *table;
422 char **before;
423 char **after;
cd9e6b16 424 LDAP *ldap_handle;
5d0a7127 425 FILE *fptr;
f78c7eaf 426 char dn_path[256];
cd9e6b16 427
5d0a7127 428 whoami = ((whoami = (char *)strrchr(argv[0], '/')) ? whoami+1 : argv[0]);
cd9e6b16 429
430 if (argc < 4)
431 {
432 com_err(whoami, 0, "%s", "argc < 4");
433 exit(1);
434 }
435 beforec = atoi(argv[2]);
436 afterc = atoi(argv[3]);
437
438 if (argc < (4 + beforec + afterc))
439 {
440 com_err(whoami, 0, "%s", "argc < (4 + breforec + afterc)");
441 exit(1);
442 }
443
444 table = argv[1];
445 before = &argv[4];
446 after = &argv[4 + beforec];
447
bfb6f0ad 448 for (i = 1; i < argc; i++)
0d958b3c 449 {
bfb6f0ad 450 strcat(tbl_buf, argv[i]);
451 strcat(tbl_buf, " ");
0d958b3c 452 }
bfb6f0ad 453 com_err(whoami, 0, "%s", tbl_buf);
454
0d958b3c 455 check_winad();
f75f605a 456
cd9e6b16 457 memset(ldap_domain, '\0', sizeof(ldap_domain));
f75f605a 458 if ((fptr = fopen(WINADCFG, "r")) != NULL)
5d0a7127 459 {
cd9e6b16 460 fread(ldap_domain, sizeof(char), sizeof(ldap_domain), fptr);
5d0a7127 461 fclose(fptr);
462 }
cd9e6b16 463 if (strlen(ldap_domain) == 0)
9db0b148 464 strcpy(ldap_domain, "win.mit.edu");
5d0a7127 465 initialize_sms_error_table();
466 initialize_krb_error_table();
cd9e6b16 467
f78c7eaf 468 memset(default_server, '\0', sizeof(default_server));
469 memset(dn_path, '\0', sizeof(dn_path));
89db421e 470 for (i = 0; i < 5; i++)
cd9e6b16 471 {
89db421e 472 if (!(rc = ad_connect(&ldap_handle, ldap_domain, dn_path, "", "", default_server, 1)))
473 break;
474 sleep(2);
475 }
476 if (rc)
477 {
478 critical_alert("incremental", "winad.incr cannot connect to any server in domain %s", ldap_domain);
cd9e6b16 479 exit(1);
480 }
cd9e6b16 481
9db0b148 482 for (i = 0; i < (int)strlen(table); i++)
483 table[i] = tolower(table[i]);
5d0a7127 484 if (!strcmp(table, "users"))
f78c7eaf 485 do_user(ldap_handle, dn_path, ldap_domain, before, beforec, after,
486 afterc);
5d0a7127 487 else if (!strcmp(table, "list"))
cd9e6b16 488 do_list(ldap_handle, dn_path, ldap_domain, before, beforec, after,
489 afterc);
5d0a7127 490 else if (!strcmp(table, "imembers"))
cd9e6b16 491 do_member(ldap_handle, dn_path, ldap_domain, before, beforec, after,
492 afterc);
cd9e6b16 493 else if (!strcmp(table, "filesys"))
f78c7eaf 494 do_filesys(ldap_handle, dn_path, ldap_domain, before, beforec, after,
495 afterc);
6c8f12af 496 else if (!strcmp(table, "containers"))
497 do_container(ldap_handle, dn_path, ldap_domain, before, beforec, after,
498 afterc);
f78c7eaf 499 ad_kdc_disconnect();
5d0a7127 500 rc = ldap_unbind_s(ldap_handle);
5d0a7127 501 exit(0);
502}
503
6c8f12af 504void do_container(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
505 char **before, int beforec, char **after, int afterc)
506{
507
508 if ((beforec == 0) && (afterc == 0))
509 return;
510
511 if ((beforec != 0) && (afterc == 0)) /*delete a new container*/
512 {
513 com_err(whoami, 0, "deleting container %s", before[CONTAINER_NAME]);
514 container_delete(ldap_handle, dn_path, beforec, before);
515 return;
516 }
517 if ((beforec == 0) && (afterc != 0)) /*create a container*/
518 {
9cfe334f 519 com_err(whoami, 0, "creating container %s", after[CONTAINER_NAME]);
6c8f12af 520 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
521 container_create(ldap_handle, dn_path, afterc, after);
522 return;
523 }
524
525 if (strcasecmp(before[CONTAINER_NAME], after[CONTAINER_NAME]))
526 {
527 com_err(whoami, 0, "renaming container %s to %s", before[CONTAINER_NAME], after[CONTAINER_NAME]);
528 container_rename(ldap_handle, dn_path, beforec, before, afterc, after);
529 return;
530 }
9cfe334f 531 com_err(whoami, 0, "updating container %s information", after[CONTAINER_NAME]);
6c8f12af 532 container_update(ldap_handle, dn_path, beforec, before, afterc, after);
533 return;
534}
535
f78c7eaf 536void do_filesys(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
537 char **before, int beforec, char **after, int afterc)
538{
539 long rc;
540 char *av[3];
541 char *call_args[7];
542 int acreate;
543 int atype;
544 int bcreate;
545 int btype;
f75f605a 546 int abort_flag;
f78c7eaf 547
f75f605a 548 abort_flag = 0;
f78c7eaf 549
550 if (afterc < FS_CREATE)
551 atype = acreate = 0;
552 else
553 {
554 atype = !strcmp(after[FS_TYPE], "AFS");
555 acreate = atoi(after[FS_CREATE]);
556 }
557
558 if (beforec < FS_CREATE)
559 {
560 if (acreate == 0 || atype == 0)
561 goto cleanup;
562 com_err(whoami, 0, "Processing filesys %s", after[FS_NAME]);
f75f605a 563 abort_flag = 0;
564 while (1)
565 {
566 if ((rc = filesys_process(ldap_handle, dn_path, after[FS_NAME],
567 after[FS_TYPE], after[FS_PACK], LDAP_MOD_ADD)) != LDAP_NO_SUCH_OBJECT)
568 {
569 if (rc != LDAP_SUCCESS)
570 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
571 break;
572 }
573 if (abort_flag == 1)
574 break;
575 sleep(1);
576 abort_flag = 1;
577 if (rc = moira_connect())
578 {
579 critical_alert("AD incremental",
580 "Error contacting Moira server : %s",
581 error_message(rc));
582 return;
583 }
584 av[0] = after[FS_NAME];
585 call_args[0] = (char *)ldap_handle;
586 call_args[1] = dn_path;
89db421e 587 call_args[2] = "";
f75f605a 588 call_args[3] = NULL;
589 sid_base = NULL;
590 sid_ptr = &sid_base;
5b8457c5 591 callback_rc = 0;
f75f605a 592 if (rc = mr_query("get_user_account_by_login", 1, av, user_create,
593 call_args))
594 {
595 moira_disconnect();
596 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
597 break;
598 }
5b8457c5 599 if (callback_rc)
600 {
601 moira_disconnect();
602 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
603 break;
604 }
f75f605a 605 if (sid_base != NULL)
606 {
607 sid_update(ldap_handle, dn_path);
608 linklist_free(sid_base);
609 sid_base = NULL;
610 }
611 moira_disconnect();
612 }
f78c7eaf 613 goto cleanup;
614 }
615
616 btype = !strcmp(before[FS_TYPE], "AFS");
617 bcreate = atoi(before[FS_CREATE]);
618 if (afterc < FS_CREATE)
619 {
620 if (btype && bcreate)
621 {
f75f605a 622 if (rc = filesys_process(ldap_handle, dn_path, before[FS_NAME],
623 before[FS_TYPE], before[FS_PACK], LDAP_MOD_DELETE))
f78c7eaf 624 {
f75f605a 625 com_err(whoami, 0, "Couldn't delete filesys %s", before[FS_NAME]);
f78c7eaf 626 }
627 }
f75f605a 628 return;
f78c7eaf 629 }
630
631 if (!acreate)
f75f605a 632 return;
f78c7eaf 633
634 if (!atype && !btype)
635 {
636 if (strcmp(before[FS_TYPE], "ERR") || strcmp(after[FS_TYPE], "ERR"))
637 {
f75f605a 638 com_err(whoami, 0, "Filesystem %s or %s is not AFS",
639 before[FS_NAME], after[FS_NAME]);
640 return;
f78c7eaf 641 }
642 }
643 com_err(whoami, 0, "Processing filesys %s", after[FS_NAME]);
f75f605a 644 abort_flag = 0;
645 while (1)
646 {
647 if ((rc = filesys_process(ldap_handle, dn_path, after[FS_NAME],
648 after[FS_TYPE], after[FS_PACK], LDAP_MOD_ADD)) != LDAP_NO_SUCH_OBJECT)
649 {
650 if (rc != LDAP_SUCCESS)
651 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
652 break;
653 }
654 if (abort_flag == 1)
655 break;
656 sleep(1);
657 abort_flag = 1;
658 if (rc = moira_connect())
659 {
660 critical_alert("AD incremental",
661 "Error contacting Moira server : %s",
662 error_message(rc));
663 return;
664 }
665 av[0] = after[FS_NAME];
666 call_args[0] = (char *)ldap_handle;
667 call_args[1] = dn_path;
89db421e 668 call_args[2] = "";
f75f605a 669 call_args[3] = NULL;
670 sid_base = NULL;
671 sid_ptr = &sid_base;
5b8457c5 672 callback_rc = 0;
f75f605a 673 if (rc = mr_query("get_user_account_by_login", 1, av, user_create,
674 call_args))
675 {
676 moira_disconnect();
677 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
678 break;
679 }
5b8457c5 680 if (callback_rc)
681 {
682 moira_disconnect();
683 com_err(whoami, 0, "Couldn't process filesys %s", after[FS_NAME]);
684 break;
685 }
f75f605a 686 if (sid_base != NULL)
687 {
688 sid_update(ldap_handle, dn_path);
689 linklist_free(sid_base);
690 sid_base = NULL;
691 }
692 moira_disconnect();
693 }
694
f78c7eaf 695cleanup:
f78c7eaf 696 return;
697}
89db421e 698
699#define L_LIST_DESC 9
700#define L_LIST_ID 10
701
cd9e6b16 702void do_list(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
703 char **before, int beforec, char **after, int afterc)
5d0a7127 704{
89db421e 705 int updateGroup;
909e0dc3 706 int ProcessGroup;
f75f605a 707 long rc;
89db421e 708 char group_membership[6];
709 char list_id[32];
f75f605a 710 int security_flag;
89db421e 711 char filter[128];
f75f605a 712 char group_ou[256];
89db421e 713 char before_list_id[32];
f75f605a 714 char before_group_membership[1];
715 int before_security_flag;
716 char before_group_ou[256];
f75f605a 717 LK_ENTRY *ptr = NULL;
9db0b148 718
719 if (beforec == 0 && afterc == 0)
720 return;
721
89db421e 722 memset(list_id, '\0', sizeof(list_id));
723 memset(before_list_id, '\0', sizeof(before_list_id));
724 memset(before_group_ou, '\0', sizeof(before_group_ou));
725 memset(before_group_membership, '\0', sizeof(before_group_membership));
726 memset(group_ou, '\0', sizeof(group_ou));
727 memset(group_membership, '\0', sizeof(group_membership));
728 updateGroup = 0;
729
730 if (beforec > L_GID)
731 {
732 if (beforec < L_LIST_ID)
733 return;
734 if (beforec > L_LIST_DESC)
735 {
736 strcpy(before_list_id, before[L_LIST_ID]);
737 }
f75f605a 738 before_security_flag = 0;
f75f605a 739 get_group_membership(before_group_membership, before_group_ou, &before_security_flag, before);
740 }
89db421e 741 if (afterc > L_GID)
f75f605a 742 {
89db421e 743 if (afterc < L_LIST_ID)
744 return;
745 if (afterc > L_LIST_DESC)
746 {
747 strcpy(list_id, before[L_LIST_ID]);
748 }
f75f605a 749 security_flag = 0;
f75f605a 750 get_group_membership(group_membership, group_ou, &security_flag, after);
751 }
89db421e 752
753 if ((beforec == 0) && (afterc == 0)) /*this case should never happen*/
f75f605a 754 return;
cd9e6b16 755
89db421e 756 updateGroup = 0;
757 if (beforec)
cd9e6b16 758 {
89db421e 759 updateGroup = 1;
760 if ((rc = process_group(ldap_handle, dn_path, before_list_id, before[L_NAME],
761 before_group_ou, before_group_membership,
762 before_security_flag, CHECK_GROUPS)))
763 {
764 if (rc == AD_NO_GROUPS_FOUND)
765 updateGroup = 0;
766 else
f75f605a 767 {
89db421e 768 if ((rc == AD_WRONG_GROUP_DN_FOUND) || (rc == AD_MULTIPLE_GROUPS_FOUND))
769 {
770 rc = process_group(ldap_handle, dn_path, before_list_id, before[L_NAME],
771 before_group_ou, before_group_membership,
772 before_security_flag, CLEANUP_GROUPS);
773 }
774 if ((rc != AD_NO_GROUPS_FOUND) && (rc != 0))
f75f605a 775 {
89db421e 776 com_err(whoami, 0, "Could not change list name from %s to %s",
777 before[L_NAME], after[L_NAME]);
f75f605a 778 return;
779 }
89db421e 780 if (rc == AD_NO_GROUPS_FOUND)
781 updateGroup = 0;
782 }
783 }
784 }
785
786 if ((beforec != 0) && (afterc != 0))
787 {
788 if (((strcmp(after[L_NAME], before[L_NAME])) ||
789 ((!strcmp(after[L_NAME], before[L_NAME])) &&
790 (strcmp(before_group_ou, group_ou)))) &&
791 (updateGroup == 1))
792 {
793 com_err(whoami, 0, "Changing list name from %s to %s",
794 before[L_NAME], after[L_NAME]);
795 if ((strlen(before_group_ou) == 0) || (strlen(before_group_membership) == 0) ||
796 (strlen(group_ou) == 0) || (strlen(group_membership) == 0))
797 {
798 com_err(whoami, 0, "%s", "couldn't find the group OU's");
799 return;
800 }
801 memset(filter, '\0', sizeof(filter));
802 if ((rc = group_rename(ldap_handle, dn_path,
803 before[L_NAME], before_group_membership,
804 before_group_ou, before_security_flag, before[L_LIST_DESC],
805 after[L_NAME], group_membership,
806 group_ou, security_flag, after[L_LIST_DESC],
807 list_id, filter)))
808 {
809 if (rc != AD_NO_GROUPS_FOUND)
f75f605a 810 {
89db421e 811 com_err(whoami, 0, "Could not change list name from %s to %s",
812 before[L_NAME], after[L_NAME]);
f75f605a 813 return;
814 }
89db421e 815 updateGroup = 0;
f75f605a 816 }
89db421e 817 beforec = 0;
f75f605a 818 }
819 else
89db421e 820 beforec = 0;
cd9e6b16 821 }
822
89db421e 823 if (beforec)
984c91b7 824 {
f75f605a 825 if ((strlen(before_group_ou) == 0) || (strlen(before_group_membership) == 0))
984c91b7 826 {
f75f605a 827 com_err(whoami, 0, "couldn't find the group OU for group %s", before[L_NAME]);
828 return;
829 }
984c91b7 830 com_err(whoami, 0, "Deleting group %s", before[L_NAME]);
89db421e 831 rc = group_delete(ldap_handle, dn_path, before[L_NAME],
832 before_group_membership, before_list_id);
f75f605a 833 return;
5d0a7127 834 }
89db421e 835 if (afterc)
5d0a7127 836 {
89db421e 837 if (!updateGroup)
838 {
839 com_err(whoami, 0, "Creating group %s", after[L_NAME]);
840 if (rc = process_group(ldap_handle, dn_path, list_id, after[L_NAME],
841 group_ou, group_membership,
842 security_flag, CHECK_GROUPS))
843 {
844 if (rc != AD_NO_GROUPS_FOUND)
845 {
846 if ((rc == AD_WRONG_GROUP_DN_FOUND) || (rc == AD_MULTIPLE_GROUPS_FOUND))
847 {
848 rc = process_group(ldap_handle, dn_path, list_id, after[L_NAME],
849 group_ou, group_membership,
850 security_flag, CLEANUP_GROUPS);
851 }
852 if (rc)
853 {
854 com_err(whoami, 0, "Could not create list %s", after[L_NAME]);
855 return;
856 }
857 }
858 }
859 }
860 else
861 com_err(whoami, 0, "Updating group %s information", after[L_NAME]);
cd9e6b16 862
f75f605a 863 if (rc = moira_connect())
864 {
865 critical_alert("AD incremental",
866 "Error contacting Moira server : %s",
867 error_message(rc));
868 return;
869 }
870
909e0dc3 871 ProcessGroup = 0;
872 if (ProcessAce(ldap_handle, dn_path, after[L_NAME], "LIST", 0, &ProcessGroup))
873 return;
874 if (ProcessGroup)
875 {
876 if (ProcessAce(ldap_handle, dn_path, after[L_NAME], "LIST", 1, &ProcessGroup))
877 return;
878 }
89db421e 879 if (make_new_group(ldap_handle, dn_path, list_id, after[L_NAME],
880 group_ou, group_membership, security_flag, updateGroup))
cd9e6b16 881 {
f75f605a 882 moira_disconnect();
f75f605a 883 return;
cd9e6b16 884 }
89db421e 885 if (atoi(after[L_ACTIVE]))
cd9e6b16 886 {
89db421e 887 populate_group(ldap_handle, dn_path, after[L_NAME], group_ou,
888 group_membership, security_flag, list_id);
cd9e6b16 889 }
f75f605a 890 moira_disconnect();
5d0a7127 891 }
f75f605a 892 return;
5d0a7127 893}
894
f75f605a 895#define LM_EXTRA_ACTIVE (LM_END)
896#define LM_EXTRA_PUBLIC (LM_END+1)
897#define LM_EXTRA_HIDDEN (LM_END+2)
898#define LM_EXTRA_MAILLIST (LM_END+3)
899#define LM_EXTRA_GROUP (LM_END+4)
900#define LM_EXTRA_GID (LM_END+5)
89db421e 901#define LMN_LIST_ID (LM_END+6)
902#define LM_LIST_ID (LM_END+7)
903#define LM_USER_ID (LM_END+8)
904#define LM_EXTRA_END (LM_END+9)
984c91b7 905
5d0a7127 906void do_member(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
cd9e6b16 907 char **before, int beforec, char **after, int afterc)
5d0a7127 908{
cd9e6b16 909 char group_name[128];
910 char user_name[128];
9db0b148 911 char user_type[128];
89db421e 912 char moira_list_id[32];
913 char moira_user_id[32];
f75f605a 914 char group_membership[1];
f75f605a 915 char group_ou[256];
5f7b0741 916 char machine_ou[256];
f75f605a 917 char *args[16];
918 char **ptr;
89db421e 919 char *av[7];
920 char *call_args[7];
f75f605a 921 char *pUserOu;
89db421e 922 int security_flag;
923 int rc;
909e0dc3 924 int ProcessGroup;
f75f605a 925
926 pUserOu = NULL;
927 ptr = NULL;
89db421e 928 memset(moira_list_id, '\0', sizeof(moira_list_id));
929 memset(moira_user_id, '\0', sizeof(moira_user_id));
5d0a7127 930 if (afterc)
931 {
89db421e 932 if (afterc < LM_EXTRA_GID)
f75f605a 933 return;
984c91b7 934 if (!atoi(after[LM_EXTRA_ACTIVE]))
cd9e6b16 935 return;
f75f605a 936 ptr = after;
89db421e 937 if (!strcasecmp(ptr[LM_TYPE], "LIST"))
938 return;
984c91b7 939 strcpy(user_name, after[LM_MEMBER]);
940 strcpy(group_name, after[LM_LIST]);
941 strcpy(user_type, after[LM_TYPE]);
5f7b0741 942 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
943 {
944 if (afterc > LM_EXTRA_GROUP)
945 {
f7c496a6 946 strcpy(moira_list_id, after[LMN_LIST_ID]);
947 strcpy(moira_user_id, after[LM_LIST_ID]);
5f7b0741 948 }
949 }
950 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
89db421e 951 {
952 if (afterc > LMN_LIST_ID)
953 {
954 strcpy(moira_list_id, after[LM_LIST_ID]);
955 strcpy(moira_user_id, after[LM_USER_ID]);
956 }
957 }
958 else
959 {
960 if (afterc > LM_EXTRA_GID)
961 strcpy(moira_list_id, after[LMN_LIST_ID]);
962 }
5d0a7127 963 }
964 else if (beforec)
965 {
89db421e 966 if (beforec < LM_EXTRA_GID)
f75f605a 967 return;
984c91b7 968 if (!atoi(before[LM_EXTRA_ACTIVE]))
9db0b148 969 return;
f75f605a 970 ptr = before;
89db421e 971 if (!strcasecmp(ptr[LM_TYPE], "LIST"))
972 return;
984c91b7 973 strcpy(user_name, before[LM_MEMBER]);
974 strcpy(group_name, before[LM_LIST]);
975 strcpy(user_type, before[LM_TYPE]);
5f7b0741 976 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
977 {
978 if (beforec > LM_EXTRA_GROUP)
979 {
f7c496a6 980 strcpy(moira_list_id, before[LMN_LIST_ID]);
981 strcpy(moira_user_id, before[LM_LIST_ID]);
5f7b0741 982 }
983 }
984 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
89db421e 985 {
986 if (beforec > LMN_LIST_ID)
987 {
988 strcpy(moira_list_id, before[LM_LIST_ID]);
989 strcpy(moira_user_id, before[LM_USER_ID]);
990 }
991 }
992 else
993 {
994 if (beforec > LM_EXTRA_GID)
995 strcpy(moira_list_id, before[LMN_LIST_ID]);
996 }
5d0a7127 997 }
cd9e6b16 998
f75f605a 999 if (ptr == NULL)
1000 return;
1001
1002 args[L_NAME] = ptr[LM_LIST];
1003 args[L_ACTIVE] = ptr[LM_EXTRA_ACTIVE];
1004 args[L_PUBLIC] = ptr[LM_EXTRA_PUBLIC];
1005 args[L_HIDDEN] = ptr[LM_EXTRA_HIDDEN];
1006 args[L_MAILLIST] = ptr[LM_EXTRA_MAILLIST];
1007 args[L_GROUP] = ptr[LM_EXTRA_GROUP];
1008 args[L_GID] = ptr[LM_EXTRA_GID];
1009
1010 security_flag = 0;
1011 memset(group_ou, '\0', sizeof(group_ou));
1012 get_group_membership(group_membership, group_ou, &security_flag, args);
1013 if (strlen(group_ou) == 0)
cd9e6b16 1014 {
f75f605a 1015 com_err(whoami, 0, "couldn't find the group OU for group %s", group_name);
cd9e6b16 1016 return;
1017 }
89db421e 1018 if (rc = process_group(ldap_handle, dn_path, moira_list_id, group_name, group_ou, group_membership, security_flag, CHECK_GROUPS))
1019 {
1020 if (rc != AD_NO_GROUPS_FOUND)
1021 {
1022 if (rc = process_group(ldap_handle, dn_path, moira_list_id, group_name, group_ou, group_membership, security_flag, CLEANUP_GROUPS))
1023 {
1024 if (rc != AD_NO_GROUPS_FOUND)
1025 {
1026 if (afterc)
1027 com_err(whoami, 0, "Couldn't add %s to group %s - unable to process group", user_name, group_name);
1028 else
c0bd7667 1029 com_err(whoami, 0, "Couldn't remove %s from group %s - unable to process group", user_name, group_name);
89db421e 1030 return;
1031 }
1032 }
1033 }
1034 }
1035 if (rc == AD_NO_GROUPS_FOUND)
1036 {
1037 if (rc = moira_connect())
1038 {
1039 critical_alert("AD incremental",
1040 "Error contacting Moira server : %s",
1041 error_message(rc));
1042 return;
1043 }
f75f605a 1044
89db421e 1045 com_err(whoami, 0, "creating group %s", group_name);
909e0dc3 1046 ProcessGroup = 0;
1047 if (ProcessAce(ldap_handle, dn_path, ptr[LM_LIST], "LIST", 0, &ProcessGroup))
1048 return;
1049 if (ProcessGroup)
1050 {
1051 if (ProcessAce(ldap_handle, dn_path, ptr[LM_LIST], "LIST", 1, &ProcessGroup))
1052 return;
1053 }
89db421e 1054 if (make_new_group(ldap_handle, dn_path, moira_list_id, ptr[LM_LIST],
1055 group_ou, group_membership, security_flag, 0))
1056 {
1057 moira_disconnect();
1058 return;
1059 }
1060 if (atoi(ptr[LM_EXTRA_ACTIVE]))
1061 {
1062 populate_group(ldap_handle, dn_path, ptr[LM_LIST], group_ou,
1063 group_membership, security_flag, moira_list_id);
1064 }
1065 moira_disconnect();
1066 }
f75f605a 1067 rc = 0;
1068 if (beforec)
1069 {
89db421e 1070 com_err(whoami, 0, "removing user %s from list %s", user_name, group_name);
f75f605a 1071 pUserOu = user_ou;
5f7b0741 1072 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1073 {
1074 memset(machine_ou, '\0', sizeof(machine_ou));
1075 if (get_machine_ou(ldap_handle, dn_path, ptr[LM_MEMBER], machine_ou))
1076 return;
1077 pUserOu = machine_ou;
1078 }
f75f605a 1079 if (!strcasecmp(ptr[LM_TYPE], "STRING"))
cd9e6b16 1080 {
f75f605a 1081 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER], contact_ou))
1082 return;
1083 pUserOu = contact_ou;
1084 }
1085 else if (!strcasecmp(ptr[LM_TYPE], "KERBEROS"))
1086 {
1087 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER], kerberos_ou))
1088 return;
1089 pUserOu = kerberos_ou;
1090 }
89db421e 1091 if (rc = member_remove(ldap_handle, dn_path, group_name,
1092 group_ou, group_membership, ptr[LM_MEMBER],
1093 pUserOu, moira_list_id))
c0bd7667 1094 com_err(whoami, 0, "couldn't remove %s from group %s", user_name, group_name);
89db421e 1095 return;
f75f605a 1096 }
89db421e 1097
1098 com_err(whoami, 0, "Adding %s to list %s", user_name, group_name);
1099 pUserOu = user_ou;
5f7b0741 1100
1101 if (!strcasecmp(ptr[LM_TYPE], "MACHINE"))
1102 {
1103 memset(machine_ou, '\0', sizeof(machine_ou));
1104 if (get_machine_ou(ldap_handle, dn_path, ptr[LM_MEMBER], machine_ou))
1105 return;
1106 pUserOu = machine_ou;
1107 }
1108 else if (!strcasecmp(ptr[LM_TYPE], "STRING"))
f75f605a 1109 {
89db421e 1110 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER], contact_ou))
f75f605a 1111 return;
89db421e 1112 pUserOu = contact_ou;
1113 }
1114 else if (!strcasecmp(ptr[LM_TYPE], "KERBEROS"))
1115 {
1116 if (contact_create(ldap_handle, dn_path, ptr[LM_MEMBER], kerberos_ou))
1117 return;
1118 pUserOu = kerberos_ou;
1119 }
1120 else if (!strcasecmp(ptr[LM_TYPE], "USER"))
1121 {
1122 if ((rc = check_user(ldap_handle, dn_path, ptr[LM_MEMBER],
1123 moira_user_id)) == AD_NO_USER_FOUND)
f75f605a 1124 {
89db421e 1125 if (rc = moira_connect())
1126 {
1127 critical_alert("AD incremental",
1128 "Error connection to Moira : %s",
1129 error_message(rc));
1130 return;
1131 }
1132 com_err(whoami, 0, "creating user %s", after[U_NAME]);
1133 av[0] = ptr[LM_MEMBER];
1134 call_args[0] = (char *)ldap_handle;
1135 call_args[1] = dn_path;
1136 call_args[2] = moira_user_id;
1137 call_args[3] = NULL;
1138 sid_base = NULL;
1139 sid_ptr = &sid_base;
1140 callback_rc = 0;
1141 if (rc = mr_query("get_user_account_by_login", 1, av, user_create,
1142 call_args))
1143 {
1144 moira_disconnect();
1145 com_err(whoami, 0, "couldn't create user %s : %s",
1146 ptr[LM_MEMBER], error_message(rc));
1147 return;
1148 }
1149 if (callback_rc)
1150 {
1151 moira_disconnect();
1152 com_err(whoami, 0, "couldn't create user %s", ptr[LM_MEMBER]);
1153 return;
1154 }
1155 sleep(1);
1156 if (sid_base != NULL)
1157 {
1158 sid_update(ldap_handle, dn_path);
1159 linklist_free(sid_base);
1160 }
f75f605a 1161 }
89db421e 1162 else
f75f605a 1163 {
89db421e 1164 if (rc != 0)
f75f605a 1165 return;
cd9e6b16 1166 }
89db421e 1167 pUserOu = user_ou;
cd9e6b16 1168 }
89db421e 1169
1170 if (rc = member_add(ldap_handle, dn_path, group_name,
1171 group_ou, group_membership, ptr[LM_MEMBER],
1172 pUserOu, moira_list_id))
cd9e6b16 1173 {
89db421e 1174 com_err(whoami, 0, "couldn't add %s to group %s", user_name, group_name);
f75f605a 1175 }
1176 return;
5d0a7127 1177}
1178
cd9e6b16 1179
89db421e 1180#define U_USER_ID 10
1181
f78c7eaf 1182void do_user(LDAP *ldap_handle, char *dn_path, char *ldap_hostname,
1183 char **before, int beforec, char **after,
cd9e6b16 1184 int afterc)
5d0a7127 1185{
984c91b7 1186 int rc;
89db421e 1187 char *av[7];
1188 char after_user_id[32];
1189 char before_user_id[32];
1190 char *call_args[7];
984c91b7 1191
5b8457c5 1192 if ((beforec == 0) && (afterc == 0))
984c91b7 1193 return;
1194
89db421e 1195 memset(after_user_id, '\0', sizeof(after_user_id));
1196 memset(before_user_id, '\0', sizeof(before_user_id));
1197 if (beforec > U_USER_ID)
1198 strcpy(before_user_id, before[U_USER_ID]);
1199 if (afterc > U_USER_ID)
1200 strcpy(after_user_id, after[U_USER_ID]);
984c91b7 1201
89db421e 1202 if ((beforec == 0) && (afterc == 0)) /*this case should never happen */
984c91b7 1203 return;
cd9e6b16 1204
89db421e 1205 if ((beforec == 0) && (afterc != 0)) /*this case only happens when the account*/
1206 return; /*account is first created but not usable*/
f75f605a 1207
89db421e 1208 if ((beforec != 0) && (afterc == 0)) /*this case only happens when the account*/
1209 { /*is expunged*/
1210 if (atoi(before[U_STATE]) == 0)
cd9e6b16 1211 {
89db421e 1212 com_err(whoami, 0, "expunging user %s from AD", before[U_NAME]);
1213 user_delete(ldap_handle, dn_path, before[U_NAME], before_user_id);
cd9e6b16 1214 }
f75f605a 1215 return;
5d0a7127 1216 }
f75f605a 1217
89db421e 1218 /*process anything that gets here*/
c0bd7667 1219 if ((rc = check_user(ldap_handle, dn_path, before[U_NAME],
1220 before_user_id)) == AD_NO_USER_FOUND)
5d0a7127 1221 {
6c8f12af 1222 if (!check_string(after[U_NAME]))
1223 return;
f75f605a 1224 if (rc = moira_connect())
1225 {
1226 critical_alert("AD incremental",
1227 "Error connection to Moira : %s",
1228 error_message(rc));
1229 return;
1230 }
89db421e 1231 com_err(whoami, 0, "creating user %s", after[U_NAME]);
5d0a7127 1232
984c91b7 1233 av[0] = after[U_NAME];
cd9e6b16 1234 call_args[0] = (char *)ldap_handle;
1235 call_args[1] = dn_path;
89db421e 1236 call_args[2] = after_user_id;
9db0b148 1237 call_args[3] = NULL;
cd9e6b16 1238 sid_base = NULL;
1239 sid_ptr = &sid_base;
5b8457c5 1240 callback_rc = 0;
cd9e6b16 1241 if (rc = mr_query("get_user_account_by_login", 1, av, user_create,
1242 call_args))
1243 {
f75f605a 1244 moira_disconnect();
89db421e 1245 com_err(whoami, 0, "couldn't create user %s : %s",
f75f605a 1246 after[U_NAME], error_message(rc));
1247 return;
cd9e6b16 1248 }
5b8457c5 1249 if (callback_rc)
1250 {
1251 moira_disconnect();
89db421e 1252 com_err(whoami, 0, "couldn't create user %s", after[U_NAME]);
5b8457c5 1253 return;
1254 }
f75f605a 1255 sleep(1);
cd9e6b16 1256 if (sid_base != NULL)
1257 {
1258 sid_update(ldap_handle, dn_path);
1259 linklist_free(sid_base);
1260 }
89db421e 1261 return;
1262 }
1263 else
1264 {
1265 if (rc != 0)
1266 return;
1267 }
1268 if (strcmp(before[U_NAME], after[U_NAME]))
1269 {
1270 if ((check_string(before[U_NAME])) && (check_string(after[U_NAME])))
f75f605a 1271 {
89db421e 1272 com_err(whoami, 0, "changing user %s to %s",
1273 before[U_NAME], after[U_NAME]);
1274 if ((rc = user_rename(ldap_handle, dn_path, before[U_NAME],
1275 after[U_NAME])) != LDAP_SUCCESS)
f75f605a 1276 {
89db421e 1277 return;
f75f605a 1278 }
1279 }
cd9e6b16 1280 }
89db421e 1281 com_err(whoami, 0, "updating user %s information", after[U_NAME]);
1282 rc = user_update(ldap_handle, dn_path, after[U_NAME],
1283 after[U_UID], after[U_MITID],
1284 after_user_id, atoi(after[U_STATE]));
f75f605a 1285 return;
5d0a7127 1286}
1287
1288int construct_newvalues(LK_ENTRY *linklist_base, int modvalue_count,
cd9e6b16 1289 char *oldValue, char *newValue,
1290 char ***modvalues, int type)
5d0a7127 1291{
cd9e6b16 1292 LK_ENTRY *linklist_ptr;
1293 int i;
1294 char *cPtr;
5d0a7127 1295
cd9e6b16 1296 if (((*modvalues) = calloc(1, (modvalue_count + 1) * sizeof(char *)))
1297 == NULL)
1298 {
1299 return(1);
1300 }
5d0a7127 1301 for (i = 0; i < (modvalue_count + 1); i++)
cd9e6b16 1302 (*modvalues)[i] = NULL;
5d0a7127 1303 if (modvalue_count != 0)
1304 {
1305 linklist_ptr = linklist_base;
1306 for (i = 0; i < modvalue_count; i++)
cd9e6b16 1307 {
1308 if ((oldValue != NULL) && (newValue != NULL))
1309 {
1310 if ((cPtr = (char *)strstr(linklist_ptr->value, oldValue))
1311 != (char *)NULL)
1312 {
1313 if (type == REPLACE)
1314 {
1315 if (((*modvalues)[i] = calloc(1, strlen(newValue) + 1))
1316 == NULL)
1317 return(1);
1318 memset((*modvalues)[i], '\0', strlen(newValue) + 1);
1319 strcpy((*modvalues)[i], newValue);
1320 }
1321 else
1322 {
1323 if (((*modvalues)[i] = calloc(1,
1324 (int)(cPtr - linklist_ptr->value) +
1325 (linklist_ptr->length - strlen(oldValue)) +
1326 strlen(newValue) + 1)) == NULL)
1327 return(1);
1328 memset((*modvalues)[i], '\0',
1329 (int)(cPtr - linklist_ptr->value) +
1330 (linklist_ptr->length - strlen(oldValue)) +
1331 strlen(newValue) + 1);
1332 memcpy((*modvalues)[i], linklist_ptr->value,
1333 (int)(cPtr - linklist_ptr->value));
1334 strcat((*modvalues)[i], newValue);
1335 strcat((*modvalues)[i],
1336 &linklist_ptr->value[(int)(cPtr - linklist_ptr->value) + strlen(oldValue)]);
1337 }
1338 }
1339 else
1340 {
1341 (*modvalues)[i] = calloc(1, linklist_ptr->length + 1);
1342 memset((*modvalues)[i], '\0', linklist_ptr->length + 1);
1343 memcpy((*modvalues)[i], linklist_ptr->value,
1344 linklist_ptr->length);
1345 }
1346 }
1347 else
1348 {
1349 (*modvalues)[i] = calloc(1, linklist_ptr->length + 1);
1350 memset((*modvalues)[i], '\0', linklist_ptr->length + 1);
1351 memcpy((*modvalues)[i], linklist_ptr->value,
1352 linklist_ptr->length);
1353 }
1354 linklist_ptr = linklist_ptr->next;
1355 }
1356 (*modvalues)[i] = NULL;
5d0a7127 1357 }
1358 return(0);
1359}
1360
cd9e6b16 1361
5d0a7127 1362int linklist_build(LDAP *ldap_handle, char *dn_path, char *search_exp,
cd9e6b16 1363 char **attr_array, LK_ENTRY **linklist_base,
1364 int *linklist_count)
5d0a7127 1365{
cd9e6b16 1366 ULONG rc;
5d0a7127 1367 LDAPMessage *ldap_entry;
cd9e6b16 1368
1369 rc = 0;
5d0a7127 1370 ldap_entry = NULL;
1371 (*linklist_base) = NULL;
1372 (*linklist_count) = 0;
1373 if ((rc = ldap_search_s(ldap_handle, dn_path, LDAP_SCOPE_SUBTREE,
cd9e6b16 1374 search_exp, attr_array, 0, &ldap_entry))
5d0a7127 1375 != LDAP_SUCCESS)
6c8f12af 1376 {
1377 if (rc != LDAP_SIZELIMIT_EXCEEDED)
1378 return(0);
1379 }
1380
cd9e6b16 1381 rc = retrieve_entries(ldap_handle, ldap_entry, linklist_base, linklist_count);
1382
5d0a7127 1383 ldap_msgfree(ldap_entry);
1384 return(rc);
1385}
1386
cd9e6b16 1387
5d0a7127 1388int retrieve_entries(LDAP *ldap_handle, LDAPMessage *ldap_entry,
cd9e6b16 1389 LK_ENTRY **linklist_base, int *linklist_count)
5d0a7127 1390{
cd9e6b16 1391 char distinguished_name[1024];
1392 LK_ENTRY *linklist_ptr;
1393 int rc;
1394
5d0a7127 1395 if ((ldap_entry = ldap_first_entry(ldap_handle, ldap_entry)) == NULL)
1396 return(0);
cd9e6b16 1397
1398 memset(distinguished_name, '\0', sizeof(distinguished_name));
1399 get_distinguished_name(ldap_handle, ldap_entry, distinguished_name);
1400
1401 if ((rc = retrieve_attributes(ldap_handle, ldap_entry, distinguished_name,
1402 linklist_base)) != 0)
5d0a7127 1403 return(rc);
cd9e6b16 1404
5d0a7127 1405 while ((ldap_entry = ldap_next_entry(ldap_handle, ldap_entry)) != NULL)
1406 {
cd9e6b16 1407 memset(distinguished_name, '\0', sizeof(distinguished_name));
1408 get_distinguished_name(ldap_handle, ldap_entry, distinguished_name);
1409
1410 if ((rc = retrieve_attributes(ldap_handle, ldap_entry, distinguished_name,
1411 linklist_base)) != 0)
1412 return(rc);
5d0a7127 1413 }
cd9e6b16 1414
5d0a7127 1415 linklist_ptr = (*linklist_base);
1416 (*linklist_count) = 0;
1417 while (linklist_ptr != NULL)
1418 {
1419 ++(*linklist_count);
1420 linklist_ptr = linklist_ptr->next;
1421 }
1422 return(0);
1423}
1424
1425int retrieve_attributes(LDAP *ldap_handle, LDAPMessage *ldap_entry,
cd9e6b16 1426 char *distinguished_name, LK_ENTRY **linklist_current)
5d0a7127 1427{
cd9e6b16 1428 char *Attribute;
1429 BerElement *ptr;
1430
5d0a7127 1431 ptr = NULL;
cd9e6b16 1432 if ((Attribute = ldap_first_attribute(ldap_handle, ldap_entry, &ptr)) != NULL)
5d0a7127 1433 {
cd9e6b16 1434 retrieve_values(ldap_handle, ldap_entry, Attribute, distinguished_name,
1435 linklist_current);
5d0a7127 1436 ldap_memfree(Attribute);
cd9e6b16 1437 while ((Attribute = ldap_next_attribute(ldap_handle, ldap_entry,
1438 ptr)) != NULL)
1439 {
1440 retrieve_values(ldap_handle, ldap_entry, Attribute,
1441 distinguished_name, linklist_current);
1442 ldap_memfree(Attribute);
1443 }
5d0a7127 1444 }
cd9e6b16 1445 ldap_ber_free(ptr, 0);
5d0a7127 1446 return(0);
1447}
1448
cd9e6b16 1449int retrieve_values(LDAP *ldap_handle, LDAPMessage *ldap_entry,
1450 char *Attribute, char *distinguished_name,
1451 LK_ENTRY **linklist_current)
5d0a7127 1452{
cd9e6b16 1453 char **str_value;
1454 char temp[256];
1455 void **Ptr;
1456 int use_bervalue;
1457 LK_ENTRY *linklist_previous;
5d0a7127 1458 LDAP_BERVAL **ber_value;
cd9e6b16 1459 DWORD ber_length;
5d0a7127 1460#ifdef LDAP_DEBUG
cd9e6b16 1461 SID *sid;
1462 GUID *guid;
1463 int i;
1464 int intValue;
1465 DWORD *subauth;
1466 SID_IDENTIFIER_AUTHORITY *sid_auth;
1467 unsigned char *subauth_count;
1468#endif /*LDAP_BEGUG*/
5d0a7127 1469
1470 use_bervalue = 0;
1471 memset(temp, '\0', sizeof(temp));
1472 if ((!strcmp(Attribute, "objectSid")) ||
1473 (!strcmp(Attribute, "objectGUID")))
1474 use_bervalue = 1;
cd9e6b16 1475
5d0a7127 1476 if (use_bervalue)
1477 {
1478 ber_value = ldap_get_values_len(ldap_handle, ldap_entry, Attribute);
1479 Ptr = (void **)ber_value;
1480 str_value = NULL;
cd9e6b16 1481 }
5d0a7127 1482 else
1483 {
1484 str_value = ldap_get_values(ldap_handle, ldap_entry, Attribute);
1485 Ptr = (void **)str_value;
1486 ber_value = NULL;
1487 }
1488 if (Ptr != NULL)
1489 {
1490 for (; *Ptr; Ptr++)
cd9e6b16 1491 {
1492 if ((linklist_previous = calloc(1, sizeof(LK_ENTRY))) == NULL)
1493 return(1);
1494 memset(linklist_previous, '\0', sizeof(LK_ENTRY));
1495 linklist_previous->next = (*linklist_current);
1496 (*linklist_current) = linklist_previous;
1497
1498 if (((*linklist_current)->attribute = calloc(1,
1499 strlen(Attribute) + 1)) == NULL)
1500 return(1);
1501 memset((*linklist_current)->attribute, '\0', strlen(Attribute) + 1);
1502 strcpy((*linklist_current)->attribute, Attribute);
1503 if (use_bervalue)
1504 {
1505 ber_length = (*(LDAP_BERVAL **)Ptr)->bv_len;
1506 if (((*linklist_current)->value = calloc(1, ber_length)) == NULL)
1507 return(1);
1508 memset((*linklist_current)->value, '\0', ber_length);
1509 memcpy((*linklist_current)->value, (*(LDAP_BERVAL **)Ptr)->bv_val,
1510 ber_length);
1511 (*linklist_current)->length = ber_length;
1512 }
1513 else
1514 {
1515 if (((*linklist_current)->value = calloc(1,
1516 strlen(*Ptr) + 1)) == NULL)
1517 return(1);
1518 memset((*linklist_current)->value, '\0', strlen(*Ptr) + 1);
1519 (*linklist_current)->length = strlen(*Ptr);
1520 strcpy((*linklist_current)->value, *Ptr);
1521 }
1522 (*linklist_current)->ber_value = use_bervalue;
1523 if (((*linklist_current)->dn = calloc(1,
1524 strlen(distinguished_name) + 1)) == NULL)
1525 return(1);
1526 memset((*linklist_current)->dn, '\0', strlen(distinguished_name) + 1);
1527 strcpy((*linklist_current)->dn, distinguished_name);
1528
5d0a7127 1529#ifdef LDAP_DEBUG
cd9e6b16 1530 if (!strcmp(Attribute, "objectGUID"))
1531 {
1532 guid = (GUID *)((*linklist_current)->value);
1533 sprintf(temp, "%08x-%04x-%04x-%02x%02x-%02x%02x%02x%02x%02x%02x",
1534 guid->Data1, guid->Data2, guid->Data3,
1535 guid->Data4[0], guid->Data4[1], guid->Data4[2],
1536 guid->Data4[3], guid->Data4[4], guid->Data4[5],
1537 guid->Data4[6], guid->Data4[7]);
1538 print_to_screen(" %20s : {%s}\n", Attribute, temp);
1539 }
1540 else if (!strcmp(Attribute, "objectSid"))
1541 {
1542 sid = (SID *)((*(LDAP_BERVAL **)Ptr)->bv_val);
5d0a7127 1543#ifdef _WIN32
cd9e6b16 1544 print_to_screen(" Revision = %d\n", sid->Revision);
1545 print_to_screen(" SID Identifier Authority:\n");
1546 sid_auth = &sid->IdentifierAuthority;
1547 if (sid_auth->Value[0])
1548 print_to_screen(" SECURITY_NULL_SID_AUTHORITY\n");
1549 else if (sid_auth->Value[1])
1550 print_to_screen(" SECURITY_WORLD_SID_AUTHORITY\n");
1551 else if (sid_auth->Value[2])
1552 print_to_screen(" SECURITY_LOCAL_SID_AUTHORITY\n");
1553 else if (sid_auth->Value[3])
1554 print_to_screen(" SECURITY_CREATOR_SID_AUTHORITY\n");
1555 else if (sid_auth->Value[5])
1556 print_to_screen(" SECURITY_NT_AUTHORITY\n");
1557 else
1558 print_to_screen(" UNKNOWN SID AUTHORITY\n");
1559 subauth_count = GetSidSubAuthorityCount(sid);
1560 print_to_screen(" SidSubAuthorityCount = %d\n",
1561 *subauth_count);
1562 print_to_screen(" SidSubAuthority:\n");
1563 for (i = 0; i < *subauth_count; i++)
1564 {
1565 if ((subauth = GetSidSubAuthority(sid, i)) != NULL)
1566 print_to_screen(" %u\n", *subauth);
1567 }
5d0a7127 1568#endif
cd9e6b16 1569 }
1570 else if ((!memcmp(Attribute, "userAccountControl",
1571 strlen("userAccountControl"))) ||
1572 (!memcmp(Attribute, "sAMAccountType",
1573 strlen("sAmAccountType"))))
1574 {
1575 intValue = atoi(*Ptr);
1576 print_to_screen(" %20s : %ld\n",Attribute, intValue);
1577 if (!memcmp(Attribute, "userAccountControl",
1578 strlen("userAccountControl")))
1579 {
1580 if (intValue & UF_ACCOUNTDISABLE)
1581 print_to_screen(" %20s : %s\n",
1582 "", "Account disabled");
1583 else
1584 print_to_screen(" %20s : %s\n",
1585 "", "Account active");
1586 if (intValue & UF_HOMEDIR_REQUIRED)
1587 print_to_screen(" %20s : %s\n",
1588 "", "Home directory required");
1589 if (intValue & UF_LOCKOUT)
1590 print_to_screen(" %20s : %s\n",
1591 "", "Account locked out");
1592 if (intValue & UF_PASSWD_NOTREQD)
1593 print_to_screen(" %20s : %s\n",
1594 "", "No password required");
1595 if (intValue & UF_PASSWD_CANT_CHANGE)
1596 print_to_screen(" %20s : %s\n",
1597 "", "Cannot change password");
1598 if (intValue & UF_TEMP_DUPLICATE_ACCOUNT)
1599 print_to_screen(" %20s : %s\n",
1600 "", "Temp duplicate account");
1601 if (intValue & UF_NORMAL_ACCOUNT)
1602 print_to_screen(" %20s : %s\n",
1603 "", "Normal account");
1604 if (intValue & UF_INTERDOMAIN_TRUST_ACCOUNT)
1605 print_to_screen(" %20s : %s\n",
1606 "", "Interdomain trust account");
1607 if (intValue & UF_WORKSTATION_TRUST_ACCOUNT)
1608 print_to_screen(" %20s : %s\n",
1609 "", "Workstation trust account");
1610 if (intValue & UF_SERVER_TRUST_ACCOUNT)
1611 print_to_screen(" %20s : %s\n",
1612 "", "Server trust account");
1613 }
1614 }
1615 else
1616 {
1617 print_to_screen(" %20s : %s\n",Attribute, *Ptr);
1618 }
5d0a7127 1619#endif /*LDAP_DEBUG*/
cd9e6b16 1620 }
5d0a7127 1621 if (str_value != NULL)
cd9e6b16 1622 ldap_value_free(str_value);
5d0a7127 1623 if (ber_value != NULL)
cd9e6b16 1624 ldap_value_free_len(ber_value);
5d0a7127 1625 }
1626 (*linklist_current) = linklist_previous;
1627 return(0);
1628}
1629
5d0a7127 1630int moira_connect(void)
1631{
cd9e6b16 1632 long rc;
1633 char HostName[64];
1634
5d0a7127 1635 if (!mr_connections++)
1636 {
1637#ifdef _WIN32
1638 memset(HostName, '\0', sizeof(HostName));
1639 strcpy(HostName, "ttsp");
cd9e6b16 1640 rc = mr_connect_cl(HostName, "winad.incr", QUERY_VERSION, 1);
1641/*det
5d0a7127 1642 rc = mr_connect(HostName);
cd9e6b16 1643*/
5d0a7127 1644#else
1645 struct utsname uts;
1646 uname(&uts);
cd9e6b16 1647 rc = mr_connect_cl(uts.nodename, "winad.incr", QUERY_VERSION, 1);
1648/*
5d0a7127 1649 rc = mr_connect(uts.nodename);
cd9e6b16 1650*/
5d0a7127 1651#endif /*WIN32*/
cd9e6b16 1652/*det
5d0a7127 1653 if (!rc)
cd9e6b16 1654 rc = mr_auth("winad.incr");
1655*/
5d0a7127 1656 return rc;
1657 }
1658 return 0;
1659}
1660
0d958b3c 1661void check_winad(void)
1662{
1663 int i;
1664
1665 for (i = 0; file_exists(STOP_FILE); i++)
1666 {
1667 if (i > 30)
1668 {
f75f605a 1669 critical_alert("AD incremental",
f78c7eaf 1670 "WINAD incremental failed (%s exists): %s",
1671 STOP_FILE, tbl_buf);
1672 exit(1);
1673 }
0d958b3c 1674 sleep(60);
1675 }
1676}
1677
5d0a7127 1678int moira_disconnect(void)
1679{
5d0a7127 1680
cd9e6b16 1681 if (!--mr_connections)
5d0a7127 1682 {
cd9e6b16 1683 mr_disconnect();
5d0a7127 1684 }
cd9e6b16 1685 return 0;
5d0a7127 1686}
1687
5d0a7127 1688void get_distinguished_name(LDAP *ldap_handle, LDAPMessage *ldap_entry,
cd9e6b16 1689 char *distinguished_name)
5d0a7127 1690{
cd9e6b16 1691 char *CName;
1692
5d0a7127 1693 CName = ldap_get_dn(ldap_handle, ldap_entry);
1694 if (CName == NULL)
1695 return;
1696 strcpy(distinguished_name, CName);
1697 ldap_memfree(CName);
1698}
1699
1700int linklist_create_entry(char *attribute, char *value,
cd9e6b16 1701 LK_ENTRY **linklist_entry)
5d0a7127 1702{
1703 (*linklist_entry) = calloc(1, sizeof(LK_ENTRY));
1704 if (!(*linklist_entry))
1705 {
1706 return(1);
1707 }
1708 memset((*linklist_entry), '\0', sizeof(LK_ENTRY));
1709 (*linklist_entry)->attribute = calloc(1, strlen(attribute) + 1);
1710 memset((*linklist_entry)->attribute, '\0', strlen(attribute) + 1);
1711 strcpy((*linklist_entry)->attribute, attribute);
1712 (*linklist_entry)->value = calloc(1, strlen(value) + 1);
1713 memset((*linklist_entry)->value, '\0', strlen(value) + 1);
1714 strcpy((*linklist_entry)->value, value);
1715 (*linklist_entry)->length = strlen(value);
1716 (*linklist_entry)->next = NULL;
1717 return(0);
1718}
1719
1720void print_to_screen(const char *fmt, ...)
1721{
1722 va_list pvar;
cd9e6b16 1723
5d0a7127 1724 va_start(pvar, fmt);
1725 vfprintf(stderr, fmt, pvar);
1726 fflush(stderr);
1727 va_end(pvar);
1728}
cd9e6b16 1729
1730int get_group_membership(char *group_membership, char *group_ou,
1731 int *security_flag, char **av)
1732{
1733 int maillist_flag;
1734 int group_flag;
1735
1736 maillist_flag = atoi(av[L_MAILLIST]);
1737 group_flag = atoi(av[L_GROUP]);
1738 if (security_flag != NULL)
1739 (*security_flag) = 0;
1740
1741 if ((maillist_flag) && (group_flag))
1742 {
1743 if (group_membership != NULL)
1744 group_membership[0] = 'B';
1745 if (security_flag != NULL)
1746 (*security_flag) = 1;
1747 if (group_ou != NULL)
1748 strcpy(group_ou, group_ou_both);
1749 }
1750 else if ((!maillist_flag) && (group_flag))
1751 {
1752 if (group_membership != NULL)
1753 group_membership[0] = 'S';
1754 if (security_flag != NULL)
1755 (*security_flag) = 1;
1756 if (group_ou != NULL)
1757 strcpy(group_ou, group_ou_security);
1758 }
1759 else if ((maillist_flag) && (!group_flag))
1760 {
1761 if (group_membership != NULL)
1762 group_membership[0] = 'D';
1763 if (group_ou != NULL)
1764 strcpy(group_ou, group_ou_distribution);
1765 }
1766 else
1767 {
1768 if (group_membership != NULL)
1769 group_membership[0] = 'N';
1770 if (group_ou != NULL)
1771 strcpy(group_ou, group_ou_neither);
1772 }
1773 return(0);
1774}
1775
f75f605a 1776int group_rename(LDAP *ldap_handle, char *dn_path,
1777 char *before_group_name, char *before_group_membership,
5a775f54 1778 char *before_group_ou, int before_security_flag, char *before_desc,
f75f605a 1779 char *after_group_name, char *after_group_membership,
89db421e 1780 char *after_group_ou, int after_security_flag, char *after_desc,
1781 char *MoiraId, char *filter)
9db0b148 1782{
1783 LDAPMod *mods[20];
1784 char old_dn[512];
1785 char new_dn[512];
78af4e6e 1786 char new_dn_path[512];
78af4e6e 1787 char sam_name[256];
9db0b148 1788 char *attr_array[3];
89db421e 1789 char *mitMoiraId_v[] = {NULL, NULL};
9db0b148 1790 char *name_v[] = {NULL, NULL};
5a775f54 1791 char *desc_v[] = {NULL, NULL};
78af4e6e 1792 char *samAccountName_v[] = {NULL, NULL};
c76c595a 1793 char *groupTypeControl_v[] = {NULL, NULL};
1794 u_int groupTypeControl = ADS_GROUP_TYPE_GLOBAL_GROUP;
1795 char groupTypeControlStr[80];
9db0b148 1796 int n;
1797 int i;
1798 int rc;
9db0b148 1799 LK_ENTRY *group_base;
1800 int group_count;
9db0b148 1801
f75f605a 1802 if (!check_string(before_group_name))
78af4e6e 1803 {
f75f605a 1804 com_err(whoami, 0, "invalid LDAP list name %s", before_group_name);
89db421e 1805 return(AD_INVALID_NAME);
78af4e6e 1806 }
f75f605a 1807 if (!check_string(after_group_name))
78af4e6e 1808 {
f75f605a 1809 com_err(whoami, 0, "invalid LDAP list name %s", after_group_name);
89db421e 1810 return(AD_INVALID_NAME);
1811 }
1812
1813 group_count = 0;
1814 group_base = NULL;
1815 if (rc = ad_get_group(ldap_handle, dn_path, before_group_name,
1816 before_group_membership,
1817 MoiraId, "distinguishedName", &group_base,
1818 &group_count, filter))
1819 return(rc);
1820
1821 if (group_count == 0)
1822 {
1823 return(AD_NO_GROUPS_FOUND);
1824 }
1825 if (group_count != 1)
1826 {
1827 com_err(whoami, 0,
1828 "multiple groups with MoiraId = %s exist in the AD",
1829 MoiraId);
1830 return(AD_MULTIPLE_GROUPS_FOUND);
78af4e6e 1831 }
89db421e 1832 strcpy(old_dn, group_base->value);
78af4e6e 1833
89db421e 1834 linklist_free(group_base);
1835 group_base = NULL;
1836 group_count = 0;
1837 attr_array[0] = "sAMAccountName";
9db0b148 1838 attr_array[1] = NULL;
89db421e 1839 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
9db0b148 1840 &group_base, &group_count)) != 0)
1841 {
f75f605a 1842 com_err(whoami, 0, "LDAP server unable to get list %s dn : %s",
1843 after_group_name, ldap_err2string(rc));
1844 return(rc);
9db0b148 1845 }
1846 if (group_count != 1)
1847 {
89db421e 1848 com_err(whoami, 0,
1849 "Unable to get sAMAccountName for group %s",
1850 before_group_name);
1851 return(AD_LDAP_FAILURE);
9db0b148 1852 }
89db421e 1853
1854 strcpy(sam_name, group_base->value);
9db0b148 1855 linklist_free(group_base);
1856 group_base = NULL;
1857 group_count = 0;
1858
f75f605a 1859 sprintf(new_dn_path, "%s,%s", after_group_ou, dn_path);
1860 sprintf(new_dn, "cn=%s", after_group_name);
1861 if ((rc = ldap_rename_s(ldap_handle, old_dn, new_dn, new_dn_path,
78af4e6e 1862 TRUE, NULL, NULL)) != LDAP_SUCCESS)
1863 {
f75f605a 1864 com_err(whoami, 0, "Couldn't rename list from %s to %s : %s",
89db421e 1865 before_group_name, after_group_name, ldap_err2string(rc));
f75f605a 1866 return(rc);
78af4e6e 1867 }
9db0b148 1868
f75f605a 1869 name_v[0] = after_group_name;
c0bd7667 1870 if (!strncmp(&sam_name[strlen(sam_name) - strlen("_group")], "_group", strlen("_group")))
89db421e 1871 {
1872 sprintf(sam_name, "%s_group", after_group_name);
1873 }
1874 else
1875 {
1876 com_err(whoami, 0, "Couldn't rename list from %s to %s : sAMAccountName not found",
1877 before_group_name, after_group_name);
1878 return(rc);
1879 }
78af4e6e 1880 samAccountName_v[0] = sam_name;
c76c595a 1881 if (after_security_flag)
1882 groupTypeControl |= ADS_GROUP_TYPE_SECURITY_ENABLED;
1883 sprintf(groupTypeControlStr, "%ld", groupTypeControl);
1884 groupTypeControl_v[0] = groupTypeControlStr;
9db0b148 1885 n = 0;
5a775f54 1886 ADD_ATTR("samAccountName", samAccountName_v, LDAP_MOD_REPLACE);
9db0b148 1887 ADD_ATTR("displayName", name_v, LDAP_MOD_REPLACE);
89db421e 1888 desc_v[0] = after_desc;
5a775f54 1889 if (strlen(after_desc) == 0)
1890 desc_v[0] = NULL;
1891 ADD_ATTR("description", desc_v, LDAP_MOD_REPLACE);
89db421e 1892 mitMoiraId_v[0] = MoiraId;
1893 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
c76c595a 1894 ADD_ATTR("groupType", groupTypeControl_v, LDAP_MOD_REPLACE);
9db0b148 1895 mods[n] = NULL;
f75f605a 1896 sprintf(new_dn, "cn=%s,%s,%s", after_group_name, after_group_ou, dn_path);
1897 if ((rc = ldap_modify_s(ldap_handle, new_dn, mods)) != LDAP_SUCCESS)
78af4e6e 1898 {
f75f605a 1899 com_err(whoami, 0, "After renaming, couldn't modify list data for %s : %s",
1900 after_group_name, ldap_err2string(rc));
78af4e6e 1901 }
9db0b148 1902 for (i = 0; i < n; i++)
1903 free(mods[i]);
f75f605a 1904 return(rc);
9db0b148 1905}
1906
cd9e6b16 1907int group_create(int ac, char **av, void *ptr)
1908{
1909 LDAPMod *mods[20];
5b8457c5 1910 LK_ENTRY *group_base;
cd9e6b16 1911 char new_dn[256];
1912 char group_ou[256];
1913 char new_group_name[256];
1914 char sam_group_name[256];
1915 char cn_group_name[256];
1916 char *cn_v[] = {NULL, NULL};
1917 char *objectClass_v[] = {"top", "group", NULL};
1918 char info[256];
1919 char *samAccountName_v[] = {NULL, NULL};
cd9e6b16 1920 char *altSecurityIdentities_v[] = {NULL, NULL};
89db421e 1921 char *member_v[] = {NULL, NULL};
cd9e6b16 1922 char *name_v[] = {NULL, NULL};
1923 char *desc_v[] = {NULL, NULL};
1924 char *info_v[] = {NULL, NULL};
89db421e 1925 char *mitMoiraId_v[] = {NULL, NULL};
cd9e6b16 1926 char *groupTypeControl_v[] = {NULL, NULL};
1927 char groupTypeControlStr[80];
1928 char group_membership[1];
1929 int i;
1930 int security_flag;
1931 u_int groupTypeControl = ADS_GROUP_TYPE_GLOBAL_GROUP;
1932 int n;
1933 int rc;
5b8457c5 1934 int group_count;
89db421e 1935 int updateGroup;
1936 char filter[128];
cd9e6b16 1937 char *attr_array[3];
1938 char **call_args;
1939
1940 call_args = ptr;
1941
cd9e6b16 1942 if (!check_string(av[L_NAME]))
78af4e6e 1943 {
f75f605a 1944 com_err(whoami, 0, "invalid LDAP list name %s", av[L_NAME]);
89db421e 1945 return(AD_INVALID_NAME);
78af4e6e 1946 }
f75f605a 1947
89db421e 1948 updateGroup = (int)call_args[4];
cd9e6b16 1949 memset(group_ou, 0, sizeof(group_ou));
1950 memset(group_membership, 0, sizeof(group_membership));
1951 security_flag = 0;
1952 get_group_membership(group_membership, group_ou, &security_flag, av);
89db421e 1953 strcpy(new_group_name, av[L_NAME]);
1954 sprintf(new_dn, "cn=%s,%s,%s", new_group_name, group_ou, call_args[1]);
cd9e6b16 1955 if (security_flag)
1956 groupTypeControl |= ADS_GROUP_TYPE_SECURITY_ENABLED;
89db421e 1957
1958 sprintf(sam_group_name, "%s_group", av[L_NAME]);
cd9e6b16 1959
89db421e 1960 if (!updateGroup)
1961 {
cd9e6b16 1962
89db421e 1963 sprintf(groupTypeControlStr, "%ld", groupTypeControl);
1964 groupTypeControl_v[0] = groupTypeControlStr;
cd9e6b16 1965
89db421e 1966 strcpy(cn_group_name, av[L_NAME]);
cd9e6b16 1967
89db421e 1968 samAccountName_v[0] = sam_group_name;
1969 name_v[0] = new_group_name;
1970 cn_v[0] = new_group_name;
cd9e6b16 1971
89db421e 1972 n = 0;
1973 ADD_ATTR("cn", cn_v, LDAP_MOD_ADD);
1974 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
1975 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_ADD);
1976 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
1977 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
1978 if (strlen(av[L_DESC]) != 0)
1979 {
1980 desc_v[0] = av[L_DESC];
1981 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
1982 }
1983 ADD_ATTR("groupType", groupTypeControl_v, LDAP_MOD_ADD);
1984 if (strlen(av[L_ACE_NAME]) != 0)
1985 {
1986 sprintf(info, "The Administrator of this list is: %s", av[L_ACE_NAME]);
1987 info_v[0] = info;
1988 ADD_ATTR("info", info_v, LDAP_MOD_ADD);
1989 }
1990 if (strlen(call_args[5]) != 0)
1991 {
1992 mitMoiraId_v[0] = call_args[5];
1993 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_ADD);
1994 }
1995 mods[n] = NULL;
1996
1997 rc = ldap_add_ext_s((LDAP *)call_args[0], new_dn, mods, NULL, NULL);
1998
1999 for (i = 0; i < n; i++)
2000 free(mods[i]);
2001 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
2002 {
909e0dc3 2003 com_err(whoami, 0, "Unable to create list %s in AD : %s",
89db421e 2004 av[L_NAME], ldap_err2string(rc));
2005 callback_rc = rc;
2006 return(rc);
2007 }
78af4e6e 2008 }
89db421e 2009 if ((rc == LDAP_ALREADY_EXISTS) || (updateGroup))
5a775f54 2010 {
2011 n = 0;
89db421e 2012 desc_v[0] = NULL;
2013 if (strlen(av[L_DESC]) != 0)
2014 desc_v[0] = av[L_DESC];
5a775f54 2015 ADD_ATTR("description", desc_v, LDAP_MOD_REPLACE);
89db421e 2016 info_v[0] = NULL;
2017 if (strlen(av[L_ACE_NAME]) != 0)
2018 {
2019 sprintf(info, "The Administrator of this list is: %s", av[L_ACE_NAME]);
2020 info_v[0] = info;
2021 }
2022 ADD_ATTR("info", info_v, LDAP_MOD_REPLACE);
2023 if (strlen(call_args[5]) != 0)
2024 {
2025 mitMoiraId_v[0] = call_args[5];
2026 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
2027 }
2028 if (!(atoi(av[L_ACTIVE])))
2029 {
2030 member_v[0] = NULL;
2031 ADD_ATTR("member", member_v, LDAP_MOD_REPLACE);
2032 }
5a775f54 2033 mods[n] = NULL;
2034 rc = ldap_modify_s((LDAP *)call_args[0], new_dn, mods);
2035 for (i = 0; i < n; i++)
2036 free(mods[i]);
909e0dc3 2037 if (rc != LDAP_SUCCESS)
2038 {
2039 com_err(whoami, 0, "Unable to update list %s in AD : %s",
2040 av[L_NAME], ldap_err2string(rc));
2041 callback_rc = rc;
2042 return(rc);
2043 }
5a775f54 2044 }
89db421e 2045
909e0dc3 2046 ProcessGroupSecurity((LDAP *)call_args[0], call_args[1], av[L_NAME],
2047 atoi(av[L_HIDDEN]), av[L_ACE_TYPE], av[L_ACE_NAME]);
2048
89db421e 2049 sprintf(filter, "(sAMAccountName=%s)", sam_group_name);
2050 if (strlen(call_args[5]) != 0)
6c8f12af 2051 sprintf(filter, "(&(objectClass=group)(mitMoiraId=%s))", call_args[5]);
cd9e6b16 2052 attr_array[0] = "objectSid";
2053 attr_array[1] = NULL;
5b8457c5 2054 group_count = 0;
2055 group_base = NULL;
89db421e 2056 if ((rc = linklist_build((LDAP *)call_args[0], call_args[1], filter, attr_array,
5b8457c5 2057 &group_base, &group_count)) == LDAP_SUCCESS)
cd9e6b16 2058 {
3e586ecf 2059 if (group_count != 1)
2060 {
2061 if (strlen(call_args[5]) != 0)
2062 {
2063 linklist_free(group_base);
2064 group_count = 0;
2065 group_base = NULL;
2066 sprintf(filter, "(sAMAccountName=%s)", sam_group_name);
2067 rc = linklist_build((LDAP *)call_args[0], call_args[1], filter,
2068 attr_array, &group_base, &group_count);
2069 }
2070 }
5b8457c5 2071 if (group_count == 1)
cd9e6b16 2072 {
5b8457c5 2073 (*sid_ptr) = group_base;
cd9e6b16 2074 (*sid_ptr)->member = strdup(av[L_NAME]);
2075 (*sid_ptr)->type = (char *)GROUPS;
2076 sid_ptr = &(*sid_ptr)->next;
2077 }
5b8457c5 2078 else
2079 {
2080 if (group_base != NULL)
2081 linklist_free(group_base);
2082 }
cd9e6b16 2083 }
5b8457c5 2084 else
2085 {
2086 if (group_base != NULL)
2087 linklist_free(group_base);
2088 }
2089 return(LDAP_SUCCESS);
cd9e6b16 2090}
2091
909e0dc3 2092int ProcessGroupSecurity(LDAP *ldap_handle, char *dn_path, char *TargetGroupName,
2093 int HiddenGroup, char *AceType, char *AceName)
2094{
2095 char filter_exp[1024];
2096 char *attr_array[5];
2097 char search_path[512];
2098 char root_ou[128];
2099 char TemplateDn[512];
2100 char TemplateSamName[128];
2101 char TargetDn[512];
2102 char TargetSamName[128];
2103 char AceSamAccountName[128];
2104 char AceDn[256];
2105 unsigned char AceSid[128];
2106 unsigned char UserTemplateSid[128];
2107 char acBERBuf[N_SD_BER_BYTES];
2108 char GroupSecurityTemplate[256];
2109 int AceSidCount;
2110 int UserTemplateSidCount;
2111 int group_count;
2112 int n;
2113 int i;
2114 int rc;
2115 int nVal;
2116 ULONG dwInfo;
2117 int array_count = 0;
2118 LDAPMod *mods[20];
2119 LK_ENTRY *group_base;
2120 LDAP_BERVAL **ppsValues;
2121 LDAPControl sControl = {"1.2.840.113556.1.4.801",
2122 { N_SD_BER_BYTES, acBERBuf },
2123 TRUE
2124 };
2125 LDAPControl *apsServerControls[] = {&sControl, NULL};
2126 LDAPMessage *psMsg;
2127
2128 dwInfo = OWNER_SECURITY_INFORMATION | GROUP_SECURITY_INFORMATION | DACL_SECURITY_INFORMATION | SACL_SECURITY_INFORMATION;
2129 BEREncodeSecurityBits(dwInfo, acBERBuf);
2130
2131 sprintf(search_path, "%s,%s", group_ou_root, dn_path);
2132 sprintf(filter_exp, "(sAMAccountName=%s_group)", TargetGroupName);
2133 attr_array[0] = "sAMAccountName";
2134 attr_array[1] = NULL;
2135 group_count = 0;
2136 group_base = NULL;
2137 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
2138 &group_base, &group_count) != 0))
2139 return(1);
2140 if (group_count != 1)
2141 {
2142 linklist_free(group_base);
2143 return(1);
2144 }
2145 strcpy(TargetDn, group_base->dn);
2146 strcpy(TargetSamName, group_base->value);
2147 linklist_free(group_base);
2148 group_base = NULL;
2149 group_count = 0;
2150
2151 UserTemplateSidCount = 0;
2152 memset(UserTemplateSid, '\0', sizeof(UserTemplateSid));
2153 memset(AceSamAccountName, '\0', sizeof(AceSamAccountName));
2154 memset(AceSid, '\0', sizeof(AceSid));
2155 AceSidCount = 0;
2156 group_base = NULL;
2157 group_count = 0;
2158 if (strlen(AceName) != 0)
2159 {
2160 if (!strcmp(AceType, "LIST"))
2161 {
2162 sprintf(AceSamAccountName, "%s_group", AceName);
2163 strcpy(root_ou, group_ou_root);
2164 }
2165 else if (!strcmp(AceType, "USER"))
2166 {
2167 sprintf(AceSamAccountName, "%s", AceName);
2168 strcpy(root_ou, user_ou);
2169 }
2170 if (strlen(AceSamAccountName) != 0)
2171 {
2172 sprintf(search_path, "%s,%s", root_ou, dn_path);
2173 sprintf(filter_exp, "(sAMAccountName=%s)", AceSamAccountName);
2174 attr_array[0] = "objectSid";
2175 attr_array[1] = NULL;
2176 group_count = 0;
2177 group_base = NULL;
2178 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
2179 &group_base, &group_count) != 0))
2180 return(1);
2181 if (group_count == 1)
2182 {
2183 strcpy(AceDn, group_base->dn);
2184 AceSidCount = group_base->length;
2185 memcpy(AceSid, group_base->value, AceSidCount);
2186 }
2187 linklist_free(group_base);
2188 group_base = NULL;
2189 group_count = 0;
2190 }
2191 }
2192 if (AceSidCount == 0)
2193 {
2194 com_err(whoami, 0, "Group %s: Administrator: %s, Type: %s - does not have an AD SID.", TargetGroupName, AceName, AceType);
2195 com_err(whoami, 0, " Non-admin security group template will be used.");
2196 }
2197 else
2198 {
2199 sprintf(search_path, "%s,%s", security_template_ou, dn_path);
2200 sprintf(filter_exp, "(sAMAccountName=%s)", "UserTemplate.u");
2201 attr_array[0] = "objectSid";
2202 attr_array[1] = NULL;
2203
2204 group_count = 0;
2205 group_base = NULL;
2206 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
2207 &group_base, &group_count) != 0))
2208 return(1);
2209 if ((rc != 0) || (group_count != 1))
2210 {
2211 com_err(whoami, 0, "Couldn't process user security template: %s", "UserTemplate");
2212 AceSidCount = 0;
2213 }
2214 else
2215 {
2216 UserTemplateSidCount = group_base->length;
2217 memcpy(UserTemplateSid, group_base->value, UserTemplateSidCount);
2218 }
2219 linklist_free(group_base);
2220 group_base = NULL;
2221 group_count = 0;
2222 }
2223
2224 if (HiddenGroup)
2225 {
2226 if (AceSidCount == 0)
2227 {
2228 strcpy(GroupSecurityTemplate, HIDDEN_GROUP);
2229 sprintf(filter_exp, "(sAMAccountName=%s)", HIDDEN_GROUP);
2230 }
2231 else
2232 {
2233 strcpy(GroupSecurityTemplate, HIDDEN_GROUP_WITH_ADMIN);
2234 sprintf(filter_exp, "(sAMAccountName=%s)", HIDDEN_GROUP_WITH_ADMIN);
2235 }
2236 }
2237 else
2238 {
2239 if (AceSidCount == 0)
2240 {
2241 strcpy(GroupSecurityTemplate, NOT_HIDDEN_GROUP);
2242 sprintf(filter_exp, "(sAMAccountName=%s)", NOT_HIDDEN_GROUP);
2243 }
2244 else
2245 {
2246 strcpy(GroupSecurityTemplate, NOT_HIDDEN_GROUP_WITH_ADMIN);
2247 sprintf(filter_exp, "(sAMAccountName=%s)", NOT_HIDDEN_GROUP_WITH_ADMIN);
2248 }
2249 }
2250
2251 sprintf(search_path, "%s,%s", security_template_ou, dn_path);
2252 attr_array[0] = "sAMAccountName";
2253 attr_array[1] = NULL;
2254 group_count = 0;
2255 group_base = NULL;
2256 if ((rc = linklist_build(ldap_handle, search_path, filter_exp, attr_array,
2257 &group_base, &group_count) != 0))
2258 return(1);
2259 if (group_count != 1)
2260 {
2261 linklist_free(group_base);
2262 com_err(whoami, 0, "Couldn't process group security template: %s - security not set", GroupSecurityTemplate);
2263 return(1);
2264 }
2265 strcpy(TemplateDn, group_base->dn);
2266 strcpy(TemplateSamName, group_base->value);
2267 linklist_free(group_base);
2268 group_base = NULL;
2269 group_count = 0;
2270
2271 sprintf(filter_exp, "(sAMAccountName=%s)", TemplateSamName);
2272 rc = ldap_search_ext_s(ldap_handle,
2273 TemplateDn,
2274 LDAP_SCOPE_SUBTREE,
2275 filter_exp,
2276 NULL,
2277 0,
2278 apsServerControls,
2279 NULL,
2280 NULL,
2281 0,
2282 &psMsg);
2283
2284 if ((psMsg = ldap_first_entry(ldap_handle, psMsg)) == NULL)
2285 {
2286 com_err(whoami, 0, "Couldn't find group security template: %s - security not set", GroupSecurityTemplate);
2287 return(1);
2288 }
2289 ppsValues = ldap_get_values_len(ldap_handle, psMsg, "ntSecurityDescriptor");
2290 if (ppsValues == NULL)
2291 {
2292 com_err(whoami, 0, "Couldn't find group security descriptor for group %s - security not set", GroupSecurityTemplate);
2293 return(1);
2294 }
2295
2296 if (AceSidCount != 0)
2297 {
2298 for (nVal = 0; ppsValues[nVal] != NULL; nVal++)
2299 {
2300 for (i = 0; i < (int)(ppsValues[nVal]->bv_len - UserTemplateSidCount); i++)
2301 {
2302 if (!memcmp(&ppsValues[nVal]->bv_val[i], UserTemplateSid, UserTemplateSidCount))
2303 {
2304 memcpy(&ppsValues[nVal]->bv_val[i], AceSid, AceSidCount);
2305 break;
2306 }
2307 }
2308 }
2309 }
2310
2311 n = 0;
2312 ADD_ATTR("ntSecurityDescriptor", (char **)ppsValues, LDAP_MOD_REPLACE | LDAP_MOD_BVALUES);
2313 mods[n] = NULL;
2314
2315 rc = ldap_modify_s(ldap_handle, TargetDn, mods);
2316 for (i = 0; i < n; i++)
2317 free(mods[i]);
2318 ldap_value_free_len(ppsValues);
2319 ldap_msgfree(psMsg);
2320 if (rc != LDAP_SUCCESS)
2321 {
2322 com_err(whoami, 0, "Couldn't set security settings for group %s : %s",
2323 TargetGroupName, ldap_err2string(rc));
2324 if (AceSidCount != 0)
2325 {
2326 com_err(whoami, 0, "Trying to set security for group %s without admin.",
2327 TargetGroupName);
2328 if (rc = ProcessGroupSecurity(ldap_handle, dn_path, TargetGroupName,
2329 HiddenGroup, "", ""))
2330 {
2331 com_err(whoami, 0, "Unable to set security for group %s.",
2332 TargetGroupName);
2333 return(rc);
2334 }
2335 }
2336 return(rc);
2337 }
2338 com_err(whoami, 0, "Security set for group %s.", TargetGroupName);
2339 return(rc);
2340}
2341
89db421e 2342int group_delete(LDAP *ldap_handle, char *dn_path, char *group_name,
2343 char *group_membership, char *MoiraId)
cd9e6b16 2344{
2345 LK_ENTRY *group_base;
f75f605a 2346 char temp[512];
89db421e 2347 char filter[128];
cd9e6b16 2348 int group_count;
2349 int rc;
2350
f75f605a 2351 if (!check_string(group_name))
78af4e6e 2352 {
f75f605a 2353 com_err(whoami, 0, "invalid LDAP list name %s", group_name);
89db421e 2354 return(AD_INVALID_NAME);
78af4e6e 2355 }
89db421e 2356
2357 memset(filter, '\0', sizeof(filter));
cd9e6b16 2358 group_count = 0;
2359 group_base = NULL;
cd9e6b16 2360 sprintf(temp, "%s,%s", group_ou_root, dn_path);
89db421e 2361 if (rc = ad_get_group(ldap_handle, temp, group_name,
2362 group_membership, MoiraId,
2363 "distinguishedName", &group_base,
2364 &group_count, filter))
2365 return(rc);
2366
cd9e6b16 2367 if (group_count == 1)
78af4e6e 2368 {
2369 if ((rc = ldap_delete_s(ldap_handle, group_base->value)) != LDAP_SUCCESS)
2370 {
f75f605a 2371 linklist_free(group_base);
2372 com_err(whoami, 0, "Unable to delete list %s from AD : %s",
2373 group_name, ldap_err2string(rc));
89db421e 2374 return(rc);
78af4e6e 2375 }
f75f605a 2376 linklist_free(group_base);
78af4e6e 2377 }
2378 else
2379 {
f75f605a 2380 linklist_free(group_base);
2381 com_err(whoami, 0, "Unable to find list %s in AD.", group_name);
89db421e 2382 return(AD_NO_GROUPS_FOUND);
78af4e6e 2383 }
f75f605a 2384
78af4e6e 2385 return(0);
cd9e6b16 2386}
2387
909e0dc3 2388int BEREncodeSecurityBits(ULONG uBits, char *pBuffer)
2389{
2390 *pBuffer++ = 0x30;
2391 *pBuffer++ = 0x03;
2392 *pBuffer++ = 0x02;
2393 *pBuffer++ = 0x00;
2394 return(N_SD_BER_BYTES);
2395}
2396
f75f605a 2397int process_lists(int ac, char **av, void *ptr)
cd9e6b16 2398{
f75f605a 2399 int rc;
2400 int security_flag;
2401 char group_ou[256];
2402 char group_membership[2];
2403 char **call_args;
cd9e6b16 2404
2405 call_args = ptr;
2406
f75f605a 2407 security_flag = 0;
2408 memset(group_ou, '\0', sizeof(group_ou));
2409 memset(group_membership, '\0', sizeof(group_membership));
2410 get_group_membership(group_membership, group_ou, &security_flag, av);
2411 rc = member_add((LDAP *)call_args[0], (char *)call_args[1], av[L_NAME],
89db421e 2412 group_ou, group_membership, call_args[2],
2413 (char *)call_args[3], "");
cd9e6b16 2414 return(0);
2415}
2416
2417int member_list_build(int ac, char **av, void *ptr)
2418{
2419 LK_ENTRY *linklist;
78af4e6e 2420 char temp[1024];
cd9e6b16 2421 char **call_args;
2422
2423 call_args = ptr;
2424
2425 strcpy(temp, av[ACE_NAME]);
2426 if (!check_string(temp))
2427 return(0);
f78c7eaf 2428 if (!strcmp(av[ACE_TYPE], "USER"))
cd9e6b16 2429 {
f75f605a 2430 if (!((int)call_args[3] & MOIRA_USERS))
f78c7eaf 2431 return(0);
2432 }
2433 else if (!strcmp(av[ACE_TYPE], "STRING"))
2434 {
f75f605a 2435 if (!((int)call_args[3] & MOIRA_STRINGS))
f78c7eaf 2436 return(0);
2437 if (contact_create((LDAP *)call_args[0], call_args[1], temp, contact_ou))
2438 return(0);
cd9e6b16 2439 }
2440 else if (!strcmp(av[ACE_TYPE], "LIST"))
2441 {
f75f605a 2442 if (!((int)call_args[3] & MOIRA_LISTS))
f78c7eaf 2443 return(0);
cd9e6b16 2444 }
f78c7eaf 2445 else if (!strcmp(av[ACE_TYPE], "KERBEROS"))
cd9e6b16 2446 {
f75f605a 2447 if (!((int)call_args[3] & MOIRA_KERBEROS))
f78c7eaf 2448 return(0);
2449 if (contact_create((LDAP *)call_args[0], call_args[1], temp, kerberos_ou))
2450 return(0);
cd9e6b16 2451 }
f78c7eaf 2452 else
2453 return(0);
2454
cd9e6b16 2455 linklist = member_base;
2456 while (linklist)
2457 {
2458 if (!strcasecmp(temp, linklist->member))
2459 return(0);
2460 linklist = linklist->next;
2461 }
2462 linklist = calloc(1, sizeof(LK_ENTRY));
2463 linklist->op = 1;
2464 linklist->dn = NULL;
2465 linklist->list = calloc(1, strlen(call_args[2]) + 1);
2466 strcpy(linklist->list, call_args[2]);
2467 linklist->type = calloc(1, strlen(av[ACE_TYPE]) + 1);
2468 strcpy(linklist->type, av[ACE_TYPE]);
2469 linklist->member = calloc(1, strlen(temp) + 1);
2470 strcpy(linklist->member, temp);
2471 linklist->next = member_base;
2472 member_base = linklist;
2473 return(0);
2474}
2475
78af4e6e 2476int member_remove(LDAP *ldap_handle, char *dn_path, char *group_name,
f75f605a 2477 char *group_ou, char *group_membership, char *user_name,
89db421e 2478 char *UserOu, char *MoiraId)
78af4e6e 2479{
2480 char distinguished_name[1024];
f75f605a 2481 char *modvalues[2];
78af4e6e 2482 char temp[256];
89db421e 2483 char filter[128];
78af4e6e 2484 int group_count;
2485 int i;
2486 int n;
2487 LDAPMod *mods[20];
2488 LK_ENTRY *group_base;
2489 ULONG rc;
2490
2491 if (!check_string(group_name))
89db421e 2492 return(AD_INVALID_NAME);
2493
2494 memset(filter, '\0', sizeof(filter));
2495 group_base = NULL;
2496 group_count = 0;
2497 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
2498 group_membership, MoiraId,
2499 "distinguishedName", &group_base,
2500 &group_count, filter))
2501 return(rc);
2502
78af4e6e 2503 if (group_count != 1)
2504 {
f75f605a 2505 com_err(whoami, 0, "LDAP server unable to find list %s in AD",
2506 group_name);
2507 linklist_free(group_base);
2508 group_base = NULL;
2509 group_count = 0;
78af4e6e 2510 goto cleanup;
2511 }
2512 strcpy(distinguished_name, group_base->value);
2513 linklist_free(group_base);
2514 group_base = NULL;
2515 group_count = 0;
78af4e6e 2516
f75f605a 2517 sprintf(temp, "CN=%s,%s,%s", user_name, UserOu, dn_path);
2518 modvalues[0] = temp;
2519 modvalues[1] = NULL;
2520
2521 n = 0;
2522 ADD_ATTR("member", modvalues, LDAP_MOD_DELETE);
2523 mods[n] = NULL;
2524 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
2525 for (i = 0; i < n; i++)
2526 free(mods[i]);
6c8f12af 2527 if (rc == LDAP_UNWILLING_TO_PERFORM)
2528 rc = LDAP_SUCCESS;
f75f605a 2529 if (rc != LDAP_SUCCESS)
78af4e6e 2530 {
f75f605a 2531 com_err(whoami, 0, "LDAP server unable to modify list %s members : %s",
2532 group_name, ldap_err2string(rc));
2533 goto cleanup;
78af4e6e 2534 }
2535
2536cleanup:
78af4e6e 2537 return(rc);
2538}
2539
f75f605a 2540int member_add(LDAP *ldap_handle, char *dn_path, char *group_name,
89db421e 2541 char *group_ou, char *group_membership, char *user_name,
2542 char *UserOu, char *MoiraId)
cd9e6b16 2543{
2544 char distinguished_name[1024];
f75f605a 2545 char *modvalues[2];
cd9e6b16 2546 char temp[256];
89db421e 2547 char filter[128];
cd9e6b16 2548 int group_count;
cd9e6b16 2549 int n;
f75f605a 2550 int i;
cd9e6b16 2551 LDAPMod *mods[20];
2552 LK_ENTRY *group_base;
cd9e6b16 2553 ULONG rc;
2554
89db421e 2555 if (!check_string(group_name))
2556 return(AD_INVALID_NAME);
2557
cd9e6b16 2558 rc = 0;
89db421e 2559 memset(filter, '\0', sizeof(filter));
cd9e6b16 2560 group_base = NULL;
2561 group_count = 0;
89db421e 2562 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
2563 group_membership, MoiraId,
2564 "distinguishedName", &group_base,
2565 &group_count, filter))
2566 return(rc);
cd9e6b16 2567
cd9e6b16 2568 if (group_count != 1)
2569 {
f75f605a 2570 linklist_free(group_base);
2571 group_base = NULL;
2572 group_count = 0;
2573 com_err(whoami, 0, "LDAP server unable to find list %s in AD",
2574 group_name);
89db421e 2575 return(AD_MULTIPLE_GROUPS_FOUND);
cd9e6b16 2576 }
f75f605a 2577
cd9e6b16 2578 strcpy(distinguished_name, group_base->value);
2579 linklist_free(group_base);
2580 group_base = NULL;
2581 group_count = 0;
2582
f75f605a 2583 sprintf(temp, "CN=%s,%s,%s", user_name, UserOu, dn_path);
2584 modvalues[0] = temp;
2585 modvalues[1] = NULL;
cd9e6b16 2586
f75f605a 2587 n = 0;
2588 ADD_ATTR("member", modvalues, LDAP_MOD_ADD);
2589 mods[n] = NULL;
2590 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
2591 if (rc == LDAP_ALREADY_EXISTS)
2592 rc = LDAP_SUCCESS;
89db421e 2593 if ((!strcmp(UserOu, contact_ou)) || (!strcmp(UserOu, kerberos_ou)))
2594 {
2595 if (rc == LDAP_UNWILLING_TO_PERFORM)
2596 rc = LDAP_SUCCESS;
2597 }
f75f605a 2598 for (i = 0; i < n; i++)
2599 free(mods[i]);
2600 if (rc != LDAP_SUCCESS)
cd9e6b16 2601 {
89db421e 2602 com_err(whoami, 0, "LDAP server unable to add %s to list %s as a member : %s",
2603 user_name, group_name, ldap_err2string(rc));
cd9e6b16 2604 }
2605
f75f605a 2606 return(rc);
cd9e6b16 2607}
2608
2609int contact_create(LDAP *ld, char *bind_path, char *user, char *group_ou)
2610{
2611 LDAPMod *mods[20];
2612 char new_dn[256];
2613 char cn_user_name[256];
2614 char contact_name[256];
f78c7eaf 2615 char *email_v[] = {NULL, NULL};
cd9e6b16 2616 char *cn_v[] = {NULL, NULL};
2617 char *contact_v[] = {NULL, NULL};
2618 char *objectClass_v[] = {"top", "person",
2619 "organizationalPerson",
2620 "contact", NULL};
2621 char *name_v[] = {NULL, NULL};
2622 char *desc_v[] = {NULL, NULL};
2623 int n;
2624 int rc;
2625 int i;
2626
2627 if (!check_string(user))
78af4e6e 2628 {
f75f605a 2629 com_err(whoami, 0, "invalid LDAP name %s", user);
89db421e 2630 return(AD_INVALID_NAME);
78af4e6e 2631 }
cd9e6b16 2632 strcpy(contact_name, user);
2633 sprintf(cn_user_name,"CN=%s,%s,%s", contact_name, group_ou, bind_path);
2634 cn_v[0] = cn_user_name;
2635 contact_v[0] = contact_name;
2636 name_v[0] = user;
2637 desc_v[0] = "Auto account created by Moira";
f78c7eaf 2638 email_v[0] = user;
cd9e6b16 2639
2640 strcpy(new_dn, cn_user_name);
2641 n = 0;
2642 ADD_ATTR("cn", contact_v, LDAP_MOD_ADD);
2643 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
2644 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
2645 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
2646 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
f78c7eaf 2647 if (!strcmp(group_ou, contact_ou))
2648 {
2649 ADD_ATTR("mail", email_v, LDAP_MOD_ADD);
2650 }
cd9e6b16 2651 mods[n] = NULL;
2652
2653 rc = ldap_add_ext_s(ld, new_dn, mods, NULL, NULL);
2654 for (i = 0; i < n; i++)
2655 free(mods[i]);
f78c7eaf 2656 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
2657 {
2658 n = 0;
2659 ADD_ATTR("cn", contact_v, LDAP_MOD_ADD);
2660 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
2661 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
2662 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
2663 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
2664 mods[n] = NULL;
2665 rc = ldap_add_ext_s(ld, new_dn, mods, NULL, NULL);
2666 for (i = 0; i < n; i++)
2667 free(mods[i]);
2668 }
cd9e6b16 2669 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
78af4e6e 2670 {
f75f605a 2671 com_err(whoami, 0, "could not create contact %s : %s",
2672 user, ldap_err2string(rc));
89db421e 2673 return(rc);
78af4e6e 2674 }
2675 return(0);
2676}
2677
f75f605a 2678int user_update(LDAP *ldap_handle, char *dn_path, char *user_name,
89db421e 2679 char *Uid, char *MitId, char *MoiraId, int State)
78af4e6e 2680{
2681 LDAPMod *mods[20];
2682 LK_ENTRY *group_base;
2683 int group_count;
2684 char distinguished_name[256];
89db421e 2685 char *mitMoiraId_v[] = {NULL, NULL};
78af4e6e 2686 char *uid_v[] = {NULL, NULL};
2687 char *mitid_v[] = {NULL, NULL};
f78c7eaf 2688 char *homedir_v[] = {NULL, NULL};
2689 char *winProfile_v[] = {NULL, NULL};
2690 char *drives_v[] = {NULL, NULL};
89db421e 2691 char *userAccountControl_v[] = {NULL, NULL};
2692 char userAccountControlStr[80];
78af4e6e 2693 int n;
2694 int rc;
2695 int i;
65382c46 2696 int last_weight;
89db421e 2697 u_int userAccountControl = UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD | UF_PASSWD_CANT_CHANGE;
2698 char filter[128];
78af4e6e 2699 char *attr_array[3];
65382c46 2700 char cWeight[3];
f78c7eaf 2701 char **hp;
2702 char path[256];
65382c46 2703 char cPath[256];
c0bd7667 2704 char temp[256];
f78c7eaf 2705 char winPath[256];
2706 char winProfile[256];
78af4e6e 2707
f75f605a 2708 if (!check_string(user_name))
78af4e6e 2709 {
f75f605a 2710 com_err(whoami, 0, "invalid LDAP user name %s", user_name);
89db421e 2711 return(AD_INVALID_NAME);
78af4e6e 2712 }
2713
78af4e6e 2714 group_count = 0;
2715 group_base = NULL;
89db421e 2716
2717 if (strlen(MoiraId) != 0)
78af4e6e 2718 {
c0bd7667 2719 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
89db421e 2720 attr_array[0] = "cn";
2721 attr_array[1] = NULL;
2722 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
2723 &group_base, &group_count)) != 0)
2724 {
2725 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
2726 user_name, ldap_err2string(rc));
2727 return(rc);
2728 }
2729 }
c0bd7667 2730 if (group_count != 1)
89db421e 2731 {
c0bd7667 2732 linklist_free(group_base);
2733 group_base = NULL;
2734 group_count = 0;
89db421e 2735 sprintf(filter, "(sAMAccountName=%s)", user_name);
2736 attr_array[0] = "cn";
2737 attr_array[1] = NULL;
c0bd7667 2738 sprintf(temp, "%s,%s", user_ou, dn_path);
2739 if ((rc = linklist_build(ldap_handle, temp, filter, attr_array,
89db421e 2740 &group_base, &group_count)) != 0)
2741 {
2742 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
2743 user_name, ldap_err2string(rc));
2744 return(rc);
2745 }
78af4e6e 2746 }
2747
2748 if (group_count != 1)
2749 {
f75f605a 2750 com_err(whoami, 0, "LDAP server unable to find user %s in AD",
2751 user_name);
2752 linklist_free(group_base);
89db421e 2753 return(AD_NO_USER_FOUND);
78af4e6e 2754 }
2755 strcpy(distinguished_name, group_base->dn);
2756
f75f605a 2757 linklist_free(group_base);
2758 group_count = 0;
78af4e6e 2759 n = 0;
f78c7eaf 2760 if ((hp = hes_resolve(user_name, "filsys")) != NULL)
2761 {
65382c46 2762 memset(cWeight, 0, sizeof(cWeight));
2763 memset(cPath, 0, sizeof(cPath));
f78c7eaf 2764 memset(path, 0, sizeof(path));
2765 memset(winPath, 0, sizeof(winPath));
65382c46 2766 last_weight = 1000;
2767 i = 0;
2768 while (hp[i] != NULL)
f78c7eaf 2769 {
7863a0af 2770 if (sscanf(hp[i], "%*s %s", cPath))
65382c46 2771 {
7863a0af 2772 if (strnicmp(cPath, AFS, strlen(AFS)) == 0)
65382c46 2773 {
7863a0af 2774 if (sscanf(hp[i], "%*s %*s %*s %*s %s", cWeight))
2775 {
2776 if (atoi(cWeight) < last_weight)
2777 {
2778 strcpy(path, cPath);
2779 last_weight = (int)atoi(cWeight);
2780 }
2781 }
2782 else
2783 strcpy(path, cPath);
2784 }
65382c46 2785 }
2786 ++i;
2787 }
2788 if (strlen(path))
2789 {
2790 if (!strnicmp(path, AFS, strlen(AFS)))
2791 {
2792 AfsToWinAfs(path, winPath);
2793 homedir_v[0] = winPath;
2794 ADD_ATTR("homeDirectory", homedir_v, LDAP_MOD_REPLACE);
2795 strcpy(winProfile, winPath);
2796 strcat(winProfile, "\\.winprofile");
2797 winProfile_v[0] = winProfile;
2798 ADD_ATTR("profilePath", winProfile_v, LDAP_MOD_REPLACE);
2799 drives_v[0] = "H:";
2800 ADD_ATTR("homeDrive", drives_v, LDAP_MOD_REPLACE);
2801 }
f78c7eaf 2802 }
2803 }
89db421e 2804 uid_v[0] = Uid;
2805 if (strlen(Uid) == 0)
2806 uid_v[0] = NULL;
2807 ADD_ATTR("uid", uid_v, LDAP_MOD_REPLACE);
2808 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_REPLACE);
2809 mitid_v[0] = MitId;
2810 if (strlen(MitId) == 0)
2811 mitid_v[0] = NULL;
2812 ADD_ATTR("employeeID", mitid_v, LDAP_MOD_REPLACE);
2813 mitMoiraId_v[0] = MoiraId;
2814 if (strlen(MoiraId) == 0)
2815 mitMoiraId_v[0] = NULL;
2816 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
2817 if ((State != US_NO_PASSWD) && (State != US_REGISTERED))
2818 userAccountControl |= UF_ACCOUNTDISABLE;
2819 sprintf(userAccountControlStr, "%ld", userAccountControl);
2820 userAccountControl_v[0] = userAccountControlStr;
2821 ADD_ATTR("userAccountControl", userAccountControl_v, LDAP_MOD_REPLACE);
78af4e6e 2822 mods[n] = NULL;
89db421e 2823 if ((rc = ldap_modify_s(ldap_handle, distinguished_name, mods)) != LDAP_SUCCESS)
78af4e6e 2824 {
89db421e 2825 com_err(whoami, 0, "Couldn't modify user data for %s : %s",
2826 user_name, ldap_err2string(rc));
78af4e6e 2827 }
89db421e 2828 for (i = 0; i < n; i++)
2829 free(mods[i]);
2830
f78c7eaf 2831 if (hp != NULL)
2832 {
2833 i = 0;
2834 while (hp[i])
2835 {
2836 free(hp[i]);
2837 i++;
2838 }
2839 }
78af4e6e 2840
f75f605a 2841 return(rc);
cd9e6b16 2842}
2843
f75f605a 2844int user_rename(LDAP *ldap_handle, char *dn_path, char *before_user_name,
89db421e 2845 char *user_name)
9db0b148 2846{
2847 LDAPMod *mods[20];
2848 char new_dn[256];
2849 char old_dn[256];
9db0b148 2850 char upn[256];
2851 char temp[128];
2852 char *userPrincipalName_v[] = {NULL, NULL};
2853 char *altSecurityIdentities_v[] = {NULL, NULL};
2854 char *name_v[] = {NULL, NULL};
78af4e6e 2855 char *samAccountName_v[] = {NULL, NULL};
9db0b148 2856 int n;
2857 int rc;
2858 int i;
9db0b148 2859
f75f605a 2860 if (!check_string(before_user_name))
78af4e6e 2861 {
f75f605a 2862 com_err(whoami, 0, "invalid LDAP user name %s", before_user_name);
89db421e 2863 return(AD_INVALID_NAME);
78af4e6e 2864 }
f75f605a 2865 if (!check_string(user_name))
78af4e6e 2866 {
f75f605a 2867 com_err(whoami, 0, "invalid LDAP user name %s", user_name);
89db421e 2868 return(AD_INVALID_NAME);
78af4e6e 2869 }
9db0b148 2870
f75f605a 2871 strcpy(user_name, user_name);
2872 sprintf(old_dn, "cn=%s,%s,%s", before_user_name, user_ou, dn_path);
9db0b148 2873 sprintf(new_dn, "cn=%s", user_name);
f75f605a 2874 if ((rc = ldap_rename_s(ldap_handle, old_dn, new_dn, NULL, TRUE,
9db0b148 2875 NULL, NULL)) != LDAP_SUCCESS)
2876 {
89db421e 2877 com_err(whoami, 0, "Couldn't rename user from %s to %s : %s",
2878 before_user_name, user_name, ldap_err2string(rc));
f75f605a 2879 return(rc);
9db0b148 2880 }
2881
2882 name_v[0] = user_name;
2883 sprintf(upn, "%s@%s", user_name, ldap_domain);
2884 userPrincipalName_v[0] = upn;
2885 sprintf(temp, "Kerberos:%s@%s", user_name, PRIMARY_REALM);
2886 altSecurityIdentities_v[0] = temp;
78af4e6e 2887 samAccountName_v[0] = user_name;
9db0b148 2888
2889 n = 0;
2890 ADD_ATTR("altSecurityIdentities", altSecurityIdentities_v, LDAP_MOD_REPLACE);
2891 ADD_ATTR("userPrincipalName", userPrincipalName_v, LDAP_MOD_REPLACE);
2892 ADD_ATTR("displayName", name_v, LDAP_MOD_REPLACE);
78af4e6e 2893 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_REPLACE);
9db0b148 2894 mods[n] = NULL;
f75f605a 2895 sprintf(new_dn, "cn=%s,%s,%s", user_name, user_ou, dn_path);
2896 if ((rc = ldap_modify_s(ldap_handle, new_dn, mods)) != LDAP_SUCCESS)
9db0b148 2897 {
f75f605a 2898 com_err(whoami, 0, "After renaming, couldn't modify user data for %s : %s",
2899 user_name, ldap_err2string(rc));
9db0b148 2900 }
2901 for (i = 0; i < n; i++)
2902 free(mods[i]);
f75f605a 2903 return(rc);
9db0b148 2904}
2905
f75f605a 2906int filesys_process(LDAP *ldap_handle, char *dn_path, char *fs_name,
2907 char *fs_type, char *fs_pack, int operation)
f78c7eaf 2908{
2909 char distinguished_name[256];
2910 char winPath[256];
2911 char winProfile[256];
89db421e 2912 char filter[128];
f78c7eaf 2913 char *attr_array[3];
2914 char *homedir_v[] = {NULL, NULL};
2915 char *winProfile_v[] = {NULL, NULL};
2916 char *drives_v[] = {NULL, NULL};
f78c7eaf 2917 int group_count;
2918 int n;
2919 int rc;
2920 int i;
f78c7eaf 2921 LDAPMod *mods[20];
2922 LK_ENTRY *group_base;
2923
f75f605a 2924 if (!check_string(fs_name))
f78c7eaf 2925 {
f75f605a 2926 com_err(whoami, 0, "invalid filesys name %s", fs_name);
89db421e 2927 return(AD_INVALID_NAME);
f78c7eaf 2928 }
2929
f75f605a 2930 if (strcmp(fs_type, "AFS"))
f78c7eaf 2931 {
f75f605a 2932 com_err(whoami, 0, "invalid filesys type %s", fs_type);
89db421e 2933 return(AD_INVALID_FILESYS);
f78c7eaf 2934 }
2935
f78c7eaf 2936 group_count = 0;
2937 group_base = NULL;
89db421e 2938 sprintf(filter, "(sAMAccountName=%s)", fs_name);
f78c7eaf 2939 attr_array[0] = "cn";
2940 attr_array[1] = NULL;
89db421e 2941 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
f78c7eaf 2942 &group_base, &group_count)) != 0)
2943 {
f75f605a 2944 com_err(whoami, 0, "LDAP server couldn't process filesys %s : %s",
2945 fs_name, ldap_err2string(rc));
2946 return(rc);
f78c7eaf 2947 }
2948
2949 if (group_count != 1)
2950 {
f75f605a 2951 linklist_free(group_base);
2952 com_err(whoami, 0, "LDAP server unable to find user %s in AD",
2953 fs_name);
2954 return(LDAP_NO_SUCH_OBJECT);
f78c7eaf 2955 }
2956 strcpy(distinguished_name, group_base->dn);
f75f605a 2957 linklist_free(group_base);
2958 group_count = 0;
f78c7eaf 2959
2960 n = 0;
2961 if (operation == LDAP_MOD_ADD)
2962 {
2963 memset(winPath, 0, sizeof(winPath));
f75f605a 2964 AfsToWinAfs(fs_pack, winPath);
f78c7eaf 2965 homedir_v[0] = winPath;
2966 drives_v[0] = "H:";
2967 memset(winProfile, 0, sizeof(winProfile));
2968 strcpy(winProfile, winPath);
2969 strcat(winProfile, "\\.winprofile");
2970 winProfile_v[0] = winProfile;
2971 }
2972 else
2973 {
2974 homedir_v[0] = NULL;
2975 drives_v[0] = NULL;
2976 winProfile_v[0] = NULL;
2977 }
2978 ADD_ATTR("profilePath", winProfile_v, operation);
2979 ADD_ATTR("homeDrive", drives_v, operation);
2980 ADD_ATTR("homeDirectory", homedir_v, operation);
2981 mods[n] = NULL;
2982
f75f605a 2983 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
f78c7eaf 2984 if (rc != LDAP_SUCCESS)
2985 {
f75f605a 2986 com_err(whoami, 0, "Couldn't modify user data for filesys %s : %s",
2987 fs_name, ldap_err2string(rc));
f78c7eaf 2988 }
2989 for (i = 0; i < n; i++)
2990 free(mods[i]);
2991
f75f605a 2992 return(rc);
f78c7eaf 2993}
2994
cd9e6b16 2995int user_create(int ac, char **av, void *ptr)
2996{
5b8457c5 2997 LK_ENTRY *group_base;
cd9e6b16 2998 LDAPMod *mods[20];
2999 char new_dn[256];
3000 char user_name[256];
9db0b148 3001 char sam_name[256];
5b8457c5 3002 char upn[256];
cd9e6b16 3003 char *cn_v[] = {NULL, NULL};
3004 char *objectClass_v[] = {"top", "person",
3005 "organizationalPerson",
3006 "user", NULL};
3007
3008 char *samAccountName_v[] = {NULL, NULL};
3009 char *altSecurityIdentities_v[] = {NULL, NULL};
89db421e 3010 char *mitMoiraId_v[] = {NULL, NULL};
cd9e6b16 3011 char *name_v[] = {NULL, NULL};
3012 char *desc_v[] = {NULL, NULL};
cd9e6b16 3013 char *userPrincipalName_v[] = {NULL, NULL};
3014 char *userAccountControl_v[] = {NULL, NULL};
78af4e6e 3015 char *uid_v[] = {NULL, NULL};
3016 char *mitid_v[] = {NULL, NULL};
cd9e6b16 3017 char userAccountControlStr[80];
3018 char temp[128];
3019 u_int userAccountControl = UF_NORMAL_ACCOUNT | UF_DONT_EXPIRE_PASSWD | UF_PASSWD_CANT_CHANGE;
3020 int n;
3021 int rc;
3022 int i;
5b8457c5 3023 int group_count;
89db421e 3024 char filter[128];
cd9e6b16 3025 char *attr_array[3];
3026 char **call_args;
3027
3028 call_args = ptr;
3029
78af4e6e 3030 if (!check_string(av[U_NAME]))
3031 {
89db421e 3032 callback_rc = AD_INVALID_NAME;
f75f605a 3033 com_err(whoami, 0, "invalid LDAP user name %s", av[U_NAME]);
89db421e 3034 return(AD_INVALID_NAME);
78af4e6e 3035 }
9db0b148 3036
cd9e6b16 3037 strcpy(user_name, av[U_NAME]);
3038 sprintf(upn, "%s@%s", user_name, ldap_domain);
78af4e6e 3039 sprintf(sam_name, "%s", av[U_NAME]);
9db0b148 3040 samAccountName_v[0] = sam_name;
89db421e 3041 if ((atoi(av[U_STATE]) != US_NO_PASSWD) && (atoi(av[U_STATE]) != US_REGISTERED))
cd9e6b16 3042 userAccountControl |= UF_ACCOUNTDISABLE;
3043 sprintf(userAccountControlStr, "%ld", userAccountControl);
3044 userAccountControl_v[0] = userAccountControlStr;
3045 userPrincipalName_v[0] = upn;
3046
3047 cn_v[0] = user_name;
3048 name_v[0] = user_name;
3049 desc_v[0] = "Auto account created by Moira";
3050 sprintf(temp, "Kerberos:%s@%s", user_name, PRIMARY_REALM);
3051 altSecurityIdentities_v[0] = temp;
3052 sprintf(new_dn, "cn=%s,%s,%s", user_name, user_ou, call_args[1]);
3053
3054 n = 0;
3055 ADD_ATTR("cn", cn_v, LDAP_MOD_ADD);
3056 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
3057 ADD_ATTR("sAMAccountName", samAccountName_v, LDAP_MOD_ADD);
3058 ADD_ATTR("userPrincipalName", userPrincipalName_v, LDAP_MOD_ADD);
3059 ADD_ATTR("userAccountControl", userAccountControl_v, LDAP_MOD_ADD);
3060 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
3061 ADD_ATTR("displayName", name_v, LDAP_MOD_ADD);
3062 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
89db421e 3063 if (strlen(call_args[2]) != 0)
3064 {
3065 mitMoiraId_v[0] = call_args[2];
3066 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_ADD);
3067 }
cd9e6b16 3068 ADD_ATTR("altSecurityIdentities", altSecurityIdentities_v, LDAP_MOD_ADD);
78af4e6e 3069 if (strlen(av[U_UID]) != 0)
3070 {
3071 uid_v[0] = av[U_UID];
3072 ADD_ATTR("uid", uid_v, LDAP_MOD_ADD);
3073 ADD_ATTR("uidNumber", uid_v, LDAP_MOD_ADD);
3074 }
3075 if (strlen(av[U_MITID]) != 0)
3076 mitid_v[0] = av[U_MITID];
3077 else
3078 mitid_v[0] = "none";
3079 ADD_ATTR("employeeID", mitid_v, LDAP_MOD_ADD);
cd9e6b16 3080 mods[n] = NULL;
3081
3082 rc = ldap_add_ext_s((LDAP *)call_args[0], new_dn, mods, NULL, NULL);
78af4e6e 3083 for (i = 0; i < n; i++)
3084 free(mods[i]);
5b8457c5 3085 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
3086 {
3087 com_err(whoami, 0, "could not create user %s : %s",
3088 user_name, ldap_err2string(rc));
3089 callback_rc = rc;
3090 return(rc);
3091 }
cd9e6b16 3092 if (rc == LDAP_SUCCESS)
3093 {
f78c7eaf 3094 if ((rc = set_password(sam_name, "", ldap_domain)) != 0)
cd9e6b16 3095 {
f75f605a 3096 com_err(whoami, 0, "Couldn't set password for user %s : %ld",
3097 user_name, rc);
cd9e6b16 3098 }
3099 }
89db421e 3100 sprintf(filter, "(sAMAccountName=%s)", av[U_NAME]);
3101 if (strlen(call_args[2]) != 0)
c0bd7667 3102 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", call_args[2]);
cd9e6b16 3103 attr_array[0] = "objectSid";
3104 attr_array[1] = NULL;
5b8457c5 3105 group_count = 0;
3106 group_base = NULL;
89db421e 3107 if ((rc = linklist_build((LDAP *)call_args[0], call_args[1], filter, attr_array,
5b8457c5 3108 &group_base, &group_count)) == LDAP_SUCCESS)
cd9e6b16 3109 {
3e586ecf 3110 if (group_count != 1)
3111 {
3112 if (strlen(call_args[2]) != 0)
3113 {
3114 linklist_free(group_base);
3115 group_count = 0;
3116 group_base = NULL;
3117 sprintf(filter, "(sAMAccountName=%s)", av[U_NAME]);
3118 rc = linklist_build((LDAP *)call_args[0], call_args[1], filter,
3119 attr_array, &group_base, &group_count);
3120 }
3121 }
5b8457c5 3122 if (group_count == 1)
cd9e6b16 3123 {
5b8457c5 3124 (*sid_ptr) = group_base;
3e586ecf 3125 (*sid_ptr)->member = strdup(av[U_NAME]);
5b8457c5 3126 (*sid_ptr)->type = (char *)GROUPS;
cd9e6b16 3127 sid_ptr = &(*sid_ptr)->next;
3128 }
5b8457c5 3129 else
3130 {
3131 if (group_base != NULL)
3132 linklist_free(group_base);
3133 }
3134 }
3135 else
3136 {
3137 if (group_base != NULL)
3138 linklist_free(group_base);
cd9e6b16 3139 }
78af4e6e 3140 return(0);
cd9e6b16 3141}
3142
89db421e 3143int user_change_status(LDAP *ldap_handle, char *dn_path,
3144 char *user_name, char *MoiraId,
3145 int operation)
cd9e6b16 3146{
89db421e 3147 char filter[128];
cd9e6b16 3148 char *attr_array[3];
3149 char temp[256];
3150 char distinguished_name[1024];
cd9e6b16 3151 char **modvalues;
89db421e 3152 char *mitMoiraId_v[] = {NULL, NULL};
cd9e6b16 3153 LDAPMod *mods[20];
3154 LK_ENTRY *group_base;
3155 int group_count;
3156 int rc;
3157 int i;
3158 int n;
3159 ULONG ulongValue;
3160
f75f605a 3161 if (!check_string(user_name))
78af4e6e 3162 {
f75f605a 3163 com_err(whoami, 0, "invalid LDAP user name %s", user_name);
89db421e 3164 return(AD_INVALID_NAME);
78af4e6e 3165 }
f75f605a 3166
cd9e6b16 3167 group_count = 0;
3168 group_base = NULL;
89db421e 3169
3170 if (strlen(MoiraId) != 0)
cd9e6b16 3171 {
c0bd7667 3172 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
89db421e 3173 attr_array[0] = "UserAccountControl";
3174 attr_array[1] = NULL;
3175 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3176 &group_base, &group_count)) != 0)
3177 {
3178 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
3179 user_name, ldap_err2string(rc));
3180 return(rc);
3181 }
3182 }
c0bd7667 3183 if (group_count != 1)
89db421e 3184 {
c0bd7667 3185 linklist_free(group_base);
3186 group_count = 0;
3187 group_base = NULL;
89db421e 3188 sprintf(filter, "(sAMAccountName=%s)", user_name);
3189 attr_array[0] = "UserAccountControl";
3190 attr_array[1] = NULL;
3191 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3192 &group_base, &group_count)) != 0)
3193 {
3194 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
3195 user_name, ldap_err2string(rc));
3196 return(rc);
3197 }
cd9e6b16 3198 }
3199
78af4e6e 3200 if (group_count != 1)
cd9e6b16 3201 {
f75f605a 3202 linklist_free(group_base);
3203 com_err(whoami, 0, "LDAP server unable to find user %s in AD",
3204 user_name);
3205 return(LDAP_NO_SUCH_OBJECT);
cd9e6b16 3206 }
3207
3208 strcpy(distinguished_name, group_base->dn);
3209 ulongValue = atoi((*group_base).value);
3210 if (operation == MEMBER_DEACTIVATE)
3211 ulongValue |= UF_ACCOUNTDISABLE;
3212 else
3213 ulongValue &= ~UF_ACCOUNTDISABLE;
3214 sprintf(temp, "%ld", ulongValue);
3215 if ((rc = construct_newvalues(group_base, group_count, (*group_base).value,
3216 temp, &modvalues, REPLACE)) == 1)
f75f605a 3217 goto cleanup;
cd9e6b16 3218 linklist_free(group_base);
3219 group_base = NULL;
3220 group_count = 0;
3221 n = 0;
3222 ADD_ATTR("UserAccountControl", modvalues, LDAP_MOD_REPLACE);
89db421e 3223 if (strlen(MoiraId) != 0)
3224 {
3225 mitMoiraId_v[0] = MoiraId;
3226 ADD_ATTR("mitMoiraId", mitMoiraId_v, LDAP_MOD_REPLACE);
3227 }
cd9e6b16 3228 mods[n] = NULL;
f75f605a 3229 rc = ldap_modify_s(ldap_handle, distinguished_name, mods);
cd9e6b16 3230 for (i = 0; i < n; i++)
3231 free(mods[i]);
3232 free_values(modvalues);
3233 if (rc != LDAP_SUCCESS)
3234 {
f75f605a 3235 com_err(whoami, 0, "LDAP server could not change status of user %s : %s",
3236 user_name, ldap_err2string(rc));
cd9e6b16 3237 }
3238cleanup:
f75f605a 3239 return(rc);
cd9e6b16 3240}
3241
89db421e 3242int user_delete(LDAP *ldap_handle, char *dn_path,
3243 char *u_name, char *MoiraId)
cd9e6b16 3244{
89db421e 3245 char filter[128];
cd9e6b16 3246 char *attr_array[3];
3247 char distinguished_name[1024];
3248 char user_name[512];
3249 LK_ENTRY *group_base;
3250 int group_count;
3251 int rc;
3252
3253 if (!check_string(u_name))
89db421e 3254 return(AD_INVALID_NAME);
3255
cd9e6b16 3256 strcpy(user_name, u_name);
3257 group_count = 0;
3258 group_base = NULL;
89db421e 3259
3260 if (strlen(MoiraId) != 0)
cd9e6b16 3261 {
c0bd7667 3262 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
89db421e 3263 attr_array[0] = "name";
3264 attr_array[1] = NULL;
3265 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3266 &group_base, &group_count)) != 0)
3267 {
3268 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
3269 user_name, ldap_err2string(rc));
3270 goto cleanup;
3271 }
3272 }
c0bd7667 3273 if (group_count != 1)
89db421e 3274 {
c0bd7667 3275 linklist_free(group_base);
3276 group_count = 0;
3277 group_base = NULL;
89db421e 3278 sprintf(filter, "(sAMAccountName=%s)", user_name);
3279 attr_array[0] = "name";
3280 attr_array[1] = NULL;
3281 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3282 &group_base, &group_count)) != 0)
3283 {
3284 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
3285 user_name, ldap_err2string(rc));
3286 goto cleanup;
3287 }
cd9e6b16 3288 }
3289
78af4e6e 3290 if (group_count != 1)
cd9e6b16 3291 {
f75f605a 3292 com_err(whoami, 0, "LDAP server unable to find user %s in AD",
3293 user_name);
cd9e6b16 3294 goto cleanup;
3295 }
3296
3297 strcpy(distinguished_name, group_base->dn);
3298 if (rc = ldap_delete_s(ldap_handle, distinguished_name))
3299 {
f75f605a 3300 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
3301 user_name, ldap_err2string(rc));
cd9e6b16 3302 }
3303
3304cleanup:
3305 linklist_free(group_base);
78af4e6e 3306 return(0);
cd9e6b16 3307}
3308
3309void linklist_free(LK_ENTRY *linklist_base)
3310{
3311 LK_ENTRY *linklist_previous;
3312
3313 while (linklist_base != NULL)
3314 {
3315 if (linklist_base->dn != NULL)
3316 free(linklist_base->dn);
3317 if (linklist_base->attribute != NULL)
3318 free(linklist_base->attribute);
3319 if (linklist_base->value != NULL)
3320 free(linklist_base->value);
3321 if (linklist_base->member != NULL)
3322 free(linklist_base->member);
3323 if (linklist_base->type != NULL)
3324 free(linklist_base->type);
3325 if (linklist_base->list != NULL)
3326 free(linklist_base->list);
3327 linklist_previous = linklist_base;
3328 linklist_base = linklist_previous->next;
3329 free(linklist_previous);
3330 }
3331}
3332
3333void free_values(char **modvalues)
3334{
3335 int i;
3336
3337 i = 0;
3338 if (modvalues != NULL)
3339 {
3340 while (modvalues[i] != NULL)
3341 {
3342 free(modvalues[i]);
3343 modvalues[i] = NULL;
3344 ++i;
3345 }
3346 free(modvalues);
3347 }
3348}
3349
3350int sid_update(LDAP *ldap_handle, char *dn_path)
3351{
3352 LK_ENTRY *ptr;
3353 int rc;
3354 unsigned char temp[126];
3355 char *av[3];
3356
3357 ptr = sid_base;
3358
3359 while (ptr != NULL)
3360 {
3361 memset(temp, 0, sizeof(temp));
3362 convert_b_to_a(temp, ptr->value, ptr->length);
5b8457c5 3363 if (!ptr->member)
3364 continue;
cd9e6b16 3365 av[0] = ptr->member;
3366 av[1] = temp;
3367 if (ptr->type == (char *)GROUPS)
3368 {
3369 ptr->type = NULL;
3370 rc = mr_query("add_list_sid_by_name", 2, av, NULL, NULL);
3371 }
3372 else if (ptr->type == (char *)USERS)
3373 {
3374 ptr->type = NULL;
3375 rc = mr_query("add_user_sid_by_login", 2, av, NULL, NULL);
3376 }
3377 ptr = ptr->next;
3378 }
3379 return(0);
3380}
3381
3382void convert_b_to_a(char *string, UCHAR *binary, int length)
3383{
3384 int i;
3385 int j;
3386 UCHAR tmp;
3387
3388 j = 0;
3389 for (i = 0; i < length; i++)
3390 {
3391 tmp = binary[i];
3392 string[j] = tmp;
3393 string[j] >>= 4;
3394 string[j] &= 0x0f;
3395 string[j] += 0x30;
3396 if (string[j] > '9')
3397 string[j] += 0x27;
3398 ++j;
3399 string[j] = tmp & 0x0f;
3400 string[j] += 0x30;
3401 if (string[j] > '9')
3402 string[j] += 0x27;
3403 j++;
3404 }
3405 string[j] = 0;
3406}
3407
3408static int illegalchars[] = {
3409 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^@ - ^O */
3410 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* ^P - ^_ */
3411 1, 1, 1, 1, 0, 1, 0, 0, 1, 1, 1, 1, 1, 0, 0, 1, /* SPACE - / */
3412 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, /* 0 - ? */
f75f605a 3413 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, /* @ - O */
cd9e6b16 3414 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 0, /* P - _ */
3415 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, /* ` - o */
3416 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 1, 1, 1, 0, 1, /* p - ^? */
3417 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3418 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3419 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3420 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3421 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3422 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3423 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3424 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
3425};
3426
3427int check_string(char *s)
3428{
78af4e6e 3429 char character;
3430
cd9e6b16 3431 for (; *s; s++)
3432 {
78af4e6e 3433 character = *s;
3434 if (isupper(character))
3435 character = tolower(character);
3436 if (illegalchars[(unsigned) character])
cd9e6b16 3437 return 0;
3438 }
3439 return 1;
3440}
3441
bb52f279 3442int check_container_name(char *s)
3443{
3444 char character;
3445
3446 for (; *s; s++)
3447 {
3448 character = *s;
3449 if (isupper(character))
3450 character = tolower(character);
3451
3452 if (character == ' ')
3453 continue;
3454 if (illegalchars[(unsigned) character])
3455 return 0;
3456 }
3457 return 1;
3458}
3459
cd9e6b16 3460int mr_connect_cl(char *server, char *client, int version, int auth)
3461{
984c91b7 3462 int status;
3463 char *motd;
3464 char temp[128];
cd9e6b16 3465
3466 status = mr_connect(server);
3467 if (status)
3468 {
3469 com_err(whoami, status, "while connecting to Moira");
aea5154c 3470 return status;
cd9e6b16 3471 }
3472
3473 status = mr_motd(&motd);
3474 if (status)
3475 {
3476 mr_disconnect();
3477 com_err(whoami, status, "while checking server status");
aea5154c 3478 return status;
cd9e6b16 3479 }
3480 if (motd)
3481 {
984c91b7 3482 sprintf(temp, "The Moira server is currently unavailable: %s", motd);
3483 com_err(whoami, status, temp);
cd9e6b16 3484 mr_disconnect();
aea5154c 3485 return status;
cd9e6b16 3486 }
3487
3488 status = mr_version(version);
3489 if (status)
3490 {
3491 if (status == MR_UNKNOWN_PROC)
f78c7eaf 3492 {
3493 if (version > 2)
3494 status = MR_VERSION_HIGH;
3495 else
3496 status = MR_SUCCESS;
3497 }
cd9e6b16 3498
3499 if (status == MR_VERSION_HIGH)
f78c7eaf 3500 {
3501 com_err(whoami, 0, "Warning: This client is running newer code than the server.");
3502 com_err(whoami, 0, "Some operations may not work.");
3503 }
cd9e6b16 3504 else if (status && status != MR_VERSION_LOW)
f78c7eaf 3505 {
3506 com_err(whoami, status, "while setting query version number.");
3507 mr_disconnect();
aea5154c 3508 return status;
f78c7eaf 3509 }
cd9e6b16 3510 }
3511
3512 if (auth)
3513 {
3514 status = mr_auth(client);
3515 if (status)
f78c7eaf 3516 {
3517 com_err(whoami, status, "while authenticating to Moira.");
3518 mr_disconnect();
aea5154c 3519 return status;
f78c7eaf 3520 }
cd9e6b16 3521 }
3522
aea5154c 3523 return MR_SUCCESS;
cd9e6b16 3524}
3525
f78c7eaf 3526void AfsToWinAfs(char* path, char* winPath)
3527{
3528 char* pathPtr;
3529 char* winPathPtr;
3530 strcpy(winPath, WINAFS);
3531 pathPtr = path + strlen(AFS);
3532 winPathPtr = winPath + strlen(WINAFS);
3533
3534 while (*pathPtr)
3535 {
3536 if (*pathPtr == '/')
3537 *winPathPtr = '\\';
3538 else
3539 *winPathPtr = *pathPtr;
3540
3541 pathPtr++;
3542 winPathPtr++;
3543 }
3544}
89db421e 3545
909e0dc3 3546int GetAceInfo(int ac, char **av, void *ptr)
3547{
3548 char **call_args;
3549 int security_flag;
3550
3551 call_args = ptr;
3552
3553 strcpy(call_args[0], av[L_ACE_TYPE]);
3554 strcpy(call_args[1], av[L_ACE_NAME]);
3555 security_flag = 0;
3556 get_group_membership(call_args[2], call_args[3], &security_flag, av);
3557 return(LDAP_SUCCESS);
3558
3559}
3560
3561int checkAce(LDAP *ldap_handle, char *dn_path, char *Name)
3562{
3563 char filter[128];
3564 char *attr_array[3];
3565 int group_count;
3566 int rc;
3567 LK_ENTRY *group_base;
3568
3569 group_count = 0;
3570 group_base = NULL;
3571
3572 sprintf(filter, "(sAMAccountName=%s)", Name);
3573 attr_array[0] = "sAMAccountName";
3574 attr_array[1] = NULL;
3575 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3576 &group_base, &group_count)) != 0)
3577 {
3578 com_err(whoami, 0, "LDAP server couldn't process ACE name %s : %s",
3579 Name, ldap_err2string(rc));
3580 return(1);
3581 }
3582
3583 linklist_free(group_base);
3584 group_base = NULL;
3585 if (group_count == 0)
3586 return(0);
3587 return(1);
3588}
3589
3590#define MAX_ACE 7
3591
3592int ProcessAce(LDAP *ldap_handle, char *dn_path, char *Name, char *Type, int UpdateGroup, int *ProcessGroup)
3593{
3594 char *av[2];
3595 char GroupName[256];
3596 char *call_args[7];
3597 int rc;
3598 char *AceInfo[4];
3599 char AceType[32];
3600 char AceName[128];
3601 char AceMembership[2];
3602 char AceOu[256];
3603 char temp[128];
3604
3605 strcpy(GroupName, Name);
3606
3607 if (strcasecmp(Type, "LIST"))
3608 return(1);
3609 while (1)
3610 {
3611 av[0] = GroupName;
3612 AceInfo[0] = AceType;
3613 AceInfo[1] = AceName;
3614 AceInfo[2] = AceMembership;
3615 AceInfo[3] = AceOu;
3616 memset(AceType, '\0', sizeof(AceType));
3617 memset(AceName, '\0', sizeof(AceName));
3618 memset(AceMembership, '\0', sizeof(AceMembership));
3619 memset(AceOu, '\0', sizeof(AceOu));
3620 callback_rc = 0;
3621 if (rc = mr_query("get_list_info", 1, av, GetAceInfo, AceInfo))
3622 {
3623 com_err(whoami, 0, "Couldn't get ACE info for list %s : %s", GroupName, error_message(rc));
3624 return(1);
3625 }
3626 if (callback_rc)
3627 {
3628 com_err(whoami, 0, "Couldn't get ACE info for list %s", GroupName);
3629 return(1);
3630 }
3631 if ((strcasecmp(AceType, "USER")) && (strcasecmp(AceType, "LIST")))
3632 return(0);
3633 strcpy(temp, AceName);
3634 if (!strcasecmp(AceType, "LIST"))
3635 sprintf(temp, "%s_group", AceName);
3636 if (!UpdateGroup)
3637 {
3638 if (checkAce(ldap_handle, dn_path, temp))
3639 return(0);
3640 (*ProcessGroup) = 1;
3641 }
3642 if (!strcasecmp(AceInfo[0], "LIST"))
3643 {
3644 if (make_new_group(ldap_handle, dn_path, "", AceName, AceOu, AceMembership, 0, UpdateGroup))
3645 return(1);
3646 }
3647 else if (!strcasecmp(AceInfo[0], "USER"))
3648 {
3649 av[0] = AceName;
3650 call_args[0] = (char *)ldap_handle;
3651 call_args[1] = dn_path;
3652 call_args[2] = "";
3653 call_args[3] = NULL;
3654 sid_base = NULL;
3655 sid_ptr = &sid_base;
3656 callback_rc = 0;
3657 if (rc = mr_query("get_user_account_by_login", 1, av, user_create, call_args))
3658 {
3659 com_err(whoami, 0, "Couldn't process user ACE %s for group %s.", Name, AceName);
3660 return(1);
3661 }
3662 if (callback_rc)
3663 {
3664 com_err(whoami, 0, "Couldn't process user Ace %s for group %s", Name, AceName);
3665 return(1);
3666 }
3667 if (sid_base != NULL)
3668 {
3669 sid_update(ldap_handle, dn_path);
3670 linklist_free(sid_base);
3671 sid_base = NULL;
3672 }
3673 return(0);
3674 }
3675 else
3676 return(1);
3677 if (!strcasecmp(AceType, "LIST"))
3678 {
3679 if (!strcasecmp(GroupName, AceName))
3680 return(0);
3681 }
3682 strcpy(GroupName, AceName);
3683 }
3684 return(1);
3685}
3686
89db421e 3687int make_new_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
3688 char *group_name, char *group_ou, char *group_membership,
3689 int group_security_flag, int updateGroup)
3690{
3691 char *av[3];
3692 char *call_args[7];
3693 int rc;
3694
3695 av[0] = group_name;
3696 call_args[0] = (char *)ldap_handle;
3697 call_args[1] = dn_path;
3698 call_args[2] = group_name;
3699 call_args[3] = (char *)(MOIRA_USERS | MOIRA_KERBEROS | MOIRA_STRINGS);
3700 call_args[4] = (char *)updateGroup;
3701 call_args[5] = MoiraId;
3702 call_args[6] = NULL;
3703 sid_base = NULL;
3704 sid_ptr = &sid_base;
3705 callback_rc = 0;
3706 if (rc = mr_query("get_list_info", 1, av, group_create, call_args))
3707 {
3708 moira_disconnect();
3709 com_err(whoami, 0, "Couldn't create list %s : %s", group_name, error_message(rc));
3710 return(rc);
3711 }
3712 if (callback_rc)
3713 {
3714 moira_disconnect();
3715 com_err(whoami, 0, "Couldn't create list %s", group_name);
3716 return(callback_rc);
3717 }
3718
3719 if (sid_base != NULL)
3720 {
3721 sid_update(ldap_handle, dn_path);
3722 linklist_free(sid_base);
3723 sid_base = NULL;
3724 }
3725 return(0);
3726}
3727
3728int populate_group(LDAP *ldap_handle, char *dn_path, char *group_name,
3729 char *group_ou, char *group_membership,
3730 int group_security_flag, char *MoiraId)
3731{
3732 char *av[3];
3733 char *call_args[7];
3734 char *pUserOu;
3735 LK_ENTRY *ptr;
3736 int rc;
3737
3738 com_err(whoami, 0, "Populating group %s", group_name);
3739 av[0] = group_name;
3740 call_args[0] = (char *)ldap_handle;
3741 call_args[1] = dn_path;
3742 call_args[2] = group_name;
3743 call_args[3] = (char *)(MOIRA_USERS | MOIRA_KERBEROS | MOIRA_STRINGS);
3744 call_args[4] = NULL;
3745 member_base = NULL;
3746 if (rc = mr_query("get_end_members_of_list", 1, av,
3747 member_list_build, call_args))
3748 {
3749 com_err(whoami, 0, "Couldn't populate list %s : %s",
3750 group_name, error_message(rc));
3751 return(3);
3752 }
3753 if (member_base != NULL)
3754 {
3755 ptr = member_base;
3756 while (ptr != NULL)
3757 {
3758 if (!strcasecmp(ptr->type, "LIST"))
3759 {
3760 ptr = ptr->next;
3761 continue;
3762 }
3763 pUserOu = user_ou;
3764 if (!strcasecmp(ptr->type, "STRING"))
3765 {
3766 if (contact_create(ldap_handle, dn_path, ptr->member, contact_ou))
3767 return(3);
3768 pUserOu = contact_ou;
3769 }
3770 else if (!strcasecmp(ptr->type, "KERBEROS"))
3771 {
3772 if (contact_create(ldap_handle, dn_path, ptr->member, kerberos_ou))
3773 return(3);
3774 pUserOu = kerberos_ou;
3775 }
3776 rc = member_add(ldap_handle, dn_path, group_name,
3777 group_ou, group_membership, ptr->member,
3778 pUserOu, MoiraId);
3779 ptr = ptr->next;
3780 }
3781 linklist_free(member_base);
3782 member_base = NULL;
3783 }
3784 return(0);
3785}
3786
3787int process_group(LDAP *ldap_handle, char *dn_path, char *MoiraId,
3788 char *group_name, char *group_ou, char *group_membership,
3789 int group_security_flag, int type)
3790{
3791 char before_desc[512];
3792 char before_name[256];
3793 char before_group_ou[256];
3794 char before_group_membership[2];
3795 char distinguishedName[256];
3796 char ad_distinguishedName[256];
3797 char filter[128];
3798 char *attr_array[3];
3799 int before_security_flag;
3800 int group_count;
3801 int rc;
3802 LK_ENTRY *group_base;
3803 LK_ENTRY *ptr;
3804 char ou_both[512];
3805 char ou_security[512];
3806 char ou_distribution[512];
3807 char ou_neither[512];
3808
3809 memset(ad_distinguishedName, '\0', sizeof(ad_distinguishedName));
3810 sprintf(distinguishedName, "CN=%s,%s,%s", group_name, group_ou, dn_path);
3811
3812
3813 memset(filter, '\0', sizeof(filter));
3814 group_base = NULL;
3815 group_count = 0;
3816 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
3817 "*", MoiraId,
3818 "distinguishedName", &group_base,
3819 &group_count, filter))
3820 return(rc);
3821
3822 if (type == CHECK_GROUPS)
3823 {
3824 if (group_count == 1)
3825 {
3826 if (!strcasecmp(group_base->value, distinguishedName))
3827 {
3828 linklist_free(group_base);
3829 return(0);
3830 }
3831 }
3832 linklist_free(group_base);
3833 if (group_count == 0)
3834 return(AD_NO_GROUPS_FOUND);
3835 if (group_count == 1)
3836 return(AD_WRONG_GROUP_DN_FOUND);
3837 return(AD_MULTIPLE_GROUPS_FOUND);
3838 }
3839 if (group_count == 0)
3840 {
3841 return(AD_NO_GROUPS_FOUND);
3842 }
3843 if (group_count > 1)
3844 {
3845 ptr = group_base;
3846 while (ptr != NULL)
3847 {
3848 if (!strcasecmp(distinguishedName, ptr->value))
3849 break;
3850 ptr = ptr->next;
3851 }
3852 if (ptr == NULL)
3853 {
3854 com_err(whoami, 0, "%d groups with moira id = %s", group_count, MoiraId);
3855 ptr = group_base;
3856 while (ptr != NULL)
3857 {
3858 com_err(whoami, 0, "%s with moira id = %s", ptr->value, MoiraId);
3859 ptr = ptr->next;
3860 }
3861 linklist_free(group_base);
3862 return(AD_MULTIPLE_GROUPS_FOUND);
6c8f12af 3863 }
89db421e 3864 ptr = group_base;
3865 while (ptr != NULL)
3866 {
3867 if (strcasecmp(distinguishedName, ptr->value))
3868 rc = ldap_delete_s(ldap_handle, ptr->value);
3869 ptr = ptr->next;
3870 }
3871 linklist_free(group_base);
3872 memset(filter, '\0', sizeof(filter));
3873 group_base = NULL;
3874 group_count = 0;
3875 if (rc = ad_get_group(ldap_handle, dn_path, group_name,
3876 "*", MoiraId,
3877 "distinguishedName", &group_base,
3878 &group_count, filter))
3879 return(rc);
3880 if (group_count == 0)
3881 return(AD_NO_GROUPS_FOUND);
3882 if (group_count > 1)
3883 return(AD_MULTIPLE_GROUPS_FOUND);
3884 }
3885
3886 strcpy(ad_distinguishedName, group_base->value);
3887 linklist_free(group_base);
3888 group_base = NULL;
3889 group_count = 0;
3890
3891 attr_array[0] = "sAMAccountName";
3892 attr_array[1] = NULL;
3893 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3894 &group_base, &group_count)) != 0)
3895 {
3896 com_err(whoami, 0, "LDAP server unable to get list info with MoiraId = %s: %s",
3897 MoiraId, ldap_err2string(rc));
3898 return(rc);
3899 }
3900 sprintf(filter, "(sAMAccountName=%s)", group_base->value);
3901
3902 if (!strcasecmp(ad_distinguishedName, distinguishedName))
3903 {
3904 linklist_free(group_base);
3905 group_base = NULL;
3906 group_count = 0;
3907 return(0);
3908 }
3909 linklist_free(group_base);
3910 group_base = NULL;
3911 group_count = 0;
3912 memset(ou_both, '\0', sizeof(ou_both));
3913 memset(ou_security, '\0', sizeof(ou_security));
3914 memset(ou_distribution, '\0', sizeof(ou_distribution));
3915 memset(ou_neither, '\0', sizeof(ou_neither));
3916 memset(before_name, '\0', sizeof(before_name));
3917 memset(before_desc, '\0', sizeof(before_desc));
3918 memset(before_group_membership, '\0', sizeof(before_group_membership));
3919 attr_array[0] = "name";
3920 attr_array[1] = NULL;
3921 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3922 &group_base, &group_count)) != 0)
3923 {
3924 com_err(whoami, 0, "LDAP server unable to get list name with MoiraId = %s: %s",
3925 MoiraId, ldap_err2string(rc));
3926 return(rc);
3927 }
3928 strcpy(before_name, group_base->value);
3929 linklist_free(group_base);
3930 group_base = NULL;
3931 group_count = 0;
3932 attr_array[0] = "description";
3933 attr_array[1] = NULL;
3934 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
3935 &group_base, &group_count)) != 0)
3936 {
3937 com_err(whoami, 0,
3938 "LDAP server unable to get list description with MoiraId = %s: %s",
3939 MoiraId, ldap_err2string(rc));
3940 return(rc);
3941 }
c0bd7667 3942 if (group_count != 0)
3943 {
3944 strcpy(before_desc, group_base->value);
3945 linklist_free(group_base);
3946 group_base = NULL;
3947 group_count = 0;
3948 }
89db421e 3949 change_to_lower_case(ad_distinguishedName);
3950 strcpy(ou_both, group_ou_both);
3951 change_to_lower_case(ou_both);
3952 strcpy(ou_security, group_ou_security);
3953 change_to_lower_case(ou_security);
3954 strcpy(ou_distribution, group_ou_distribution);
3955 change_to_lower_case(ou_distribution);
3956 strcpy(ou_neither, group_ou_neither);
3957 change_to_lower_case(ou_neither);
3958 if (strstr(ad_distinguishedName, ou_both))
3959 {
3960 strcpy(before_group_ou, group_ou_both);
3961 before_group_membership[0] = 'B';
3962 before_security_flag = 1;
3963 }
3964 else if (strstr(ad_distinguishedName, ou_security))
3965 {
3966 strcpy(before_group_ou, group_ou_security);
3967 before_group_membership[0] = 'S';
3968 before_security_flag = 1;
3969 }
3970 else if (strstr(ad_distinguishedName, ou_distribution))
3971 {
3972 strcpy(before_group_ou, group_ou_distribution);
3973 before_group_membership[0] = 'D';
3974 before_security_flag = 0;
3975 }
3976 else if (strstr(ad_distinguishedName, ou_neither))
3977 {
3978 strcpy(before_group_ou, group_ou_neither);
3979 before_group_membership[0] = 'N';
3980 before_security_flag = 0;
3981 }
3982 else
3983 return(AD_NO_OU_FOUND);
3984 rc = group_rename(ldap_handle, dn_path, before_name, before_group_membership,
3985 before_group_ou, before_security_flag, before_desc,
3986 group_name, group_membership, group_ou, group_security_flag,
3987 before_desc, MoiraId, filter);
3988 return(rc);
3989}
3990
3991void change_to_lower_case(char *ptr)
3992{
3993 int i;
3994
3995 for (i = 0; i < (int)strlen(ptr); i++)
3996 {
3997 ptr[i] = tolower(ptr[i]);
3998 }
3999}
4000
4001int ad_get_group(LDAP *ldap_handle, char *dn_path,
4002 char *group_name, char *group_membership,
4003 char *MoiraId, char *attribute,
4004 LK_ENTRY **linklist_base, int *linklist_count,
4005 char *rFilter)
4006{
3e586ecf 4007 LK_ENTRY *pPtr;
c0bd7667 4008 char filter[128];
4009 char *attr_array[3];
89db421e 4010 int rc;
4011
4012 (*linklist_base) = NULL;
4013 (*linklist_count) = 0;
4014 if (strlen(rFilter) != 0)
4015 {
4016 strcpy(filter, rFilter);
4017 attr_array[0] = attribute;
4018 attr_array[1] = NULL;
4019 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4020 linklist_base, linklist_count)) != 0)
4021 {
4022 com_err(whoami, 0, "LDAP server unable to get list info with MoiraId = %s: %s",
4023 MoiraId, ldap_err2string(rc));
4024 return(rc);
4025 }
4026 if ((*linklist_count) == 1)
4027 {
4028 strcpy(rFilter, filter);
4029 return(0);
4030 }
4031 }
4032
4033 linklist_free((*linklist_base));
4034 (*linklist_base) = NULL;
4035 (*linklist_count) = 0;
4036 if (strlen(MoiraId) != 0)
4037 {
c0bd7667 4038 sprintf(filter, "(&(objectClass=group)(mitMoiraId=%s))", MoiraId);
89db421e 4039 attr_array[0] = attribute;
4040 attr_array[1] = NULL;
4041 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4042 linklist_base, linklist_count)) != 0)
4043 {
4044 com_err(whoami, 0, "LDAP server unable to get list info with MoiraId = %s: %s",
4045 MoiraId, ldap_err2string(rc));
4046 return(rc);
4047 }
4048 }
3e586ecf 4049 if ((*linklist_count) > 1)
4050 {
4051 com_err(whoami, 0, "multiple groups with mitMoiraId = %s", MoiraId);
4052 pPtr = (*linklist_base);
4053 while (pPtr)
4054 {
4055 com_err(whoami, 0, "groups %s has mitMoiraId = %s", pPtr->value, MoiraId);
4056 pPtr = pPtr->next;
4057 }
4058 linklist_free((*linklist_base));
4059 (*linklist_base) = NULL;
4060 (*linklist_count) = 0;
4061 }
89db421e 4062 if ((*linklist_count) == 1)
4063 {
909e0dc3 4064 if (!memcmp(&(*linklist_base)->value[3], group_name, strlen(group_name)))
4065 {
4066 strcpy(rFilter, filter);
4067 return(0);
4068 }
89db421e 4069 }
4070
4071 linklist_free((*linklist_base));
4072 (*linklist_base) = NULL;
4073 (*linklist_count) = 0;
4074 sprintf(filter, "(sAMAccountName=%s_group)", group_name);
4075 attr_array[0] = attribute;
4076 attr_array[1] = NULL;
4077 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4078 linklist_base, linklist_count)) != 0)
4079 {
4080 com_err(whoami, 0, "LDAP server unable to get list info with MoiraId = %s: %s",
4081 MoiraId, ldap_err2string(rc));
4082 return(rc);
4083 }
4084 if ((*linklist_count) == 1)
4085 {
4086 strcpy(rFilter, filter);
4087 return(0);
4088 }
4089
89db421e 4090 return(0);
4091}
4092
4093int check_user(LDAP *ldap_handle, char *dn_path, char *UserName, char *MoiraId)
4094{
4095 char filter[128];
4096 char *attr_array[3];
4097 char SamAccountName[64];
4098 int group_count;
4099 int rc;
4100 LK_ENTRY *group_base;
c0bd7667 4101 LK_ENTRY *gPtr;
89db421e 4102
4103 group_count = 0;
4104 group_base = NULL;
4105
4106 if (strlen(MoiraId) != 0)
4107 {
c0bd7667 4108 sprintf(filter, "(&(objectClass=user)(mitMoiraId=%s))", MoiraId);
89db421e 4109 attr_array[0] = "sAMAccountName";
4110 attr_array[1] = NULL;
4111 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4112 &group_base, &group_count)) != 0)
4113 {
4114 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
4115 UserName, ldap_err2string(rc));
4116 return(rc);
4117 }
c0bd7667 4118 if (group_count > 1)
4119 {
4120 com_err(whoami, 0, "multiple users exist with MoiraId = %s",
4121 MoiraId);
4122 gPtr = group_base;
4123 while (gPtr)
4124 {
4125 com_err(whoami, 0, "user %s exist with MoiraId = %s",
4126 gPtr->value, MoiraId);
4127 gPtr = gPtr->next;
4128 }
4129 }
89db421e 4130 }
c0bd7667 4131 if (group_count != 1)
89db421e 4132 {
c0bd7667 4133 linklist_free(group_base);
4134 group_count = 0;
4135 group_base = NULL;
89db421e 4136 sprintf(filter, "(sAMAccountName=%s)", UserName);
4137 attr_array[0] = "sAMAccountName";
4138 attr_array[1] = NULL;
4139 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4140 &group_base, &group_count)) != 0)
4141 {
4142 com_err(whoami, 0, "LDAP server couldn't process user %s : %s",
4143 UserName, ldap_err2string(rc));
4144 return(rc);
4145 }
4146 }
4147
4148 if (group_count != 1)
4149 {
4150 linklist_free(group_base);
4151 return(AD_NO_USER_FOUND);
4152 }
4153 strcpy(SamAccountName, group_base->value);
4154 linklist_free(group_base);
4155 group_count = 0;
4156 rc = 0;
4157 if (strcmp(SamAccountName, UserName))
4158 {
4159 rc = user_rename(ldap_handle, dn_path, SamAccountName,
4160 UserName);
4161 }
4162 return(0);
4163}
6c8f12af 4164
4165void container_get_dn(char *src, char *dest)
4166{
4167 char *sPtr;
4168 char *array[20];
4169 char name[256];
4170 int n;
4171
4172 memset(array, '\0', 20 * sizeof(array[0]));
4173
4174 if (strlen(src) == 0)
4175 return;
4176 strcpy(name, src);
4177 sPtr = name;
4178 n = 0;
4179 array[n] = name;
4180 ++n;
4181 while (*sPtr)
4182 {
4183 if ((*sPtr) == '/')
4184 {
4185 (*sPtr) = '\0';
4186 ++sPtr;
4187 array[n] = sPtr;
4188 ++n;
4189 }
4190 else
4191 ++sPtr;
4192 }
4193 strcpy(dest, "OU=");
4194 while (n != 0)
4195 {
4196 strcat(dest, array[n-1]);
4197 --n;
4198 if (n > 0)
4199 {
4200 strcat(dest, ",OU=");
4201 }
4202 }
4203 return;
4204}
4205
4206void container_get_name(char *src, char *dest)
4207{
4208 char *sPtr;
4209 char *dPtr;
4210
4211 if (strlen(src) == 0)
4212 return;
4213 sPtr = src;
4214 dPtr = src;
4215 while (*sPtr)
4216 {
4217 if ((*sPtr) == '/')
4218 {
4219 dPtr = sPtr;
4220 ++dPtr;
4221 }
4222 ++sPtr;
4223 }
4224 strcpy(dest, dPtr);
4225 return;
4226}
4227
4228void container_check(LDAP *ldap_handle, char *dn_path, char *name)
4229{
4230 char cName[256];
4231 char *av[7];
4232 int i;
4233 int rc;
4234
4235 strcpy(cName, name);
4236 for (i = 0; i < (int)strlen(cName); i++)
4237 {
4238 if (cName[i] == '/')
4239 {
4240 cName[i] = '\0';
4241 av[CONTAINER_NAME] = cName;
4242 av[CONTAINER_DESC] = "";
4243 av[CONTAINER_LOCATION] = "";
4244 av[CONTAINER_CONTACT] = "";
4245 av[CONTAINER_TYPE] = "";
4246 av[CONTAINER_ID] = "";
4247 av[CONTAINER_ROWID] = "";
4248 rc = container_create(ldap_handle, dn_path, 7, av);
4249 if (rc == LDAP_SUCCESS)
4250 {
4251 com_err(whoami, 0, "container %s created without a mitMoiraId", cName);
4252 }
4253 cName[i] = '/';
4254 }
4255 }
4256
4257}
4258
4259int container_rename(LDAP *ldap_handle, char *dn_path, int beforec, char **before,
4260 int afterc, char **after)
4261{
4262 char dName[256];
4263 char cName[256];
4264 char new_cn[128];
4265 char new_dn_path[256];
4266 char temp[256];
4267 char distinguishedName[256];
4268 char *pPtr;
4269 int rc;
4270 int i;
4271
4272 memset(cName, '\0', sizeof(cName));
4273 container_get_name(after[CONTAINER_NAME], cName);
bb52f279 4274 if (!check_container_name(cName))
6c8f12af 4275 {
4276 com_err(whoami, 0, "invalid LDAP container name %s", cName);
4277 return(AD_INVALID_NAME);
4278 }
4279
4280 memset(distinguishedName, '\0', sizeof(distinguishedName));
4281 if (rc = container_get_distinguishedName(ldap_handle, dn_path, distinguishedName, beforec, before))
4282 return(rc);
4283 if (strlen(distinguishedName) == 0)
4284 {
4285 rc = container_create(ldap_handle, dn_path, afterc, after);
4286 return(rc);
4287 }
4288
4289 strcpy(temp, after[CONTAINER_NAME]);
9cfe334f 4290 pPtr = temp;
6c8f12af 4291 for (i = 0; i < (int)strlen(temp); i++)
4292 {
4293 if (temp[i] == '/')
4294 {
4295 pPtr = &temp[i];
4296 }
4297 }
9cfe334f 4298 (*pPtr) = '\0';
6c8f12af 4299
4300 container_get_dn(temp, dName);
9cfe334f 4301 if (strlen(temp) != 0)
4302 sprintf(new_dn_path, "%s,%s", dName, dn_path);
4303 else
4304 sprintf(new_dn_path, "%s", dn_path);
6c8f12af 4305 sprintf(new_cn, "OU=%s", cName);
4306
4307 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
4308
4309 if ((rc = ldap_rename_s(ldap_handle, distinguishedName, new_cn, new_dn_path,
4310 TRUE, NULL, NULL)) != LDAP_SUCCESS)
4311 {
4312 com_err(whoami, 0, "couldn't rename container from %s to %s : %s",
4313 before[CONTAINER_NAME], after[CONTAINER_NAME], ldap_err2string(rc));
4314 return(rc);
4315 }
4316
4317 memset(dName, '\0', sizeof(dName));
4318 container_get_dn(after[CONTAINER_NAME], dName);
4319 rc = container_adupdate(ldap_handle, dn_path, dName, "", afterc, after);
4320 return(rc);
4321}
4322
4323int container_delete(LDAP *ldap_handle, char *dn_path, int count, char **av)
4324{
4325 char distinguishedName[256];
4326 int rc;
4327
4328 memset(distinguishedName, '\0', sizeof(distinguishedName));
4329 if (rc = container_get_distinguishedName(ldap_handle, dn_path, distinguishedName, count, av))
4330 return(rc);
4331 if (strlen(distinguishedName) == 0)
4332 return(0);
4333 if ((rc = ldap_delete_s(ldap_handle, distinguishedName)) != LDAP_SUCCESS)
4334 {
4335 if (rc == LDAP_NOT_ALLOWED_ON_NONLEAF)
4336 container_move_objects(ldap_handle, dn_path, distinguishedName);
4337 else
4338 com_err(whoami, 0, "unable to delete container %s from AD : %s",
4339 av[CONTAINER_NAME], ldap_err2string(rc));
4340 }
4341 return(rc);
4342}
4343int container_create(LDAP *ldap_handle, char *dn_path, int count, char **av)
4344{
4345 char *attr_array[3];
4346 LK_ENTRY *group_base;
4347 int group_count;
4348 LDAPMod *mods[20];
4349 char *objectClass_v[] = {"top",
4350 "organizationalUnit",
4351 NULL};
4352
4353 char *ou_v[] = {NULL, NULL};
4354 char *name_v[] = {NULL, NULL};
4355 char *moiraId_v[] = {NULL, NULL};
4356 char *desc_v[] = {NULL, NULL};
4357 char *managedBy_v[] = {NULL, NULL};
4358 char dName[256];
4359 char cName[256];
4360 char managedByDN[256];
4361 char filter[256];
4362 char temp[256];
4363 int n;
4364 int i;
4365 int rc;
4366
4367 memset(filter, '\0', sizeof(filter));
4368 memset(dName, '\0', sizeof(dName));
4369 memset(cName, '\0', sizeof(cName));
4370 memset(managedByDN, '\0', sizeof(managedByDN));
4371 container_get_dn(av[CONTAINER_NAME], dName);
4372 container_get_name(av[CONTAINER_NAME], cName);
4373
4374 if ((strlen(cName) == 0) || (strlen(dName) == 0))
4375 {
4376 com_err(whoami, 0, "invalid LDAP container name %s", cName);
4377 return(AD_INVALID_NAME);
4378 }
4379
bb52f279 4380 if (!check_container_name(cName))
6c8f12af 4381 {
4382 com_err(whoami, 0, "invalid LDAP container name %s", cName);
4383 return(AD_INVALID_NAME);
4384 }
4385
4386 n = 0;
4387 ADD_ATTR("objectClass", objectClass_v, LDAP_MOD_ADD);
4388 name_v[0] = cName;
4389 ADD_ATTR("name", name_v, LDAP_MOD_ADD);
4390 ou_v[0] = cName;
4391 ADD_ATTR("ou", ou_v, LDAP_MOD_ADD);
4392 if (strlen(av[CONTAINER_ROWID]) != 0)
4393 {
4394 moiraId_v[0] = av[CONTAINER_ROWID];
4395 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_ADD);
4396 }
4397 if (strlen(av[CONTAINER_DESC]) != 0)
4398 {
4399 desc_v[0] = av[CONTAINER_DESC];
4400 ADD_ATTR("description", desc_v, LDAP_MOD_ADD);
4401 }
4402 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
4403 {
0eae7c9b 4404 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
4405 {
4406 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID], kerberos_ou))
4407 {
4408 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID], kerberos_ou,dn_path);
4409 managedBy_v[0] = managedByDN;
4410 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
4411 }
4412 }
4413 else
4414 {
4415 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
6c8f12af 4416 {
0eae7c9b 4417 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)(objectClass=user)))", av[CONTAINER_ID]);
6c8f12af 4418 }
0eae7c9b 4419 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
6c8f12af 4420 {
0eae7c9b 4421 sprintf(filter, "(&(objectClass=group)(cn=%s))", av[CONTAINER_ID]);
6c8f12af 4422 }
0eae7c9b 4423 if (strlen(filter) != 0)
6c8f12af 4424 {
4425 attr_array[0] = "distinguishedName";
4426 attr_array[1] = NULL;
4427 group_count = 0;
4428 group_base = NULL;
909e0dc3 4429 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6c8f12af 4430 &group_base, &group_count)) == LDAP_SUCCESS)
4431 {
4432 if (group_count == 1)
4433 {
4434 strcpy(managedByDN, group_base->value);
4435 managedBy_v[0] = managedByDN;
4436 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_ADD);
4437 }
4438 linklist_free(group_base);
4439 group_base = NULL;
4440 group_count = 0;
4441 }
4442 }
4443 }
0eae7c9b 4444 }
6c8f12af 4445 mods[n] = NULL;
4446
4447 sprintf(temp, "%s,%s", dName, dn_path);
4448 rc = ldap_add_ext_s(ldap_handle, temp, mods, NULL, NULL);
4449 for (i = 0; i < n; i++)
4450 free(mods[i]);
4451 if ((rc != LDAP_SUCCESS) && (rc != LDAP_ALREADY_EXISTS))
4452 {
4453 com_err(whoami, 0, "couldn't create container %s : %s",
4454 cName, ldap_err2string(rc));
4455 return(rc);
4456 }
4457 if (rc == LDAP_ALREADY_EXISTS)
4458 {
4459 if (strlen(av[CONTAINER_ROWID]) != 0)
4460 rc = container_adupdate(ldap_handle, dn_path, dName, "", count, av);
4461 }
4462 return(rc);
4463}
4464
4465int container_update(LDAP *ldap_handle, char *dn_path, int beforec, char **before,
4466 int afterc, char **after)
4467{
4468 char distinguishedName[256];
4469 int rc;
4470
4471 memset(distinguishedName, '\0', sizeof(distinguishedName));
4472 if (rc = container_get_distinguishedName(ldap_handle, dn_path, distinguishedName, afterc, after))
4473 return(rc);
4474 if (strlen(distinguishedName) == 0)
4475 {
4476 rc = container_create(ldap_handle, dn_path, afterc, after);
4477 return(rc);
4478 }
4479
4480 container_check(ldap_handle, dn_path, after[CONTAINER_NAME]);
4481 rc = container_adupdate(ldap_handle, dn_path, "", distinguishedName, afterc, after);
4482
4483 return(rc);
4484}
4485
4486int container_get_distinguishedName(LDAP *ldap_handle, char *dn_path, char *distinguishedName, int count, char **av)
4487{
4488 char *attr_array[3];
4489 LK_ENTRY *group_base;
4490 int group_count;
4491 char dName[256];
4492 char cName[256];
4493 char filter[512];
4494 int rc;
4495
4496 memset(filter, '\0', sizeof(filter));
4497 memset(dName, '\0', sizeof(dName));
4498 memset(cName, '\0', sizeof(cName));
4499 container_get_dn(av[CONTAINER_NAME], dName);
4500 container_get_name(av[CONTAINER_NAME], cName);
4501
4502 if (strlen(dName) == 0)
4503 {
4504 com_err(whoami, 0, "invalid LDAP container name %s", av[CONTAINER_NAME]);
4505 return(AD_INVALID_NAME);
4506 }
4507
bb52f279 4508 if (!check_container_name(cName))
6c8f12af 4509 {
4510 com_err(whoami, 0, "invalid LDAP container name %s", cName);
4511 return(AD_INVALID_NAME);
4512 }
4513
4514 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))", av[CONTAINER_ROWID]);
4515 attr_array[0] = "distinguishedName";
4516 attr_array[1] = NULL;
4517 group_count = 0;
4518 group_base = NULL;
4519 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4520 &group_base, &group_count)) == LDAP_SUCCESS)
4521 {
4522 if (group_count == 1)
4523 {
4524 strcpy(distinguishedName, group_base->value);
4525 }
4526 linklist_free(group_base);
4527 group_base = NULL;
4528 group_count = 0;
4529 }
4530 if (strlen(distinguishedName) == 0)
4531 {
4532 sprintf(filter, "(&(objectClass=organizationalUnit)(distinguishedName=%s,%s))", dName, dn_path);
4533 attr_array[0] = "distinguishedName";
4534 attr_array[1] = NULL;
4535 group_count = 0;
4536 group_base = NULL;
4537 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4538 &group_base, &group_count)) == LDAP_SUCCESS)
4539 {
4540 if (group_count == 1)
4541 {
4542 strcpy(distinguishedName, group_base->value);
4543 }
4544 linklist_free(group_base);
4545 group_base = NULL;
4546 group_count = 0;
4547 }
4548 }
4549 return(0);
4550}
4551
4552int container_adupdate(LDAP *ldap_handle, char *dn_path, char *dName,
4553 char *distinguishedName, int count, char **av)
4554{
4555 char *attr_array[5];
4556 LK_ENTRY *group_base;
4557 LK_ENTRY *pPtr;
4558 LDAPMod *mods[20];
4559 int group_count;
4560 char filter[512];
4561 char temp[256];
4562 char *moiraId_v[] = {NULL, NULL};
4563 char *desc_v[] = {NULL, NULL};
4564 char *managedBy_v[] = {NULL, NULL};
4565 char managedByDN[256];
4566 char moiraId[64];
4567 char desc[256];
4568 int rc;
4569 int i;
4570 int n;
4571
4572
4573 strcpy(temp, distinguishedName);
4574 if (strlen(dName) != 0)
4575 sprintf(temp, "%s,%s", dName, dn_path);
4576
4577 sprintf(filter, "(&(objectClass=organizationalUnit)(distinguishedName=%s))", temp);
4578 if (strlen(av[CONTAINER_ID]) != 0)
4579 sprintf(filter, "(&(objectClass=organizationalUnit)(mitMoiraId=%s))", av[CONTAINER_ROWID]);
4580 attr_array[0] = "mitMoiraId";
4581 attr_array[1] = "description";
4582 attr_array[2] = "managedBy";
4583 attr_array[3] = NULL;
4584 group_count = 0;
4585 group_base = NULL;
4586 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
4587 &group_base, &group_count)) != LDAP_SUCCESS)
4588 {
4589 com_err(whoami, 0, "couldn't retreive container info for %s : %s",
4590 av[CONTAINER_NAME], ldap_err2string(rc));
4591 return(rc);
4592 }
4593 memset(managedByDN, '\0', sizeof(managedByDN));
4594 memset(moiraId, '\0', sizeof(moiraId));
4595 memset(desc, '\0', sizeof(desc));
4596 pPtr = group_base;
4597 while (pPtr)
4598 {
4599 if (!strcasecmp(pPtr->attribute, "description"))
4600 strcpy(desc, pPtr->value);
9cfe334f 4601 else if (!strcasecmp(pPtr->attribute, "managedBy"))
6c8f12af 4602 strcpy(managedByDN, pPtr->value);
9cfe334f 4603 else if (!strcasecmp(pPtr->attribute, "mitMoiraId"))
6c8f12af 4604 strcpy(moiraId, pPtr->value);
4605 pPtr = pPtr->next;
4606 }
4607 linklist_free(group_base);
4608 group_base = NULL;
4609 group_count = 0;
4610
4611 n = 0;
4612 if (strlen(av[CONTAINER_ROWID]) != 0)
4613 {
4614 moiraId_v[0] = av[CONTAINER_ROWID];
4615 ADD_ATTR("mitMoiraId", moiraId_v, LDAP_MOD_REPLACE);
4616 }
4617 if (strlen(av[CONTAINER_DESC]) != 0)
4618 {
4619 desc_v[0] = av[CONTAINER_DESC];
4620 ADD_ATTR("description", desc_v, LDAP_MOD_REPLACE);
4621 }
4622 else
4623 {
4624 if (strlen(desc) != 0)
4625 {
4626 desc_v[0] = NULL;
4627 ADD_ATTR("description", desc_v, LDAP_MOD_REPLACE);
4628 }
4629 }
4630 if ((strlen(av[CONTAINER_TYPE]) != 0) && (strlen(av[CONTAINER_ID]) != 0))
4631 {
0eae7c9b 4632 if (!strcasecmp(av[CONTAINER_TYPE], "KERBEROS"))
4633 {
4634 if (!contact_create(ldap_handle, dn_path, av[CONTAINER_ID], kerberos_ou))
4635 {
4636 sprintf(managedByDN, "CN=%s,%s,%s", av[CONTAINER_ID], kerberos_ou, dn_path);
4637 managedBy_v[0] = managedByDN;
4638 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
4639 }
4640 else
4641 {
4642 if (strlen(managedByDN) != 0)
4643 {
4644 managedBy_v[0] = NULL;
4645 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
4646 }
4647 }
4648 }
4649 else
4650 {
4651 memset(filter, '\0', sizeof(filter));
4652 if (!strcasecmp(av[CONTAINER_TYPE], "USER"))
6c8f12af 4653 {
0eae7c9b 4654 sprintf(filter, "(&(cn=%s)(&(objectCategory=person)(objectClass=user)))", av[CONTAINER_ID]);
6c8f12af 4655 }
0eae7c9b 4656 if (!strcasecmp(av[CONTAINER_TYPE], "LIST"))
6c8f12af 4657 {
0eae7c9b 4658 sprintf(filter, "(&(objectClass=group)(cn=%s))", av[CONTAINER_ID]);
6c8f12af 4659 }
0eae7c9b 4660 if (strlen(filter) != 0)
6c8f12af 4661 {
4662 attr_array[0] = "distinguishedName";
4663 attr_array[1] = NULL;
4664 group_count = 0;
4665 group_base = NULL;
5f7b0741 4666 if ((rc = linklist_build(ldap_handle, dn_path, filter, attr_array,
6c8f12af 4667 &group_base, &group_count)) == LDAP_SUCCESS)
4668 {
4669 if (group_count == 1)
4670 {
4671 strcpy(managedByDN, group_base->value);
4672 managedBy_v[0] = managedByDN;
4673 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
4674 }
4675 else
4676 {
4677 if (strlen(managedByDN) != 0)
4678 {
4679 managedBy_v[0] = NULL;
4680 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
4681 }
4682 }
4683 linklist_free(group_base);
4684 group_base = NULL;
4685 group_count = 0;
4686 }
4687 }
0eae7c9b 4688 else
6c8f12af 4689 {
4690 if (strlen(managedByDN) != 0)
4691 {
4692 managedBy_v[0] = NULL;
4693 ADD_ATTR("managedBy", managedBy_v, LDAP_MOD_REPLACE);
4694 }
4695 }
0eae7c9b 4696 }
6c8f12af 4697 }
4698 mods[n] = NULL;
4699 if (n == 0)
4700 return(LDAP_SUCCESS);
4701
4702 strcpy(temp, distinguishedName);
4703 if (strlen(dName) != 0)
4704 sprintf(temp, "%s,%s", dName, dn_path);
4705 rc = ldap_modify_s(ldap_handle, temp, mods);
4706 for (i = 0; i < n; i++)
4707 free(mods[i]);
4708 if (rc != LDAP_SUCCESS)
4709 {
4710 com_err(whoami, 0, "couldn't modify container info for %s : %s",
4711 av[CONTAINER_NAME], ldap_err2string(rc));
4712 return(rc);
4713 }
4714 return(rc);
4715}
4716
4717int container_move_objects(LDAP *ldap_handle, char *dn_path, char *dName)
4718{
4719 char *attr_array[3];
4720 LK_ENTRY *group_base;
4721 LK_ENTRY *pPtr;
4722 int group_count;
4723 char filter[512];
4724 char new_cn[128];
4725 char temp[256];
4726 int rc;
4727 int NumberOfEntries = 10;
4728 int i;
4729 int count;
4730
4731 rc = ldap_set_option(ldap_handle, LDAP_OPT_SIZELIMIT, &NumberOfEntries);
4732
4733 for (i = 0; i < 3; i++)
4734 {
4735 memset(filter, '\0', sizeof(filter));
4736 if (i == 0)
4737 {
4738 strcpy(filter, "(!(|(objectClass=computer)(objectClass=organizationalUnit)))");
4739 attr_array[0] = "cn";
4740 attr_array[1] = NULL;
4741 }
4742 else if (i == 1)
4743 {
4744 strcpy(filter, "(objectClass=computer)");
4745 attr_array[0] = "cn";
4746 attr_array[1] = NULL;
4747 }
4748 else
4749 {
4750 strcpy(filter, "(objectClass=organizationalUnit)");
4751 attr_array[0] = "ou";
4752 attr_array[1] = NULL;
4753 }
4754
4755 while (1)
4756 {
4757 if ((rc = linklist_build(ldap_handle, dName, filter, attr_array,
4758 &group_base, &group_count)) != LDAP_SUCCESS)
4759 {
4760 break;
4761 }
4762 if (group_count == 0)
4763 break;
4764 pPtr = group_base;
4765 while(pPtr)
4766 {
4767 if (!strcasecmp(pPtr->attribute, "cn"))
4768 {
4769 sprintf(new_cn, "cn=%s", pPtr->value);
4770 if (i == 0)
4771 sprintf(temp, "%s,%s", orphans_other_ou, dn_path);
4772 if (i == 1)
4773 sprintf(temp, "%s,%s", orphans_machines_ou, dn_path);
4774 count = 1;
4775 while (1)
4776 {
4777 rc = ldap_rename_s(ldap_handle, pPtr->dn, new_cn, temp,
4778 TRUE, NULL, NULL);
4779 if (rc == LDAP_ALREADY_EXISTS)
4780 {
4781 sprintf(new_cn, "cn=%s_%d", pPtr->value, count);
4782 ++count;
4783 }
4784 else
4785 break;
4786 }
4787 }
4788 else if (!strcasecmp(pPtr->attribute, "ou"))
4789 {
4790 rc = ldap_delete_s(ldap_handle, pPtr->dn);
4791 }
4792 pPtr = pPtr->next;
4793 }
4794 linklist_free(group_base);
4795 group_base = NULL;
4796 group_count = 0;
4797 }
4798 }
4799 return(0);
4800}
5f7b0741 4801
4802int get_machine_ou(LDAP *ldap_handle, char *dn_path, char *member, char *machine_ou)
4803{
4804 LK_ENTRY *group_base;
4805 int group_count;
4806 int i;
4807 char filter[128];
4808 char *attr_array[3];
4809 char cn[256];
4810 char dn[256];
4811 char temp[256];
4812 char *pPtr;
4813 int rc;
4814
4815 pPtr = NULL;
4816 pPtr = strchr(member, '.');
4817 if (pPtr != NULL)
4818 (*pPtr) = '\0';
4819
4820 group_base = NULL;
4821 group_count = 0;
4822 sprintf(filter, "(sAMAccountName=%s$)", member);
4823 attr_array[0] = "cn";
4824 attr_array[1] = NULL;
4825 sprintf(temp, "%s", dn_path);
4826 if ((rc = linklist_build(ldap_handle, temp, filter, attr_array,
4827 &group_base, &group_count)) != 0)
4828 {
4829 com_err(whoami, 0, "LDAP server couldn't process machine %s : %s",
4830 member, ldap_err2string(rc));
4831 return(1);
4832 }
4833 if (group_count != 1)
4834 {
4835 com_err(whoami, 0, "LDAP server couldn't process machine %s : machine not found in AD",
4836 member);
4837 return(1);
4838 }
4839 strcpy(dn, group_base->dn);
4840 strcpy(cn, group_base->value);
4841 for (i = 0; i < (int)strlen(dn); i++)
4842 dn[i] = tolower(dn[i]);
4843 for (i = 0; i < (int)strlen(cn); i++)
4844 cn[i] = tolower(cn[i]);
4845 linklist_free(group_base);
4846 pPtr = NULL;
4847 pPtr = strstr(dn, cn);
4848 if (pPtr == NULL)
4849 {
4850 com_err(whoami, 0, "LDAP server couldn't process machine %s",
4851 member);
4852 return(1);
4853 }
4854 pPtr += strlen(cn) + 1;
4855 strcpy(machine_ou, pPtr);
4856 pPtr = NULL;
4857 pPtr = strstr(machine_ou, "dc=");
4858 if (pPtr == NULL)
4859 {
4860 com_err(whoami, 0, "LDAP server couldn't process machine %s",
4861 member);
4862 return(1);
4863 }
4864 --pPtr;
4865 (*pPtr) = '\0';
4866 return(0);
4867}
This page took 1.133265 seconds and 5 git commands to generate.