0
|
1 /*
|
|
2 * CDDL HEADER START
|
|
3 *
|
|
4 * The contents of this file are subject to the terms of the
|
|
5 * Common Development and Distribution License, Version 1.0 only
|
|
6 * (the "License"). You may not use this file except in compliance
|
|
7 * with the License.
|
|
8 *
|
|
9 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
|
|
10 * or http://www.opensolaris.org/os/licensing.
|
|
11 * See the License for the specific language governing permissions
|
|
12 * and limitations under the License.
|
|
13 *
|
|
14 * When distributing Covered Code, include this CDDL HEADER in each
|
|
15 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
|
|
16 * If applicable, add the following below this CDDL HEADER, with the
|
|
17 * fields enclosed by brackets "[]" replaced with your own identifying
|
|
18 * information: Portions Copyright [yyyy] [name of copyright owner]
|
|
19 *
|
|
20 * CDDL HEADER END
|
|
21 */
|
|
22 /*
|
|
23 * Copyright 1998 Sun Microsystems, Inc. All rights reserved.
|
|
24 * Use is subject to license terms.
|
|
25 */
|
|
26
|
|
27 /* Copyright (c) 1984, 1986, 1987, 1988, 1989 AT&T */
|
|
28 /* All Rights Reserved */
|
|
29
|
|
30
|
|
31 #pragma ident "@(#)sysfiles.c 1.12 05/06/08 SMI"
|
|
32
|
|
33 #include "uucp.h"
|
|
34
|
|
35 #include <unistd.h>
|
|
36 #include "sysfiles.h"
|
|
37 #include <sys/stropts.h>
|
|
38
|
|
39 /*
|
|
40 * manage systems files (Systems, Devices, and Dialcodes families).
|
|
41 *
|
|
42 * also manage new file Devconfig, allows per-device setup.
|
|
43 * present use is to specify what streams modules to push/pop for
|
|
44 * AT&T TLI/streams network.
|
|
45 *
|
|
46 * TODO:
|
|
47 * call bsfix()?
|
|
48 * combine the 3 versions of everything (sys, dev, and dial) into one.
|
|
49 * allow arbitrary classes of service.
|
|
50 * need verifysys() for uucheck.
|
|
51 * nameserver interface?
|
|
52 * pass sysname (or 0) to getsysline(). (might want reg. exp. or NS processing
|
|
53 */
|
|
54
|
|
55 /* private variables */
|
|
56 static void tokenize(), nameparse(), setfile(), setioctl(),
|
|
57 scansys(), scancfg(), setconfig();
|
|
58 static int namematch(), nextdialers(), nextdevices(), nextsystems(), getline();
|
|
59
|
|
60 /* pointer arrays might be dynamically allocated */
|
|
61 static char *Systems[64] = {0}; /* list of Systems files */
|
|
62 static char *Devices[64] = {0}; /* list of Devices files */
|
|
63 static char *Dialers[64] = {0}; /* list of Dialers files */
|
|
64 static char *Pops[64] = {0}; /* list of STREAMS modules to be popped */
|
|
65 static char *Pushes[64] = {0}; /* list of STREAMS modules to be pushed */
|
|
66
|
|
67 static int nsystems; /* index into list of Systems files */
|
|
68 static int ndevices; /* index into list of Devices files */
|
|
69 static int ndialers; /* index into list of Dialers files */
|
|
70 static int npops; /* index into list of STREAMS modules */
|
|
71 /*to be popped */
|
|
72 static int npushes; /* index into list of STREAMS modules */
|
|
73 /*to be pushed */
|
|
74
|
|
75 GLOBAL unsigned connecttime = CONNECTTIME;
|
|
76 GLOBAL unsigned expecttime = EXPECTTIME;
|
|
77 GLOBAL unsigned msgtime = MSGTIME;
|
|
78
|
|
79 static FILE *fsystems;
|
|
80 static FILE *fdevices;
|
|
81 static FILE *fdialers;
|
|
82
|
|
83 static char errformat[BUFSIZ];
|
|
84
|
|
85 /* this might be dynamically allocated */
|
|
86 #define NTOKENS 16
|
|
87 static char *tokens[NTOKENS], **tokptr;
|
|
88
|
|
89 /* export these */
|
|
90 EXTERN void sysreset(), devreset(), dialreset(), setdevcfg(), setservice();
|
|
91 EXTERN char *strsave();
|
|
92
|
|
93 /* import these */
|
|
94 extern char *strcpy(), *strtok(), *strchr(), *strsave();
|
|
95 EXTERN int eaccess();
|
|
96
|
|
97 /*
|
|
98 * setservice init's Systems, Devices, Dialers lists from Sysfiles
|
|
99 */
|
|
100 GLOBAL void
|
|
101 setservice(service)
|
|
102 char *service;
|
|
103 {
|
|
104 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
105
|
|
106 setconfig();
|
|
107 scansys(service);
|
|
108 (void) _uu_resetlocale(LC_ALL, prev);
|
|
109 return;
|
|
110 }
|
|
111
|
|
112 /*
|
|
113 * setdevcfg init's Pops, Pushes lists from Devconfig
|
|
114 */
|
|
115
|
|
116 GLOBAL void
|
|
117 setdevcfg(service, device)
|
|
118 char *service, *device;
|
|
119 {
|
|
120 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
121
|
|
122 scancfg(service, device);
|
|
123 (void) _uu_resetlocale(LC_ALL, prev);
|
|
124 return;
|
|
125 }
|
|
126
|
|
127 /* administrative files access */
|
|
128 GLOBAL int
|
|
129 sysaccess(type)
|
|
130 int type;
|
|
131 {
|
|
132 switch (type) {
|
|
133
|
|
134 case ACCESS_SYSTEMS:
|
|
135 return(access(Systems[nsystems], R_OK));
|
|
136 case ACCESS_DEVICES:
|
|
137 return(access(Devices[ndevices], R_OK));
|
|
138 case ACCESS_DIALERS:
|
|
139 return(access(Dialers[ndialers], R_OK));
|
|
140 case EACCESS_SYSTEMS:
|
|
141 return(eaccess(Systems[nsystems], R_OK));
|
|
142 case EACCESS_DEVICES:
|
|
143 return(eaccess(Devices[ndevices], R_OK));
|
|
144 case EACCESS_DIALERS:
|
|
145 return(eaccess(Dialers[ndialers], R_OK));
|
|
146 default:
|
|
147 (void)sprintf(errformat, "bad access type %d", type);
|
|
148 logent(errformat, "sysaccess");
|
|
149 return(FAIL);
|
|
150 }
|
|
151 }
|
|
152
|
|
153
|
|
154 /*
|
|
155 * read Sysfiles, set up lists of Systems/Devices/Dialers file names.
|
|
156 * allow multiple entries for a given service, allow a service
|
|
157 * type to describe resources more than once, e.g., systems=foo:baz systems=bar.
|
|
158 */
|
|
159 static void
|
|
160 scansys(service)
|
|
161 char *service;
|
|
162 { FILE *f;
|
|
163 char *tok, buf[BUFSIZ];
|
|
164
|
|
165 Systems[0] = Devices[0] = Dialers[0] = NULL;
|
|
166 if ((f = fopen(SYSFILES, "r")) != 0) {
|
|
167 while (getline(f, buf) > 0) {
|
|
168 /* got a (logical) line from Sysfiles */
|
|
169 /* strtok's of this buf continue in tokenize() */
|
|
170 tok = strtok(buf, " \t");
|
|
171 if (namematch("service=", tok, service)) {
|
|
172 tokenize();
|
|
173 nameparse();
|
|
174 }
|
|
175 }
|
|
176 (void) fclose(f);
|
|
177 }
|
|
178
|
|
179 /* if didn't find entries in Sysfiles, use defaults */
|
|
180 if (Systems[0] == NULL) {
|
|
181 Systems[0] = strsave(SYSTEMS);
|
|
182 ASSERT(Systems[0] != NULL, Ct_ALLOCATE, "scansys: Systems", 0);
|
|
183 Systems[1] = NULL;
|
|
184 }
|
|
185 if (Devices[0] == NULL) {
|
|
186 Devices[0] = strsave(DEVICES);
|
|
187 ASSERT(Devices[0] != NULL, Ct_ALLOCATE, "scansys: Devices", 0);
|
|
188 Devices[1] = NULL;
|
|
189 }
|
|
190 if (Dialers[0] == NULL) {
|
|
191 Dialers[0] = strsave(DIALERS);
|
|
192 ASSERT(Dialers[0] != NULL, Ct_ALLOCATE, "scansys: Dialers", 0);
|
|
193 Dialers[1] = NULL;
|
|
194 }
|
|
195 return;
|
|
196 }
|
|
197
|
|
198
|
|
199 /*
|
|
200 * read Devconfig. allow multiple entries for a given service, allow a service
|
|
201 * type to describe resources more than once, e.g., push=foo:baz push=bar.
|
|
202 */
|
|
203 static void
|
|
204 scancfg(service, device)
|
|
205 char *service, *device;
|
|
206 { FILE *f;
|
|
207 char *tok, buf[BUFSIZ];
|
|
208
|
|
209 /* (re)initialize device-specific information */
|
|
210
|
|
211 npops = npushes = 0;
|
|
212 Pops[0] = Pushes[0] = NULL;
|
|
213 connecttime = CONNECTTIME;
|
|
214 expecttime = EXPECTTIME;
|
|
215 msgtime = MSGTIME;
|
|
216
|
|
217 if ((f = fopen(DEVCONFIG, "r")) != 0) {
|
|
218 while (getline(f, buf) > 0) {
|
|
219 /* got a (logical) line from Devconfig */
|
|
220 /* strtok's of this buf continue in tokenize() */
|
|
221 tok = strtok(buf, " \t");
|
|
222 if (namematch("service=", tok, service)) {
|
|
223 tok = strtok((char *)0, " \t");
|
|
224 if ( namematch("device=", tok, device)) {
|
|
225 tokenize();
|
|
226 nameparse();
|
|
227 }
|
|
228 }
|
|
229 }
|
|
230 (void) fclose(f);
|
|
231 }
|
|
232
|
|
233 return;
|
|
234
|
|
235 }
|
|
236
|
|
237 /*
|
|
238 * given a file pointer and buffer, construct logical line in buffer
|
|
239 * (i.e., concatenate lines ending in '\'). return length of line
|
|
240 * ASSUMES that buffer is BUFSIZ long!
|
|
241 */
|
|
242
|
|
243 static int
|
|
244 getline(f, line)
|
|
245 FILE *f;
|
|
246 char *line;
|
|
247 { char *lptr, *lend;
|
|
248
|
|
249 lptr = line;
|
|
250 while (fgets(lptr, (line + BUFSIZ) - lptr, f) != NULL) {
|
|
251 lend = lptr + strlen(lptr);
|
|
252 if (lend == lptr || lend[-1] != '\n')
|
|
253 /* empty buf or line too long! */
|
|
254 break;
|
|
255 *--lend = '\0'; /* lop off ending '\n' */
|
|
256 if ( lend == line ) /* empty line - ignore */
|
|
257 continue;
|
|
258 lptr = lend;
|
|
259 if (lend[-1] != '\\')
|
|
260 break;
|
|
261 /* continuation */
|
|
262 lend[-1] = ' ';
|
|
263 }
|
|
264 return(lptr - line);
|
|
265 }
|
|
266
|
|
267 /*
|
|
268 * given a label (e.g., "service=", "device="), a name ("cu", "uucico"),
|
|
269 * and a line: if line begins with the label and if the name appears
|
|
270 * in a colon-separated list of names following the label, return true;
|
|
271 * else return false
|
|
272 */
|
|
273 static int
|
|
274 namematch(label, line, name)
|
|
275 char *label, *line, *name;
|
|
276 { char *lend;
|
|
277
|
|
278 if (strncmp(label, line, strlen(label)) != SAME) {
|
|
279 return(FALSE); /* probably a comment line */
|
|
280 }
|
|
281 line += strlen(label);
|
|
282 if (*line == '\0')
|
|
283 return(FALSE);
|
|
284 /*
|
|
285 * can't use strtok() in the following because scansys(),
|
|
286 * scancfg() do an initializing call to strtok() before
|
|
287 * coming here and then CONTINUE calling strtok() in tokenize(),
|
|
288 * after returning from namematch().
|
|
289 */
|
|
290 while ((lend = strchr(line, ':')) != NULL) {
|
|
291 *lend = '\0';
|
|
292 if (strcmp(line, name) == SAME)
|
|
293 return(TRUE);
|
|
294 line = lend+1;
|
|
295 }
|
|
296 return(strcmp(line, name) == SAME);
|
|
297 }
|
|
298
|
|
299 /*
|
|
300 * tokenize() continues pulling tokens out of a buffer -- the
|
|
301 * initializing call to strtok must have been made before calling
|
|
302 * tokenize() -- and starts stuffing 'em into tokptr.
|
|
303 */
|
|
304 static void
|
|
305 tokenize()
|
|
306 { char *tok;
|
|
307
|
|
308 tokptr = tokens;
|
|
309 while ((tok = strtok((char *) NULL, " \t")) != NULL) {
|
|
310 *tokptr++ = tok;
|
|
311 if (tokptr - tokens >= NTOKENS)
|
|
312 break;
|
|
313 }
|
|
314 *tokptr = NULL;
|
|
315 return;
|
|
316 }
|
|
317
|
|
318 /*
|
|
319 * look at top token in array: should be line of the form
|
|
320 * name=item1:item2:item3...
|
|
321 * if name is one we recognize, then call set[file|ioctl] to set up
|
|
322 * corresponding list. otherwise, log bad name.
|
|
323 */
|
|
324 static void
|
|
325 nameparse()
|
|
326 { char **line, *equals;
|
|
327 int temp;
|
|
328
|
|
329 #define setuint(a,b,c) a = ( ((temp = atoi(b)) <= 0) ? (c) : temp )
|
|
330
|
|
331 for (line = tokens; (line - tokens) < NTOKENS && *line; line++) {
|
|
332 equals = strchr(*line, '=');
|
|
333 if (equals == NULL)
|
|
334 continue; /* may be meaningful someday? */
|
|
335 *equals = '\0';
|
|
336 /* ignore entry with empty rhs */
|
|
337 if (*++equals == '\0')
|
|
338 continue;
|
|
339 if (strcmp(*line, "systems") == SAME)
|
|
340 setfile(Systems, equals);
|
|
341 else if (strcmp(*line, "devices") == SAME)
|
|
342 setfile(Devices, equals);
|
|
343 else if (strcmp(*line, "dialers") == SAME)
|
|
344 setfile(Dialers, equals);
|
|
345 else if (strcmp(*line, "pop") == SAME)
|
|
346 setioctl(Pops, equals);
|
|
347 else if (strcmp(*line, "push") == SAME)
|
|
348 setioctl(Pushes, equals);
|
|
349 else if (strcmp(*line, "connecttime") == SAME)
|
|
350 setuint(connecttime, equals, CONNECTTIME);
|
|
351 else if (strcmp(*line, "expecttime") == SAME)
|
|
352 setuint(expecttime, equals, EXPECTTIME);
|
|
353 else if (strcmp(*line, "msgtime") == SAME)
|
|
354 setuint(msgtime, equals, MSGTIME);
|
|
355 else {
|
|
356 (void)sprintf(errformat,"unrecognized label %s",*line);
|
|
357 logent(errformat, "Sysfiles|Devconfig");
|
|
358 }
|
|
359 }
|
|
360 return;
|
|
361 }
|
|
362
|
|
363 /*
|
|
364 * given the list for a particular type (systems, devices,...)
|
|
365 * and a line of colon-separated files, add 'em to list
|
|
366 */
|
|
367
|
|
368 static void
|
|
369 setfile(type, line)
|
|
370 char **type, *line;
|
|
371 { char **tptr, *tok;
|
|
372 char expandpath[BUFSIZ];
|
|
373
|
|
374 if (*line == 0)
|
|
375 return;
|
|
376 tptr = type;
|
|
377 while (*tptr) /* skip over existing entries to*/
|
|
378 tptr++; /* concatenate multiple entries */
|
|
379
|
|
380 for (tok = strtok(line, ":"); tok != NULL;
|
|
381 tok = strtok((char *) NULL, ":")) {
|
|
382 expandpath[0] = '\0';
|
|
383 if ( *tok != '/' )
|
|
384 /* by default, file names are relative to SYSDIR */
|
|
385 sprintf(expandpath, "%s/", SYSDIR);
|
|
386 strcat(expandpath, tok);
|
|
387 if (eaccess(expandpath, R_OK) != 0)
|
|
388 /* if we can't read it, no point in adding to list */
|
|
389 continue;
|
|
390 *tptr = strsave(expandpath);
|
|
391 ASSERT(*tptr != NULL, Ct_ALLOCATE, "setfile: tptr", 0);
|
|
392 tptr++;
|
|
393 }
|
|
394 return;
|
|
395 }
|
|
396
|
|
397 /*
|
|
398 * given the list for a particular ioctl (push, pop)
|
|
399 * and a line of colon-separated modules, add 'em to list
|
|
400 */
|
|
401
|
|
402 static void
|
|
403 setioctl(type, line)
|
|
404 char **type, *line;
|
|
405 { char **tptr, *tok;
|
|
406
|
|
407 if (*line == 0)
|
|
408 return;
|
|
409 tptr = type;
|
|
410 while (*tptr) /* skip over existing entries to*/
|
|
411 tptr++; /* concatenate multiple entries */
|
|
412 for (tok = strtok(line, ":"); tok != NULL;
|
|
413 tok = strtok((char *) NULL, ":")) {
|
|
414 *tptr = strsave(tok);
|
|
415 ASSERT(*tptr != NULL, Ct_ALLOCATE, "setioctl: tptr", 0);
|
|
416 tptr++;
|
|
417 }
|
|
418 return;
|
|
419 }
|
|
420
|
|
421 /*
|
|
422 * reset Systems files
|
|
423 */
|
|
424 GLOBAL void
|
|
425 sysreset()
|
|
426 {
|
|
427 if (fsystems)
|
|
428 fclose(fsystems);
|
|
429 fsystems = NULL;
|
|
430 nsystems = 0;
|
|
431 devreset();
|
|
432 return;
|
|
433 }
|
|
434
|
|
435 /*
|
|
436 * reset Devices files
|
|
437 */
|
|
438 GLOBAL void
|
|
439 devreset()
|
|
440 {
|
|
441 if (fdevices)
|
|
442 fclose(fdevices);
|
|
443 fdevices = NULL;
|
|
444 ndevices = 0;
|
|
445 dialreset();
|
|
446 return;
|
|
447 }
|
|
448
|
|
449 /*
|
|
450 * reset Dialers files
|
|
451 */
|
|
452 GLOBAL void
|
|
453 dialreset()
|
|
454 {
|
|
455 if (fdialers)
|
|
456 fclose(fdialers);
|
|
457 fdialers = NULL;
|
|
458 ndialers = 0;
|
|
459 return;
|
|
460 }
|
|
461
|
|
462 /*
|
|
463 * get next line from Systems file
|
|
464 * return TRUE if successful, FALSE if not
|
|
465 */
|
|
466 GLOBAL int
|
|
467 getsysline(buf, len)
|
|
468 char *buf;
|
|
469 {
|
|
470 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
471
|
|
472 if (Systems[0] == NULL)
|
|
473 /* not initialized via setservice() - use default */
|
|
474 setservice("uucico");
|
|
475
|
|
476 /* initialize devices and dialers whenever a new line is read */
|
|
477 /* from systems */
|
|
478 devreset();
|
|
479 if (fsystems == NULL)
|
|
480 if (nextsystems() == FALSE) {
|
|
481 (void) _uu_resetlocale(LC_ALL, prev);
|
|
482 return(FALSE);
|
|
483 }
|
|
484
|
|
485 ASSERT(len >= BUFSIZ, "BUFFER TOO SMALL", "getsysline", 0);
|
|
486 for(;;) {
|
|
487 while (getline(fsystems, buf) != NULL)
|
|
488 if ((*buf != '#') && (*buf != ' ') &&
|
|
489 (*buf != '\t') && (*buf != '\n')) {
|
|
490 (void) _uu_resetlocale(LC_ALL, prev);
|
|
491 return(TRUE);
|
|
492 }
|
|
493 if (nextsystems() == FALSE) {
|
|
494 (void) _uu_resetlocale(LC_ALL, prev);
|
|
495 return(FALSE);
|
|
496 }
|
|
497 }
|
|
498 }
|
|
499
|
|
500 /*
|
|
501 * move to next systems file. return TRUE if successful, FALSE if not
|
|
502 */
|
|
503 static int
|
|
504 nextsystems()
|
|
505 {
|
|
506 devreset();
|
|
507
|
|
508 if (fsystems != NULL) {
|
|
509 (void) fclose(fsystems);
|
|
510 nsystems++;
|
|
511 } else {
|
|
512 nsystems = 0;
|
|
513 }
|
|
514 for ( ; Systems[nsystems] != NULL; nsystems++)
|
|
515 if ((fsystems = fopen(Systems[nsystems], "r")) != NULL)
|
|
516 return(TRUE);
|
|
517 return(FALSE);
|
|
518 }
|
|
519
|
|
520 /*
|
|
521 * get next line from Devices file
|
|
522 * return TRUE if successful, FALSE if not
|
|
523 */
|
|
524 GLOBAL int
|
|
525 getdevline(buf, len)
|
|
526 char *buf;
|
|
527 {
|
|
528 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
529
|
|
530 if (Devices[0] == NULL)
|
|
531 /* not initialized via setservice() - use default */
|
|
532 setservice("uucico");
|
|
533
|
|
534 if (fdevices == NULL)
|
|
535 if (nextdevices() == FALSE) {
|
|
536 (void) _uu_resetlocale(LC_ALL, prev);
|
|
537 return(FALSE);
|
|
538 }
|
|
539 for(;;) {
|
|
540 if (fgets(buf, len, fdevices) != NULL) {
|
|
541 (void) _uu_resetlocale(LC_ALL, prev);
|
|
542 return(TRUE);
|
|
543 }
|
|
544 if (nextdevices() == FALSE) {
|
|
545 (void) _uu_resetlocale(LC_ALL, prev);
|
|
546 return(FALSE);
|
|
547 }
|
|
548 }
|
|
549 }
|
|
550
|
|
551 /*
|
|
552 * move to next devices file. return TRUE if successful, FALSE if not
|
|
553 */
|
|
554 static int
|
|
555 nextdevices()
|
|
556 {
|
|
557 if (fdevices != NULL) {
|
|
558 (void) fclose(fdevices);
|
|
559 ndevices++;
|
|
560 } else {
|
|
561 ndevices = 0;
|
|
562 }
|
|
563 for ( ; Devices[ndevices] != NULL; ndevices++)
|
|
564 if ((fdevices = fopen(Devices[ndevices], "r")) != NULL)
|
|
565 return(TRUE);
|
|
566 return(FALSE);
|
|
567 }
|
|
568
|
|
569
|
|
570 /*
|
|
571 * get next line from Dialers file
|
|
572 * return TRUE if successful, FALSE if not
|
|
573 */
|
|
574
|
|
575 GLOBAL int
|
|
576 getdialline(buf, len)
|
|
577 char *buf;
|
|
578 {
|
|
579 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
580
|
|
581 if (Dialers[0] == NULL)
|
|
582 /* not initialized via setservice() - use default */
|
|
583 setservice("uucico");
|
|
584
|
|
585 if (fdialers == NULL)
|
|
586 if (nextdialers() == FALSE) {
|
|
587 (void) _uu_resetlocale(LC_ALL, prev);
|
|
588 return(FALSE);
|
|
589 }
|
|
590 for(;;) {
|
|
591 if (fgets(buf, len, fdialers) != NULL) {
|
|
592 (void) _uu_resetlocale(LC_ALL, prev);
|
|
593 return(TRUE);
|
|
594 }
|
|
595 if (nextdialers() == FALSE) {
|
|
596 (void) _uu_resetlocale(LC_ALL, prev);
|
|
597 return(FALSE);
|
|
598 }
|
|
599 }
|
|
600 }
|
|
601
|
|
602 /*
|
|
603 * move to next dialers file. return TRUE if successful, FALSE if not
|
|
604 */
|
|
605 static int
|
|
606 nextdialers()
|
|
607 {
|
|
608 if (fdialers) {
|
|
609 (void) fclose(fdialers);
|
|
610 ndialers++;
|
|
611 } else {
|
|
612 ndialers = 0;
|
|
613 }
|
|
614
|
|
615 for ( ; Dialers[ndialers] != NULL; ndialers++)
|
|
616 if ((fdialers = fopen(Dialers[ndialers], "r")) != NULL)
|
|
617 return(TRUE);
|
|
618 return(FALSE);
|
|
619 }
|
|
620
|
|
621 /*
|
|
622 * get next module to be popped
|
|
623 * return TRUE if successful, FALSE if not
|
|
624 */
|
|
625 static int
|
|
626 getpop(buf, len, optional)
|
|
627 char *buf;
|
|
628 int len, *optional;
|
|
629 {
|
|
630 int slen;
|
|
631
|
|
632 if ( Pops[0] == NULL || Pops[npops] == NULL )
|
|
633 return(FALSE);
|
|
634
|
|
635 /* if the module name is enclosed in parentheses, */
|
|
636 /* is optional. set flag & strip parens */
|
|
637 slen = strlen(Pops[npops]) - 1;
|
|
638 if ( Pops[npops][0] == '(' && Pops[npops][slen] == ')' ) {
|
|
639 *optional = 1;
|
|
640 len = ( slen < len ? slen : len );
|
|
641 strncpy(buf, &(Pops[npops++][1]), len);
|
|
642 } else {
|
|
643 *optional = 0;
|
|
644 strncpy(buf, Pops[npops++], len);
|
|
645 }
|
|
646 buf[len-1] = '\0';
|
|
647 return(TRUE);
|
|
648 }
|
|
649
|
|
650 /*
|
|
651 * get next module to be pushed
|
|
652 * return TRUE if successful, FALSE if not
|
|
653 */
|
|
654 static int
|
|
655 getpush(buf, len)
|
|
656 char *buf;
|
|
657 int len;
|
|
658 {
|
|
659 if ( Pushes[0] == NULL || Pushes[npushes] == NULL )
|
|
660 return(FALSE);
|
|
661 strncpy(buf, Pushes[npushes++], len);
|
|
662 return(TRUE);
|
|
663 }
|
|
664
|
|
665 /*
|
|
666 * pop/push requested modules
|
|
667 * return TRUE if successful, FALSE if not
|
|
668 */
|
|
669 GLOBAL int
|
|
670 pop_push(fd)
|
|
671 int fd;
|
|
672 {
|
|
673 char strmod[FMNAMESZ], onstream[FMNAMESZ];
|
|
674 int optional;
|
|
675 char *prev = _uu_setlocale(LC_ALL, "C");
|
|
676
|
|
677 /* check for streams modules to pop */
|
|
678 while ( getpop(strmod, sizeof(strmod), &optional) ) {
|
|
679 DEBUG(5, (optional ? "pop_push: optionally POPing %s\n"
|
|
680 : "pop_push: POPing %s\n" ), strmod);
|
|
681 if ( ioctl(fd, I_LOOK, onstream) == -1 ) {
|
|
682 DEBUG(5, "pop_push: I_LOOK on fd %d failed ", fd);
|
|
683 DEBUG(5, "errno %d\n", errno);
|
|
684 (void) _uu_resetlocale(LC_ALL, prev);
|
|
685 return(FALSE);
|
|
686 }
|
|
687 if ( strcmp(strmod, onstream) != SAME ) {
|
|
688 if ( optional )
|
|
689 continue;
|
|
690 DEBUG(5, "pop_push: I_POP: %s not there\n", strmod);
|
|
691 (void) _uu_resetlocale(LC_ALL, prev);
|
|
692 return(FALSE);
|
|
693 }
|
|
694 if ( ioctl(fd, I_POP, 0) == -1 ) {
|
|
695 DEBUG(5, "pop_push: I_POP on fd %d failed ", fd);
|
|
696 DEBUG(5, "errno %d\n", errno);
|
|
697 (void) _uu_resetlocale(LC_ALL, prev);
|
|
698 return(FALSE);
|
|
699 }
|
|
700 }
|
|
701
|
|
702 /* check for streams modules to push */
|
|
703 while ( getpush(strmod, sizeof(strmod)) ) {
|
|
704 DEBUG(5, "pop_push: PUSHing %s\n", strmod);
|
|
705 if ( ioctl(fd, I_PUSH, strmod) == -1 ) {
|
|
706 DEBUG(5, "pop_push: I_PUSH on fd %d failed ", fd);
|
|
707 DEBUG(5, "errno %d\n", errno);
|
|
708 (void) _uu_resetlocale(LC_ALL, prev);
|
|
709 return(FALSE);
|
|
710 }
|
|
711 }
|
|
712 (void) _uu_resetlocale(LC_ALL, prev);
|
|
713 return(TRUE);
|
|
714 }
|
|
715
|
|
716 /*
|
|
717 * return name of currently open Systems file
|
|
718 */
|
|
719 GLOBAL char *
|
|
720 currsys()
|
|
721 {
|
|
722 return(Systems[nsystems]);
|
|
723 }
|
|
724
|
|
725 /*
|
|
726 * return name of currently open Devices file
|
|
727 */
|
|
728 GLOBAL char *
|
|
729 currdev()
|
|
730 {
|
|
731 return(Devices[ndevices]);
|
|
732 }
|
|
733
|
|
734 /*
|
|
735 * return name of currently open Dialers file
|
|
736 */
|
|
737 GLOBAL char *
|
|
738 currdial()
|
|
739 {
|
|
740 return(Dialers[ndialers]);
|
|
741 }
|
|
742
|
|
743 /*
|
|
744 * set configuration parameters provided in Config file
|
|
745 */
|
|
746 static void
|
|
747 setconfig()
|
|
748 {
|
|
749 FILE *f;
|
|
750 char buf[BUFSIZ];
|
|
751 char *tok;
|
|
752 extern char _ProtoCfg[];
|
|
753
|
|
754 if ((f = fopen(CONFIG, "r")) != 0) {
|
|
755 while (getline(f, buf) > 0) {
|
|
756 /* got a (logical) line from Config file */
|
|
757 tok = strtok(buf, " \t");
|
|
758 if ( (tok != NULL) && (*tok != '#') ) {
|
|
759 /* got a token */
|
|
760
|
|
761 /* this probably should be table driven when
|
|
762 * the list of configurable parameters grows.
|
|
763 */
|
|
764 if (strncmp("Protocol=", tok, strlen("Protocol=")) == SAME) {
|
|
765 tok += strlen("Protocol=");
|
|
766 if ( *tok != '\0' ) {
|
|
767 if ( _ProtoCfg[0] != '\0' ) {
|
|
768 DEBUG(7, "Protocol string %s ", tok);
|
|
769 DEBUG(7, "overrides %s\n", _ProtoCfg);
|
|
770 }
|
|
771 strcpy(_ProtoCfg, tok);
|
|
772 }
|
|
773 } else {
|
|
774 DEBUG(7, "Unknown configuration parameter %s\n", tok);
|
|
775 }
|
|
776 }
|
|
777 }
|
|
778 }
|
|
779 }
|