|
|
1.1 root 1: /*-
2: * Copyright (c) 1990 The Regents of the University of California.
3: * All rights reserved.
4: *
5: * Redistribution and use in source and binary forms are permitted provided
6: * that: (1) source distributions retain this entire copyright notice and
7: * comment, and (2) distributions including binaries display the following
8: * acknowledgement: ``This product includes software developed by the
9: * University of California, Berkeley and its contributors'' in the
10: * documentation or other materials provided with the distribution and in
11: * all advertising materials mentioning features or use of this software.
12: * Neither the name of the University nor the names of its contributors may
13: * be used to endorse or promote products derived from this software without
14: * specific prior written permission.
15: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
16: * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
17: * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
18: */
19:
20: #ifndef lint
21: char copyright[] =
22: "@(#) Copyright (c) 1990 The Regents of the University of California.\n\
23: All rights reserved.\n";
24: #endif /* not lint */
25:
26: #ifndef lint
27: static char sccsid[] = "@(#)kvm_mkdb.c 5.5 (Berkeley) 6/25/90";
28: #endif /* not lint */
29:
30: #include <sys/param.h>
31: #include <sys/file.h>
32: #include <ndbm.h>
33: #include <a.out.h>
34: #include <kvm.h>
35: #include <paths.h>
36: #include <limits.h>
37: #include <errno.h>
38: #include <string.h>
39: #include <stdio.h>
40:
41: char *tmp;
42: #define basename(cp) ((tmp=rindex((cp), '/')) ? tmp+1 : (cp))
43: #define USAGE "kvm_mkdb"
44:
45: char *progname;
46:
47: main(argc, argv)
48: char *argv[];
49: {
50: DBM *db;
51: char *nlistpath, *nlistname;
52: char dbtemp[MAXPATHLEN];
53: char dbname[MAXPATHLEN];
54: extern char *optarg;
55: extern int optind;
56: int ch;
57:
58: progname = argv[0];
59: while ((ch = getopt(argc, argv, "")) != EOF)
60: switch((char)ch) {
61: case '?':
62: default:
63: fprintf(stderr, "usage: %s", progname, USAGE);
64: exit(1);
65: }
66: argc -= optind;
67: argv += optind;
68:
69: nlistpath = argc > 1 ? argv[0] : _PATH_UNIX;
70: nlistname = basename(nlistpath);
71: sprintf(dbtemp, "%s/kvm_tmp%s", KVMDBDIR, nlistname);
72: sprintf(dbname, "%s/kvm_%s", KVMDBDIR, nlistname);
73: rmdb(dbtemp);
74: umask(0);
75: if ((db = dbm_open(dbtemp, O_CREAT|O_WRONLY|O_EXCL, 0644)) == NULL)
76: syserrexit("error opening dbmfile");
77: if (create_knlist(nlistpath, db) == -1)
78: errexit("error creating kernel namelist");
79: if (create_devnames(db) == -1)
80: errexit("error creating devnames");
81: rmdb(dbname);
82: mvdb(dbtemp, dbname);
83:
84: exit(0);
85: }
86:
87: rmdb(file)
88: char *file;
89: {
90: int len = strlen(file);
91:
92: if (len > (MAXPATHLEN - 5))
93: errexit("pathname too long: %s", file);
94: strcpy(file+len, ".dir");
95: if (unlink(file) < 0 && errno != ENOENT)
96: syserrexit("can't unlink %s", file);
97: strcpy(file+len, ".pag");
98: if (unlink(file) < 0 && errno != ENOENT)
99: syserrexit("can't unlink %s", file);
100: *(file+len) = '\0';
101: }
102:
103: mvdb(from, to)
104: char *from;
105: char *to;
106: {
107: int flen = strlen(from);
108: int tlen = strlen(to);
109:
110: if (flen > (MAXPATHLEN - 5) || tlen > (MAXPATHLEN - 5))
111: errexit("pathname too long: %s or %s", from, to);
112: strcpy(from+flen, ".dir");
113: strcpy(to+tlen, ".dir");
114: if (rename(from, to) == -1)
115: syserrexit("rename %s to %s", from, to);
116: strcpy(from+flen, ".pag");
117: strcpy(to+tlen, ".pag");
118: if (rename(from, to) == -1)
119: syserrexit("rename %s to %s", from, to);
120: *(from+flen) = *(to+tlen) = '\0';
121: }
122:
123: /* from libc/nlist.c */
124: #include <unistd.h>
125:
126: typedef struct nlist NLIST;
127: #define _strx n_un.n_strx
128: #define _name n_un.n_name
129: #define ISVALID(p) (p->_name && p->_name[0])
130: #define MAXSYMSIZE 256
131:
132: create_knlist(name, db)
133: char *name;
134: DBM *db;
135: {
136: register NLIST *p, *s;
137: struct exec ebuf;
138: FILE *fstr, *fsym;
139: NLIST nbuf;
140: off_t strings_offset, symbol_offset, symbol_size, lseek();
141: char sbuf[MAXSYMSIZE+1];
142: register char *bp;
143: register int c, len;
144: datum key, data;
145:
146: if (!(fsym = fopen(name, "r")))
147: syserrexit("can't open %s", name);
148: if (fread((char *)&ebuf, sizeof(struct exec), 1, fsym) != 1 ||
149: N_BADMAG(ebuf))
150: syserrexit("can't read exec");
151:
152: symbol_offset = N_SYMOFF(ebuf);
153: symbol_size = ebuf.a_syms;
154: strings_offset = symbol_offset + symbol_size;
155:
156: if (fseek(fsym, symbol_offset, SEEK_SET) == -1)
157: syserrexit("can't seek symbol table: %x", symbol_offset);
158: if ((fstr = fopen(name, "r")) == NULL)
159: syserrexit("can't open %s", name);
160:
161: sbuf[0] = KVMDB_NLIST;
162: key.dptr = sbuf;
163: data.dptr = (char *)&nbuf;
164: data.dsize = sizeof (NLIST);
165:
166: for (s = &nbuf; symbol_size; symbol_size -= sizeof (NLIST)) {
167: if (fread((char *)s, sizeof (NLIST), 1, fsym) != 1)
168: syserrexit("can't read nlist entry");
169: if (!s->_strx || s->n_type&N_STAB)
170: continue;
171: if (fseek(fstr, strings_offset + s->_strx, SEEK_SET) == -1)
172: syserrexit("can't seek string: %x",
173: strings_offset + s->_strx);
174: /*
175: * read string
176: */
177: bp = sbuf + 1;
178: len = 0;
179: while ((c = fgetc(fstr)) != EOF && c != '\0') {
180: if (++len == MAXSYMSIZE)
181: errexit("string too long");
182: *bp++ = c;
183: }
184: *bp = '\0';
185: /*
186: * and store it
187: */
188: key.dsize = bp - sbuf;
189: if (dbm_store(db, key, data, DBM_INSERT) < 0)
190: syserrexit("dbm_store");
191: if (strcmp(sbuf+1, "_version") == 0) {
192: /*
193: * store the value of version in VERSION
194: */
195: datum vers;
196: char versbuf[_BSD_LINE_MAX];
197: long versoff;
198: long reloffset;
199:
200: /* offset relative to start of text image in VM. */
201: #ifdef hp300
202: reloffset = s->n_value;
203: #endif
204: #ifdef tahoe
205: /*
206: * on tahoe, first 0x800 is reserved for communication
207: * with the console processor.
208: */
209: reloffset = ((s->n_value & ~KERNBASE) - 0x800);
210: #endif
211: #ifdef vax
212: reloffset = (s->n_value & ~KERNBASE);
213: #endif
214: /*
215: * When loaded, data is rounded
216: * to next page cluster after text, but not in file.
217: */
218: reloffset -= CLBYTES - (ebuf.a_text % CLBYTES);
219: versoff = N_TXTOFF(ebuf) + reloffset;
220: if (fseek(fstr, versoff, SEEK_SET) == -1)
221: syserrexit("seek (version): %x", s->n_value);
222: /*
223: * Just read version string up to, and
224: * including newline.
225: */
226: if (fgets(versbuf, _BSD_LINE_MAX, fstr) == NULL)
227: syserrexit("can't read version");
228: strcpy(sbuf+1, "VERSION");
229: key.dsize = (sizeof ("VERSION") - 1) + 1;
230: vers.dptr = versbuf;
231: vers.dsize = strlen(versbuf);
232: if (dbm_store(db, key, vers, DBM_INSERT) < 0)
233: syserrexit("dbm_store: can't store VERSION");
234: }
235: }
236: (void)fclose(fstr);
237: (void)fclose(fsym);
238: return (0);
239: }
240:
241: create_devnames() {}
242:
243: #include <varargs.h>
244:
245: warning(va_alist)
246: va_dcl
247: {
248: char *fmt;
249: va_list ap;
250:
251: fprintf(stderr, "%s: warning: ", progname);
252: va_start(ap);
253: fmt = va_arg(ap, char *);
254: (void) vfprintf(stderr, fmt, ap);
255: va_end(ap);
256: fprintf(stderr, "\n");
257: }
258:
259:
260: errexit(va_alist)
261: va_dcl
262: {
263: char *fmt;
264: va_list ap;
265:
266: fprintf(stderr, "%s: ", progname);
267: va_start(ap);
268: fmt = va_arg(ap, char *);
269: (void) vfprintf(stderr, fmt, ap);
270: va_end(ap);
271: fprintf(stderr, "\n");
272: exit(1);
273: }
274:
275:
276: syserrexit(va_alist)
277: va_dcl
278: {
279: char *fmt;
280: va_list ap;
281:
282: fprintf(stderr, "%s: ", progname);
283: va_start(ap);
284: fmt = va_arg(ap, char *);
285: (void) vfprintf(stderr, fmt, ap);
286: va_end(ap);
287: fprintf(stderr, ": %s\n", strerror(errno));
288: exit(1);
289: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.