2 * CDE - Common Desktop Environment
4 * Copyright (c) 1993-2012, The Open Group. All rights reserved.
6 * These libraries and programs are free software; you can
7 * redistribute them and/or modify them under the terms of the GNU
8 * Lesser General Public License as published by the Free Software
9 * Foundation; either version 2 of the License, or (at your option)
12 * These libraries and programs are distributed in the hope that
13 * they will be useful, but WITHOUT ANY WARRANTY; without even the
14 * implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
15 * PURPOSE. See the GNU Lesser General Public License for more
18 * You should have received a copy of the GNU Lesser General Public
19 * License along with these librararies and programs; if not, write
20 * to the Free Software Foundation, Inc., 51 Franklin Street, Fifth
21 * Floor, Boston, MA 02110-1301 USA
23 /* $XConsortium: astconf.c /main/2 1996/05/08 19:56:20 drk $ */
24 /***************************************************************
26 * AT&T - PROPRIETARY *
28 * THIS IS PROPRIETARY SOURCE CODE LICENSED BY *
31 * Copyright (c) 1995 AT&T Corp. *
32 * All Rights Reserved *
34 * This software is licensed by AT&T Corp. *
35 * under the terms and conditions of the license in *
36 * http://www.research.att.com/orgs/ssr/book/reuse *
38 * This software was created by the *
39 * Software Engineering Research Department *
40 * AT&T Bell Laboratories *
42 * For further information contact *
43 * gsf@research.att.com *
45 ***************************************************************/
47 /* : : generated by proto : : */
49 #if !defined(__PROTO__)
50 #if defined(__STDC__) || defined(__cplusplus) || defined(_proto) || defined(c_plusplus)
51 #if defined(__cplusplus)
52 #define __MANGLE__ "C"
57 #define __PROTO__(x) x
59 #define __PARAM__(n,o) n
60 #if !defined(__STDC__) && !defined(__cplusplus)
61 #if !defined(c_plusplus)
72 #define __PROTO__(x) ()
73 #define __OTORP__(x) x
74 #define __PARAM__(n,o) o
82 #if defined(__cplusplus) || defined(c_plusplus)
83 #define __VARARG__ ...
87 #if defined(__STDARG__)
88 #define __VA_START__(p,a) va_start(p,a)
90 #define __VA_START__(p,a) va_start(p)
93 static const char id[] = "\n@(#)getconf (AT&T Bell Laboratories) 07/17/95\0\n";
95 static const char lib[] = "";
108 #define CONF_ERROR (CONF_USER<<0)
111 #define OP_path_resolve 2
112 #define OP_universe 3
116 #if MAXVAL <= UNIV_SIZE
118 #define MAXVAL (UNIV_SIZE+1)
121 typedef struct Feature
123 struct Feature* next;
142 static Feature_t dynamic[] =
144 { &dynamic[1], "FS_3D", "", 5, CONF_AST, OP_fs_3d },
145 { &dynamic[2], "PATH_RESOLVE", "", 12, CONF_AST, OP_path_resolve },
146 { 0, "UNIVERSE", "", 8, CONF_AST, OP_universe },
150 static Feature_t* features = dynamic;
152 static Ast_confdisc_t notify;
155 * synthesize state for fp
156 * value==0 just does lookup
157 * otherwise state is set to value
161 synthesize __PARAM__((register Feature_t* fp, const char* path, const char* value), (fp, path, value)) __OTORP__(register Feature_t* fp; const char* path; const char* value;){
170 static const char state[] = "_AST_FEATURES";
176 n = sizeof(state) + 3 * MAXVAL;
177 if (s = getenv(state))
180 if (!(data = newof(0, char, n, 0)))
184 data += sizeof(state) - 1;
186 if (s) strcpy(data, s);
193 while (isspace(*d)) d++;
195 if (strneq(d, s, n) && isspace(d[n]))
200 while (*d && !isspace(*d)) d++;
201 while (isspace(*d)) d++;
203 while (*s && !isspace(*s)) s++;
205 value = (const char*)d;
209 while (*s && !isspace(*s)) s++;
210 while (isspace(*s)) s++;
212 while (*s && !isspace(*s)) s++;
214 if (strneq(v, value, n))
216 while (isspace(*s)) s++;
217 if (*s) while (*d = *s++) d++;
218 else if (d != data) d--;
221 while (*d && !isspace(*d)) d++;
222 while (isspace(*d)) d++;
223 while (*d && !isspace(*d)) d++;
224 while (isspace(*d)) d++;
225 while (*d && !isspace(*d)) d++;
234 if (!path || !path[0] || path[0] == '/' && !path[1])
236 n += strlen(path) + strlen(value) + 3;
243 data -= sizeof(state);
244 c = n + last - data + 3 * MAXVAL;
246 if (!(data = newof(data, char, c, 0)))
249 data += sizeof(state);
255 while (*d = *s++) d++;
258 while (*d = *s++) d++;
261 while (*d = *s++) d++;
262 setenviron(data - sizeof(state));
263 n = s - (char*)value - 1;
265 if (n >= sizeof(fp->value))
266 n = sizeof(fp->value) - 1;
267 else if (n == 1 && (*value == '0' || *value == '-'))
269 strncpy(fp->value, value, n);
275 * initialize the value for fp
276 * if command!=0 then it is checked for on $PATH
277 * synthesize(fp,path,succeed) called on success
278 * otherwise synthesize(fp,path,fail) called
282 initialize __PARAM__((register Feature_t* fp, const char* path, const char* command, const char* succeed, const char* fail), (fp, path, command, succeed, fail)) __OTORP__(register Feature_t* fp; const char* path; const char* command; const char* succeed; const char* fail;){
286 if (fp->op != OP_path_resolve || !fs3d(FS3D_TEST))
288 if (fp->op == OP_universe)
289 ok = streq(_UNIV_DEFAULT, "att");
290 if (p = getenv("PATH"))
293 register char* d = p;
294 int offset = stktell(stkstd);
303 if (command && (fp->op != OP_universe || !ok))
307 sfwrite(stkstd, d, r);
309 sfputr(stkstd, command, 0);
310 stkseek(stkstd, offset);
311 if (!access(stkptr(stkstd, offset), X_OK))
314 if (fp->op != OP_universe)
326 if (fp->op == OP_universe)
328 if (strneq(p, "bin:", 4) || strneq(p, "usr/bin:", 8))
331 else if (fp->op == OP_path_resolve)
332 if (strneq(p, "ast/bin:", 8))
335 if (fp->op == OP_universe)
337 if (strneq(p, "5bin", 4))
342 if (strneq(p, "bsd", 3) || strneq(p, "ucb", 3))
357 synthesize(fp, path, ok ? succeed : fail);
361 * value==0 get feature name
362 * value!=0 set feature name
363 * 0 returned if error or not defined; otherwise previous value
367 feature __PARAM__((const char* name, const char* path, const char* value), (name, path, value)) __OTORP__(const char* name; const char* path; const char* value;){
368 register Feature_t* fp;
373 if (streq(value, "-") || streq(value, "0"))
375 if (notify && !(*notify)(name, path, value))
378 for (fp = features; fp && !streq(fp->name, name); fp = fp->next);
384 if (!(fp = newof(0, Feature_t, 1, n + 1)))
386 fp->name = (const char*)fp + sizeof(Feature_t);
387 strcpy((char*)fp->name, name);
396 fp->value[0] = fs3d(value ? value[0] ? FS3D_ON : FS3D_OFF : FS3D_TEST) ? '1' : 0;
399 case OP_path_resolve:
400 if (!synthesize(fp, path, value))
401 initialize(fp, path, "hostinfo", "logical", "physical");
406 if (getuniverse(fp->value) < 0)
407 strcpy(fp->value, "att");
415 while (n < univ_max && !streq(value, univ_name[n])
421 n = setuniverse(n + 1);
425 n = universe(value ? n + 1 : U_GET);
427 if (n <= 0 || n >= univ_max)
429 strcpy(fp->value, univ_name[n - 1]);
431 if (!synthesize(fp, path, value))
432 initialize(fp, path, "echo", "att", "ucb");
438 synthesize(fp, path, value);
446 * binary search for name in conf[]
450 lookup __PARAM__((register Lookup_t* look, const char* name), (look, name)) __OTORP__(register Lookup_t* look; const char* name;){
451 register Conf_t* mid = (Conf_t*)conf;
452 register Conf_t* lo = mid;
453 register Conf_t* hi = mid + conf_elements;
456 const char* oldname = name;
465 for (p = prefix; p < &prefix[prefix_elements]; p++)
466 if (strneq(name, p->name, p->length) && ((c = name[p->length] == '_') || isdigit(name[p->length]) && name[p->length + 1] == '_'))
468 if ((look->call = p->call) < 0)
470 look->flags |= CONF_MINMAX;
471 look->standard = p->standard;
473 name += p->length + c;
474 if (isdigit(name[0]) && name[1] == '_')
476 look->section = name[0] - '0';
479 else look->section = 1;
483 c = *((unsigned char*)name);
486 mid = lo + (hi - lo) / 2;
487 if (!(v = c - *((unsigned char*)mid->name)) && !(v = strcmp(name, mid->name)))
490 hi = lo + conf_elements - 1;
491 if (look->standard >= 0 && look->standard != mid->standard) do
493 if (look->standard > mid->standard)
502 if (!streq(name, mid->name))
504 } while (look->standard != mid->standard);
505 if (look->section >= 0 && look->section != mid->section) do
507 if (look->section > mid->section)
516 if (!streq(name, mid->name))
518 } while (look->section != mid->section);
519 if (look->call >= 0 && look->call != mid->call)
531 look->error = "call";
534 look->error = "standard";
537 look->error = "section";
542 * print value line for p
543 * if !name then value prefixed by "p->name="
544 * if (flags & CONF_MINMAX) then default minmax value used
548 print __PARAM__((Sfio_t* sp, register Lookup_t* look, const char* name, const char* path), (sp, look, name, path)) __OTORP__(Sfio_t* sp; register Lookup_t* look; const char* name; const char* path;){
549 register Conf_t* p = look->conf;
550 register int flags = look->flags|CONF_DEFINED;
557 if (!name && p->call != CONF_confstr && (p->flags & (CONF_FEATURE|CONF_LIMIT)) && (p->flags & (CONF_LIMIT|CONF_PREFIXED)) != CONF_LIMIT)
559 flags |= CONF_PREFIXED;
560 if (p->flags & CONF_DEFINED)
561 flags |= CONF_MINMAX;
565 switch ((flags & CONF_MINMAX) && (p->flags & CONF_DEFINED) ? 0 : p->call)
568 if (p->flags & CONF_DEFINED)
572 flags &= ~CONF_DEFINED;
578 if (!(v = confstr(p->op, buf, sizeof(buf))))
586 v = pathconf(path, p->op);
602 if ((p->flags & CONF_FEATURE) || !(p->flags & (CONF_LIMIT|CONF_MINMAX)))
603 flags &= ~CONF_DEFINED;
605 else if (!(flags & CONF_PREFIXED))
609 liberror(lib, ERROR_SYSTEM|2, "%s: %s error", p->name, call);
612 flags &= ~CONF_DEFINED;
615 else flags &= ~CONF_DEFINED;
622 offset = stktell(sp);
624 if (!(flags & CONF_PREFIXED))
627 sfprintf(sp, "%s=", p->name);
628 if (flags & CONF_ERROR)
629 sfprintf(sp, "error");
630 else if (p->call == CONF_confstr)
631 sfprintf(sp, "%s", buf);
633 sfprintf(sp, "%ld", v);
634 else if (flags & CONF_DEFINED)
635 sfprintf(sp, "%lu", v);
636 else sfprintf(sp, "undefined");
640 if (!name && p->call != CONF_confstr && (p->flags & (CONF_FEATURE|CONF_MINMAX)))
642 if (p->flags & CONF_UNDERSCORE)
644 sfprintf(sp, "%s", prefix[p->standard].name);
646 sfprintf(sp, "%d", p->section);
647 sfprintf(sp, "_%s=", p->name);
648 if (p->flags & CONF_DEFINED)
650 if ((v = p->value) == -1 && ((p->flags & CONF_FEATURE) || !(p->flags & (CONF_LIMIT|CONF_MINMAX))))
651 flags &= ~CONF_DEFINED;
652 else flags |= CONF_DEFINED;
655 sfprintf(sp, "%ld", v);
656 else if (flags & CONF_DEFINED)
657 sfprintf(sp, "%lu", v);
658 else sfprintf(sp, "undefined");
664 stkseek(stkstd, offset);
665 return(stkptr(sp, offset));
671 * value==0 gets value for name
672 * value!=0 sets value for name and returns previous value
673 * path==0 implies path=="/"
675 * settable return values are in permanent store
676 * non-settable return values are on stkstd
678 * if (!strcmp(astconf("PATH_RESOLVE", NiL, NiL), "logical"))
681 * universe = astconf("UNIVERSE", NiL, "att");
682 * astconf("UNIVERSE", NiL, universe);
686 astconf __PARAM__((const char* name, const char* path, const char* value), (name, path, value)) __OTORP__(const char* name; const char* path; const char* value;){
692 if (lookup(&look, name))
696 liberror(lib, 2, "%s: cannot set value", name);
700 return(print(NiL, &look, name, path));
703 liberror(lib, 2, "%s: invalid %s prefix", name, look.error);
704 else if ((look.standard < 0 || look.standard == CONF_AST) && look.call <= 0 && look.section <= 1 && (s = feature(look.name, path, value)))
706 else liberror(lib, 2, "%s: invalid symbol", name);
711 * set discipline function to be called when features change
712 * old discipline function returned
716 astconfdisc __PARAM__((Ast_confdisc_t new_notify), (new_notify)) __OTORP__(Ast_confdisc_t new_notify;){
717 Ast_confdisc_t old_notify = notify;
724 * list all name=value entries on sp
725 * path==0 implies path=="/"
726 * flags==0 lists all values
727 * flags&R_OK lists readonly values
728 * flags&W_OK lists writeable values
729 * flags&X_OK lists writeable values in inputable form
733 astconflist __PARAM__((Sfio_t* sp, const char* path, int flags), (sp, path, flags)) __OTORP__(Sfio_t* sp; const char* path; int flags;){
741 else if (access(path, F_OK))
743 liberror(lib, 2, "%s: not found", path);
750 else if (flags & X_OK)
753 for (look.conf = (Conf_t*)conf; look.conf < (Conf_t*)&conf[conf_elements]; look.conf++)
754 print(sp, &look, NiL, path);
756 for (fp = features; fp; fp = fp->next)
758 #if HUH950401 /* don't get prefix happy */
759 if (fp->standard >= 0)
760 sfprintf(sp, "_%s_", prefix[fp->standard].name);
762 if (!*(s = feature(fp->name, path, NiL)))
764 if (flags & X_OK) sfprintf(sp, "%s %s - %s\n", ID, fp->name, s);
765 else sfprintf(sp, "%s=%s\n", fp->name, s);