1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
|
Index: ldap_map.h
===================================================================
RCS file: /usr/local/src/cvsroot/sendmail.8.9/src/ldap_map.h,v
retrieving revision 1.1.1.8
retrieving revision 1.9
diff -u -r1.1.1.8 -r1.9
--- ldap_map.h 1999/02/15 19:35:30 1.1.1.8
+++ ldap_map.h 1999/02/15 20:04:06 1.9
@@ -37,8 +37,8 @@
/* args for ldap_bind_s */
LDAP *ld;
char *binddn;
- char *passwd;
- int method;
+ char *secret;
+ int method;
/* args for ldap_search_st */
char *base;
@@ -55,13 +55,32 @@
#define DEFAULT_LDAP_MAP_PORT LDAP_PORT
#define DEFAULT_LDAP_MAP_SCOPE LDAP_SCOPE_SUBTREE
#define DEFAULT_LDAP_MAP_BINDDN NULL
-#define DEFAULT_LDAP_MAP_PASSWD NULL
+#define DEFAULT_LDAP_MAP_SECRET NULL
#define DEFAULT_LDAP_MAP_METHOD LDAP_AUTH_SIMPLE
#define DEFAULT_LDAP_MAP_TIMELIMIT 5
#define DEFAULT_LDAP_MAP_DEREF LDAP_DEREF_NEVER
#define DEFAULT_LDAP_MAP_SIZELIMIT 0
#define DEFAULT_LDAP_MAP_ATTRSONLY 0
#define LDAP_MAP_MAX_FILTER 1024
+
+/* authentication methods available */
+
+#define LDAP_MAP_AUTH_METHOD_MAX 3
+#define LDAP_MAP_MAX_PASSWD 256
+
+char *ldap_map_auth_methods[] = {
+ "LDAP_AUTH_NONE",
+ "LDAP_AUTH_SIMPLE",
+ "LDAP_AUTH_KRBV4"
+} ;
+
+int ldap_map_auth_methods_code[LDAP_MAP_AUTH_METHOD_MAX] = {
+ LDAP_AUTH_NONE,
+ LDAP_AUTH_SIMPLE,
+ LDAP_AUTH_KRBV4
+} ;
+
+
#ifdef LDAP_REFERRALS
# define DEFAULT_LDAP_MAP_LDAP_OPTIONS LDAP_OPT_REFERRALS
#else /* LDAP_REFERRALS */
Index: map.c
===================================================================
RCS file: /usr/local/src/cvsroot/sendmail.8.9/src/map.c,v
retrieving revision 1.1.1.11
retrieving revision 1.20
diff -u -r1.1.1.11 -r1.20
--- map.c 1999/02/15 19:35:31 1.1.1.11
+++ map.c 1999/03/30 21:22:41 1.20
@@ -2621,6 +2621,10 @@
#endif
return FALSE;
}
+ /* We could call aliaswait here, but it only adds extra
+ code to the ldap map lookup. The aliaswait "@:@" convention
+ does not make much sense in the ldap tcp-based model.
+ */
return TRUE;
}
@@ -2647,7 +2651,7 @@
LDAP_MAP_STRUCT *lmap;
LDAP *ld;
register EVENT *ev = NULL;
-
+ register int bind_result;
if (tTd(38, 2))
printf("ldap_map_start(%s)\n", map->map_mname);
@@ -2713,12 +2717,12 @@
lmap->ld = ld;
return TRUE;
#else
- if (ldap_bind_s(ld, lmap->binddn,lmap->passwd,lmap->method) != LDAP_SUCCESS)
+ if (ldap_bind_s(ld, lmap->binddn,lmap->secret,lmap->method) != LDAP_SUCCESS)
{
if (!bitset(MF_OPTIONAL, map->map_mflags))
{
- syserr("421 Cannot bind to map %s in ldap server %s",
- map->map_mname, lmap->ldaphost);
+ syserr("421 Cannot bind to map %s in ldap server %s, %s",
+ map->map_mname, lmap->ldaphost,ldap_err2string(bind_result));
}
}
else
@@ -2727,7 +2731,6 @@
lmap->ld = ld;
return TRUE;
}
-
return FALSE;
#endif
}
@@ -2811,13 +2814,13 @@
{
LDAP_MAP_STRUCT *lmap = NULL;
LDAPMessage *entry;
- char *vp;
+ char *vp,*vp_tmp;
auto int vsize;
char keybuf[MAXNAME + 1];
char filter[LDAP_MAP_MAX_FILTER + 1];
char **attr_values = NULL;
- char *result;
- int name_len;
+ char *result,*tmp;
+ int name_len,val_count,i;
char *fp, *p, *q;
if (tTd(38, 20))
@@ -2899,39 +2902,88 @@
}
}
+ result = NULL;
+ *statp = EX_NOTFOUND;
+
entry = ldap_first_entry(lmap->ld,lmap->res);
if (entry == NULL)
{
- result = NULL;
- *statp = EX_NOTFOUND;
goto quick_exit;
}
- /* Need to build the args for map_rewrite here */
- attr_values = ldap_get_values(lmap->ld,entry,lmap->attr[0]);
- if (attr_values == NULL)
- {
- /* bad things happened */
- result = NULL;
- *statp = EX_NOTFOUND;
- goto quick_exit;
+ vp = NULL ;
+
+ /* Cycle through all entries. */
+ do {
+ /* Need to build the args for map_rewrite here */
+ attr_values = ldap_get_values(lmap->ld,entry,lmap->attr[0]);
+ if (attr_values != NULL )
+ {
+ *statp = EX_OK;
+
+ /*
+ * If there is more that one munge then into
+ * a comma sep string
+ */
+ val_count = ldap_count_values(attr_values) ;
+ /* count size */
+ vsize = 0 ;
+ for( i = 0 ; i < val_count && attr_values[i] != NULL ; i++ ) {
+ vsize += strlen(attr_values[i]) + strlen(", ") ;
+ }
+ vp_tmp = (char * ) malloc(vsize) ;
+ if ( vp_tmp != NULL )
+ {
+ /* first */
+ snprintf(vp_tmp,vsize,"%s",attr_values[0]) ;
+ tmp = vp_tmp + strlen(vp_tmp);
+ /*rest */
+ for( i = 1 ; i < (val_count ) && attr_values[i] != NULL ; i++ ) {
+ snprintf(tmp,(vsize - strlen(vp_tmp)),", %s",attr_values[i]) ;
+ tmp = vp_tmp + strlen(vp_tmp) ;
+ }
+
+ } else {
+ /* Report memory error */
+ if (!bitset(MF_OPTIONAL, map->map_mflags))
+ {
+ syserr("Out of memory in ldap_map_lookup");
+ }
+ }
+ }
+ if ( vp == NULL )
+ {
+ vp = vp_tmp ;
+ } else {
+ vsize = strlen(vp) + strlen(vp_tmp) + strlen(", ") + 1 ;
+ tmp = ( char *) malloc( vsize ) ;
+ snprintf(tmp,vsize,"%s, %s",vp,vp_tmp) ;
+ /* Free things in correct order. */
+ free ( vp_tmp) ; /* vsize malloc above */
+ vp_tmp = vp ; /* tmp malloc from previous loop */
+ vp = tmp ;
+ free ( vp_tmp ) ;
+ }
+ ldap_value_free(attr_values);
+ attr_values = NULL ;
+
+ } while ( (entry = ldap_next_entry( lmap->ld, entry ) ) != NULL ) ;
+
+ if ( *statp == EX_OK ) {
+
+ vsize = strlen(vp);
+
+ if (LogLevel > 9)
+ sm_syslog(LOG_INFO, CurEnv->e_id,
+ "ldap %.100s => %s",
+ name, vp);
+ if (bitset(MF_MATCHONLY, map->map_mflags))
+ result = map_rewrite(map, name, strlen(name), NULL);
+ else
+ result = map_rewrite(map, vp, vsize, av);
+ free(vp) ;
+
}
-
- *statp = EX_OK;
-
- /* If there is more that one use the first */
- vp = attr_values[0];
- vsize = strlen(vp);
-
- if (LogLevel > 9)
- sm_syslog(LOG_INFO, CurEnv->e_id,
- "ldap %.100s => %s",
- name, vp);
- if (bitset(MF_MATCHONLY, map->map_mflags))
- result = map_rewrite(map, name, strlen(name), NULL);
- else
- result = map_rewrite(map, vp, vsize, av);
-
quick_exit:
if (attr_values != NULL)
ldap_value_free(attr_values);
@@ -2982,8 +3034,12 @@
char *args;
{
register char *p = args;
- register int done;
+ register int done,i;
LDAP_MAP_STRUCT *lmap;
+ static char m_tmp[MAXPATHLEN+LDAP_MAP_MAX_PASSWD];
+ FILE * sfd ;
+ int sff = SFF_OPENASROOT|SFF_ROOTOK|SFF_NOWLINK|SFF_NOWWFILES|SFF_NOGWFILES;
+ char *tmp ;
/* We need to alloc an LDAP_MAP_STRUCT struct */
lmap = (LDAP_MAP_STRUCT *) xalloc(sizeof(LDAP_MAP_STRUCT));
@@ -3002,7 +3058,8 @@
/* Default char ptrs to NULL */
lmap->binddn = NULL;
- lmap->passwd = NULL;
+
+ lmap->secret = NULL;
lmap->base = NULL;
lmap->ldaphost = NULL;
@@ -3088,7 +3145,9 @@
break;
case 's': /* search scope */
- if (strncasecmp(++p, "base", 4) == 0)
+ while (isascii(*++p) && isspace(*p))
+ continue;
+ if (strncasecmp(p, "base", 4) == 0)
{
lmap->scope = LDAP_SCOPE_BASE;
}
@@ -3142,7 +3201,36 @@
lmap->timelimit = atoi(p);
lmap->timeout.tv_sec = lmap->timelimit;
break;
-
+ case 'D': /* Dn to bind to server as */
+ while (isascii(*++p) && isspace(*p))
+ continue;
+ lmap->binddn = p;
+ break;
+ case 'M': /* Method for binding */
+ while (isascii(*++p) && isspace(*p))
+ continue;
+ /* Need to map ascii method to int here */
+ tmp = p ;
+ /* Argh, can't use ldap_map_dequote here */
+ if ( *tmp == '"' ) {
+ while ( isascii(*++tmp) && isspace(*tmp))
+ continue;
+ }
+ for(i = 0 ; i < LDAP_MAP_AUTH_METHOD_MAX ; i++ ) {
+ if ( strncmp(tmp,ldap_map_auth_methods[i],strlen(ldap_map_auth_methods[i])) == 0 ) {
+ lmap->method = ldap_map_auth_methods_code[i] ;
+ }
+ }
+
+ break ;
+ /* This is a string that is dependent on the
+ * method used defined above.
+ */
+ case 'S': /* Secret for binding */
+ while (isascii(*++p) && isspace(*p))
+ continue;
+ lmap->secret = p ;
+ break ;
}
/* need to account for quoted strings here arggg... */
@@ -3189,16 +3277,60 @@
return FALSE;
}
- if (lmap->binddn != NULL)
- lmap->binddn = newstr(ldap_map_dequote(lmap->binddn));
+ if (lmap->binddn != NULL) {
+ lmap->binddn = newstr(ldap_map_dequote(lmap->binddn));
+
+ if ( lmap->secret != NULL ) {
+ /* need to use method to map secret to passwd string */
+ switch(lmap->method)
+ {
+
+ case LDAP_AUTH_NONE: /* Do nothing */
+ break;
+ case LDAP_AUTH_SIMPLE: /* Secret is the name of a file with
+ the first line as the pwd. */
+
+
+ sfd = safefopen(ldap_map_dequote(lmap->secret),O_RDONLY,0,sff);
+ if ( sfd == NULL )
+ {
+ syserr("LDAP map: cannot open secret %s",ldap_map_dequote(lmap->secret));
+ return FALSE ;
+ } else
+ {
+ lmap->secret = sfgets(m_tmp,LDAP_MAP_MAX_PASSWD,sfd,0,"ldap_map_parseargs") ;
+ fclose(sfd) ;
+ if ( lmap->secret != NULL )
+ {
+ /* chomp newline */
+ if (m_tmp[strlen(m_tmp)-1] == '\n')
+ m_tmp[strlen(m_tmp)-1] = '\0';
+
+ lmap->secret = newstr(m_tmp) ;
+ }
+ }
+ break ;
+ case LDAP_AUTH_KRBV4: /* Secret is where the tgt file
+ is stashed */
+ /* We could be paranoid here.. */
+ snprintf(m_tmp,MAXPATHLEN+LDAP_MAP_MAX_PASSWD,"KRBTKFILE=%s",ldap_map_dequote(lmap->secret));
+ putenv(m_tmp);
+ lmap->secret = NULL ;
+ break ;
+ default : /* Should NEVER get here */
+ syserr("LDAP map: Garbage in lmap method" ) ;
+ return FALSE ;
+ break ;
+ } /* end switch */
+ }
+ }
else
lmap->binddn = DEFAULT_LDAP_MAP_BINDDN;
-
- if (lmap->passwd != NULL)
- lmap->passwd = newstr(ldap_map_dequote(lmap->passwd));
+ if (lmap->secret != NULL)
+ lmap->secret = newstr(ldap_map_dequote(lmap->secret));
else
- lmap->passwd = DEFAULT_LDAP_MAP_PASSWD;
+ lmap->secret = DEFAULT_LDAP_MAP_SECRET;
if (lmap->base != NULL)
lmap->base = newstr(ldap_map_dequote(lmap->base));
|