xref: /plan9/sys/src/cmd/db/setup.c (revision 219b2ee8daee37f4aad58d63f21287faa8e4ffdc)
1 
2 /*
3  * init routines
4  */
5 #include "defs.h"
6 #include "fns.h"
7 
8 char	*symfil;
9 char	*corfil;
10 
11 Map	*symmap;
12 Map	*cormap;
13 Map	*dotmap;
14 
15 int fsym, fcor;
16 static Fhdr fhdr;
17 
18 extern	Mach		mmips;
19 extern	Machdata	mipsmach;
20 
21 static int getfile(char*, int, int);
22 
23 void
24 setsym(void)
25 {
26 	Symbol s;
27 
28 	if((fsym = getfile(symfil, 1, wtflag)) < 0) {
29 		symmap = dumbmap(-1);
30 		machdata = &mipsmach;
31 		mach = &mmips;
32 		return;
33 	}
34 	if (crackhdr(fsym, &fhdr)) {
35 		machbytype(fhdr.type);
36 		symmap = loadmap(symmap, fsym, &fhdr);
37 		if (symmap == 0)
38 			symmap = dumbmap(fsym);
39 		if (syminit(fsym, &fhdr) < 0)
40 			dprint("%r\n");
41 		if (mach->sbreg && lookup(0, mach->sbreg, &s))
42 			mach->sb = s.value;
43 	}
44 	else
45 		symmap = dumbmap(fsym);
46 }
47 
48 void
49 setcor(void)
50 {
51 	char buf[64];
52 	int fd;
53 	ulong ksp;
54 	long proc;		/* address of proc table */
55 
56 
57 	if(pid > 0){	/* set kbase; should probably do other things, too */
58 		sprint(buf, "/proc/%d/proc", pid);
59 		fd = open(buf, 0);
60 		if(fd >= 0){
61 			seek(fd, mach->kspoff, 0);
62 			if(read(fd, (char *)&ksp, 4) == 4)
63  			mach->kbase = machdata->swal(ksp) & ~(mach->pgsize-1);
64 			close(fd);
65 		}
66 	}
67 	if (cormap)
68 		close(fcor);
69 
70 	fcor = getfile(corfil, 2, ORDWR);
71 	if (fcor <= 0) {
72 		if (cormap)
73 			free(cormap);
74 		cormap = dumbmap(-1);
75 		return;
76 	}
77 	cormap = newmap(cormap, fcor, 3);
78 	if (!cormap)
79 		return;
80 	setmap(cormap, fhdr.txtaddr, fhdr.txtaddr+fhdr.txtsz, fhdr.txtaddr, "text");
81 	setmap(cormap, fhdr.dataddr, mach->kbase, fhdr.dataddr, "data");
82 	setmap(cormap, mach->kbase, mach->kbase+mach->pgsize, mach->kbase, "ublock");
83 	fixregs(cormap);
84 	if (kflag) {
85 		if (get4(cormap, mach->kbase, &proc) < 0)
86 			error("can't find proc table: %r");
87 
88 		adjustreg(mach->pc, proc+mach->kpcoff, mach->kpcdelta);
89 		adjustreg(mach->sp, proc+mach->kspoff, mach->kspdelta);
90 	}
91 	kmsys();
92 	return;
93 }
94 
95 Map *
96 dumbmap(int fd)
97 {
98 	Map *dumb;
99 	extern Mach mmips;
100 	extern Machdata mipsmach;
101 
102 	dumb = newmap(0, fd, 1);
103 	setmap(dumb, 0, 0xffffffff, 0, "data");
104 	if (!mach) 			/* default machine = mips */
105 		mach = &mmips;
106 	if (!machdata)
107 		machdata = &mipsmach;
108 	return dumb;
109 }
110 
111 /*
112  * set up maps for a direct process image (/proc)
113  */
114 
115 void
116 cmdmap(Map *map)
117 {
118 	int i;
119 	char name[MAXSYM];
120 
121 	extern char lastc;
122 
123 	rdc();
124 	readsym(name);
125 	i = findseg(map, name);
126 	if (i < 0)	/* not found */
127 		error("Invalid map name");
128 
129 	if (expr(0)) {
130 		if (strcmp(name, "text") == 0)
131 			textseg(expv, &fhdr);
132 		map->seg[i].b = expv;
133 	} else
134 		error("Invalid base address");
135 	if (expr(0))
136 		map->seg[i].e = expv;
137 	else
138 		error("Invalid end address");
139 	if (expr(0))
140 		map->seg[i].f = expv;
141 	else
142 		error("Invalid file offset");
143 	if (rdc()=='?' && map == cormap) {
144 		if (fcor)
145 			close(fcor);
146 		fcor=fsym;
147 		corfil=symfil;
148 		cormap = symmap;
149 	} else if (lastc == '/' && map == symmap) {
150 		if (fsym)
151 			close(fsym);
152 		fsym=fcor;
153 		symfil=corfil;
154 		symmap=cormap;
155 	} else
156 		reread();
157 }
158 
159 static int
160 getfile(char *filnam, int cnt, int omode)
161 {
162 	int f;
163 
164 	if (filnam == 0)
165 		return -1;
166 	if (strcmp(filnam, "-") == 0)
167 		return 0;
168 	f = open(filnam, omode|OCEXEC);
169 	if(f < 0 && omode == ORDWR){
170 		f = open(filnam, OREAD|OCEXEC);
171 		if(f >= 0)
172 			dprint("%s open read-only\n", filnam);
173 	}
174 	if (f < 0 && xargc > cnt)
175 		if (wtflag)
176 			f = create(filnam, 1, 0666);
177 	if (f < 0) {
178 		dprint("cannot open `%s': %r\n", filnam);
179 		return -1;
180 	}
181 	return f;
182 }
183 
184 void
185 kmsys(void)
186 {
187 	int i;
188 
189 	i = findseg(symmap, "text");
190 	if (i >= 0) {
191 		symmap->seg[i].b = symmap->seg[i].b&~mach->ktmask;
192 		symmap->seg[i].e = ~0;
193 	}
194 	i = findseg(symmap, "data");
195 	if (i >= 0) {
196 		symmap->seg[i].b |= mach->kbase;
197 		symmap->seg[i].e |= mach->kbase;
198 	}
199 	i = findseg(symmap, "ublock");
200 	if (i >= 0)
201 		unusemap(symmap, i);
202 	cormap = newmap(cormap, fcor, 1);
203 	if (cormap)
204 		setmap(cormap, 0, ~0, 0, "data");
205 }
206 
207 void
208 attachproc(void)
209 {
210 	char buf[100];
211 	int statstat;
212 	Dir sym, mem;
213 	int fd;
214 
215 	if (!adrflg) {
216 		dprint("used pid$a\n");
217 		return;
218 	}
219 	statstat = dirfstat(fsym, &sym);
220 	sprint(buf, "/proc/%d/mem", adrval);
221 	corfil = buf;
222 	setcor();
223 	sprint(buf, "/proc/%d/text", adrval);
224 	fd = open(buf, OREAD);
225 	if (statstat < 0 || fd < 0 || dirfstat(fd, &mem) < 0
226 				|| sym.qid.path != mem.qid.path)
227 		dprint("warning: text images may be inconsistent\n");
228 	if (fd >= 0)
229 		close(fd);
230 }
231