try to get the kernel printfs out before console starts reboot
[unix-history] / usr / src / old / symorder / symorder.c
CommitLineData
22e155fc
DF
1/*
2 * Copyright (c) 1980 Regents of the University of California.
3 * All rights reserved. The Berkeley software License Agreement
4 * specifies the terms and conditions for redistribution.
5 */
6
7#ifndef lint
8char copyright[] =
9"@(#) Copyright (c) 1980 Regents of the University of California.\n\
10 All rights reserved.\n";
11#endif not lint
12
34aa0635 13#ifndef lint
48e0aad0 14static char sccsid[] = "@(#)symorder.c 5.2 (Berkeley) %G%";
22e155fc 15#endif not lint
45991748 16
faa0bd68
BJ
17/*
18 * symorder - reorder symbol table
19 */
45991748 20
faa0bd68 21#include <stdio.h>
faa0bd68 22#include <sys/types.h>
840fc587 23#include <sys/stat.h>
13257757 24#include <a.out.h>
faa0bd68
BJ
25
26#define SPACE 100
27
28struct nlist order[SPACE];
29
45991748 30char *savestr(), *index(), *malloc();
faa0bd68 31struct exec exec;
45991748 32off_t sa;
faa0bd68
BJ
33struct stat stb;
34int nsym = 0;
35int symfound = 0;
45991748
RC
36char *strings;
37char *newstrings;
38struct nlist *symtab;
39struct nlist *newtab;
40int symsize;
faa0bd68
BJ
41char asym[BUFSIZ];
42
43main(argc, argv)
44 char **argv;
45{
45991748
RC
46 register char *ns;
47 register struct nlist *symp;
48 register struct nlist *p;
faa0bd68 49 register FILE *f;
45991748 50 register int i;
faa0bd68
BJ
51 int n, o;
52
45991748 53 if (argc != 3) {
faa0bd68
BJ
54 fprintf(stderr, "Usage: symorder orderlist file\n");
55 exit(1);
56 }
45991748 57 if ((f = fopen(argv[1], "r")) == NULL) {
faa0bd68
BJ
58 perror(argv[1]);
59 exit(1);
60 }
45991748
RC
61 for (p = order; fgets(asym, sizeof asym, f) != NULL; p++, nsym++) {
62 for (i = 0; asym[i] && asym[i] != '\n'; i++)
faa0bd68
BJ
63 continue;
64 if (asym[i] == '\n')
65 asym[i] = 0;
66 p->n_un.n_name = savestr(asym);
faa0bd68
BJ
67 }
68 fclose(f);
45991748 69 if ((f = fopen(argv[2], "r")) == NULL)
faa0bd68 70 perror(argv[2]), exit(1);
45991748 71 if ((o = open(argv[2], 1)) < 0)
faa0bd68 72 perror(argv[2]), exit(1);
45991748 73 if ((fread(&exec, sizeof exec, 1, f)) != 1 || N_BADMAG(exec)) {
faa0bd68
BJ
74 fprintf(stderr, "symorder: %s: bad format\n", argv[2]);
75 exit(1);
76 }
77 if (exec.a_syms == 0) {
78 fprintf(stderr, "symorder: %s is stripped\n", argv[2]);
79 exit(1);
80 }
81 fstat(fileno(f), &stb);
82 if (stb.st_size < N_STROFF(exec)+sizeof(off_t)) {
45991748
RC
83 fprintf(stderr, "symorder: %s is in old format or truncated\n",
84 argv[2]);
faa0bd68
BJ
85 exit(1);
86 }
87 sa = N_SYMOFF(exec);
faa0bd68
BJ
88 fseek(f, sa, 0);
89 n = exec.a_syms;
45991748
RC
90 symtab = (struct nlist *)malloc(n);
91 if (symtab == (struct nlist *)0) {
92 fprintf(stderr, "symorder: Out of core, no space for symtab\n");
93 exit(1);
94 }
95 if (fread((char *)symtab, 1, n, f) != n) {
96 fprintf(stderr, "symorder: Short file "); perror(argv[2]);
97 exit(1);
98 }
99 if (fread((char *)&symsize, sizeof (int), 1, f) != 1 ||
100 symsize <= 0) {
101 fprintf(stderr, "symorder: No strings "); perror(argv[2]);
102 exit(1);
103 }
104 strings = malloc(symsize);
105 if (strings == (char *)0) {
106 fprintf(stderr,"symorder: Out of core, no space for strings\n");
107 exit(1);
108 }
48e0aad0
KM
109 /*
110 * Need to subtract four from symsize here since
111 * symsize includes itself, and we've already read
112 * it. (6/30/85 chris@maryland)
113 */
114 if (fread(strings, 1, symsize - 4, f) != symsize - 4) {
45991748
RC
115 fprintf(stderr, "symorder: Truncated strings ");
116 perror(argv[2]);
117 exit(1);
118 }
119
120 newtab = (struct nlist *)malloc(n);
121 if (newtab == (struct nlist *)0) {
122 fprintf(stderr,
123 "symorder: Out of core, no space for new symtab\n");
124 exit(1);
125 }
126 i = n / sizeof (struct nlist);
127 reorder(symtab, newtab, i);
128 free((char *)symtab);
129 symtab = newtab;
130
131 newstrings = malloc(symsize);
132 if (newstrings == (char *)0) {
133 fprintf(stderr,
134 "symorder: Out of core, no space for newstrings\n");
135 exit(1);
136 }
137 ns = newstrings;
138 for (symp = symtab; --i >= 0; symp++) {
139 if (symp->n_un.n_strx == 0)
140 continue;
141 symp->n_un.n_strx -= sizeof (int);
142 if ((unsigned)symp->n_un.n_strx >= symsize) {
143 fprintf(stderr,"symorder: Corrupted string pointers\n");
faa0bd68
BJ
144 exit(1);
145 }
45991748
RC
146 strcpy(ns, &strings[symp->n_un.n_strx]);
147 symp->n_un.n_strx = (ns - newstrings) + sizeof (int);
148 ns = index(ns, 0) + 1;
149 if (ns > &newstrings[symsize]) {
150 fprintf(stderr, "symorder: Strings grew longer!\n");
151 exit(1);
faa0bd68
BJ
152 }
153 }
45991748
RC
154
155 lseek(o, sa, 0);
156 if (write(o, (char *)symtab, n) != n) {
157 fprintf(stderr, "symorder: Write failed "); perror(argv[2]);
158 exit(1);
159 }
160 if (write(o, (char *)&symsize, sizeof (int)) != sizeof (int)) {
161 fprintf(stderr, "symorder: Write failed "); perror(argv[2]);
162 exit(1);
163 }
48e0aad0 164 if (write(o, newstrings, symsize - 4) != symsize - 4) {
45991748
RC
165 fprintf(stderr, "symorder: Write failed "); perror(argv[2]);
166 exit(1);
167 }
168 if ((i = nsym - symfound) > 0) {
169 fprintf(stderr, "symorder: %d symbol%s not found:\n",
170 i, i == 1 ? "" : "s");
faa0bd68
BJ
171 for (i = 0; i < nsym; i++) {
172 if (order[i].n_value == 0)
173 printf("%s\n", order[i].n_un.n_name);
174 }
175 }
45991748
RC
176 exit(0);
177}
178
179reorder(st1, st2, n)
180 register struct nlist *st1, *st2;
181 register n;
182{
183 register struct nlist *stp = st2 + nsym;
184 register i;
185
186 while (--n >= 0) {
187 i = inlist(st1);
188 if (i == -1)
189 *stp++ = *st1++;
190 else
191 st2[i] = *st1++;
192 }
193}
194
195inlist(p)
196 register struct nlist *p;
197{
198 register char *nam;
199 register struct nlist *op;
200
201 if (p->n_type & N_STAB)
202 return (-1);
203 if (p->n_un.n_strx == 0)
204 return (-1);
205
206 nam = &strings[p->n_un.n_strx - sizeof(int)];
207 if (nam >= &strings[symsize]) {
208 fprintf(stderr, "symorder: corrupt symtab\n");
209 exit(1);
210 }
211
212 for (op = &order[nsym]; --op >= order; ) {
213 if (strcmp(op->n_un.n_name, nam) != 0)
214 continue;
215 if (op->n_value == 0) {
216 op->n_value++;
217 symfound++;
218 }
219 return (op - order);
220 }
221 return (-1);
faa0bd68
BJ
222}
223
224#define NSAVETAB 4096
225char *savetab;
226int saveleft;
227
228char *
229savestr(cp)
230 register char *cp;
231{
232 register int len;
233
234 len = strlen(cp) + 1;
235 if (len > saveleft) {
236 saveleft = NSAVETAB;
237 if (len > saveleft)
238 saveleft = len;
239 savetab = (char *)malloc(saveleft);
240 if (savetab == 0) {
241 fprintf(stderr,
242 "symorder: ran out of memory (savestr)\n");
243 exit(1);
244 }
245 }
246 strncpy(savetab, cp, len);
247 cp = savetab;
248 savetab += len;
249 saveleft -= len;
250 return (cp);
251}