xref: /csrg-svn/old/sdb/docomm.c (revision 1332)
1*1332Sbill static	char sccsid[] = "@(#)docomm.c 4.1 10/09/80";
2*1332Sbill #include <signal.h>
3*1332Sbill #include "head.h"
4*1332Sbill #include <a.out.h>
5*1332Sbill #include <stab.h>
6*1332Sbill 
7*1332Sbill struct user u;
8*1332Sbill L_INT 	cntval;
9*1332Sbill INT	signo;
10*1332Sbill INT	adrflg;
11*1332Sbill INT	pid;
12*1332Sbill ADDR	userpc;
13*1332Sbill char	*s;
14*1332Sbill enum	{NOCOM, PRCOM, DSCOM, DSICOM} lastcom;
15*1332Sbill 		/* last command: nothing noteworthy, print source,
16*1332Sbill 			display variable, display instruction */
17*1332Sbill 
18*1332Sbill docommand() {
19*1332Sbill 	register char	*p;
20*1332Sbill 	register int	i;
21*1332Sbill 	register ADDR	addr, bkaddr;
22*1332Sbill 	struct proct 	*procp;
23*1332Sbill 	char s[4];
24*1332Sbill 
25*1332Sbill 	cntval = 1;
26*1332Sbill 	adrflg = 0;
27*1332Sbill 	errflg = 0;
28*1332Sbill 
29*1332Sbill 	if (scallf) {
30*1332Sbill 		doscall();
31*1332Sbill 		setcur(1);
32*1332Sbill 		lastcom = NOCOM;
33*1332Sbill 		return;
34*1332Sbill 	}
35*1332Sbill 
36*1332Sbill 	if (reflag) {  /* search for regular expression */
37*1332Sbill 		dore();
38*1332Sbill 		lastcom = PRCOM;
39*1332Sbill 		return;
40*1332Sbill 	}
41*1332Sbill 
42*1332Sbill 	if (cmd == '\0') {
43*1332Sbill 		if (integ != 0 && var[0] != '\0') {
44*1332Sbill 			error("Invalid command (1)");
45*1332Sbill 			return;
46*1332Sbill 		}
47*1332Sbill 		if (integ != 0) { /* print line number */
48*1332Sbill 			ffind(integ);
49*1332Sbill 			fprint();
50*1332Sbill 			lastcom = PRCOM;
51*1332Sbill 			return;
52*1332Sbill 		}
53*1332Sbill 		if (var[0] != 0) {
54*1332Sbill 			printf("Unexpected null command\n");
55*1332Sbill 			return;
56*1332Sbill 		}
57*1332Sbill 	}
58*1332Sbill 
59*1332Sbill 	switch (cmd) {
60*1332Sbill 
61*1332Sbill 	case 'Y':
62*1332Sbill 		debug = !debug;
63*1332Sbill 		break;
64*1332Sbill 
65*1332Sbill 	case 'V':
66*1332Sbill 		version();
67*1332Sbill 		break;
68*1332Sbill 
69*1332Sbill 	case 'M':
70*1332Sbill 		if (args[0]) {
71*1332Sbill 			setmap(args);
72*1332Sbill 		} else {
73*1332Sbill 			printmap("? map", &txtmap);
74*1332Sbill 			printmap("/ map", &datmap);
75*1332Sbill 		}
76*1332Sbill 		break;
77*1332Sbill 
78*1332Sbill 	case 'x':
79*1332Sbill 		printregs();
80*1332Sbill 		break;
81*1332Sbill 
82*1332Sbill 	case 'X':
83*1332Sbill 		printpc();
84*1332Sbill 		break;
85*1332Sbill 
86*1332Sbill 	case 'a':
87*1332Sbill 		if (integ) {
88*1332Sbill 			cpstr(args, "l\n");
89*1332Sbill 		} else if (proc[0]) {
90*1332Sbill 			cpall(args, "T\n");
91*1332Sbill 		} else {
92*1332Sbill 			error("Bad arguments");
93*1332Sbill 			break;
94*1332Sbill 		}
95*1332Sbill 		goto setbrk;
96*1332Sbill 		break;
97*1332Sbill 
98*1332Sbill 	case 'l':
99*1332Sbill 		setcur(1);
100*1332Sbill 		lastcom = NOCOM;
101*1332Sbill 		break;
102*1332Sbill 
103*1332Sbill 	case 'T':
104*1332Sbill 		prfrx(1);
105*1332Sbill 		lastcom = NOCOM;
106*1332Sbill 		break;
107*1332Sbill 
108*1332Sbill 	case 't':
109*1332Sbill 		prframe();
110*1332Sbill 		lastcom = NOCOM;
111*1332Sbill 		break;
112*1332Sbill 
113*1332Sbill 	case 'e':
114*1332Sbill 		p = args;
115*1332Sbill 		if (*p == '\0') {
116*1332Sbill #ifndef FLEXNAMES
117*1332Sbill 			printf("%.16s() in \"%s\"\n",
118*1332Sbill 				curproc()->pname, curfile);
119*1332Sbill #else
120*1332Sbill 			printf("%s() in \"%s\"\n",
121*1332Sbill 				curproc()->pname, curfile);
122*1332Sbill #endif
123*1332Sbill 			break;
124*1332Sbill 		}
125*1332Sbill 
126*1332Sbill 		while (*p != '\0')
127*1332Sbill 			if (*p++ == '.') goto l1;
128*1332Sbill 		/* argument is procedure name */
129*1332Sbill 		procp = findproc(args);
130*1332Sbill 		if ((procp->pname[0] != '\0') && (procp->sfptr != badfile)) {
131*1332Sbill 			finit(adrtofilep(procp->paddr)->sfilename);
132*1332Sbill 			ffind(procp->lineno);
133*1332Sbill 		}
134*1332Sbill 		else printf("Can't find %s\n", args);
135*1332Sbill #ifndef FLEXNAMES
136*1332Sbill 		printf("%.16s() in \"%s\"\n", curproc()->pname, curfile);
137*1332Sbill #else
138*1332Sbill 		printf("%s() in \"%s\"\n", curproc()->pname, curfile);
139*1332Sbill #endif
140*1332Sbill 		lastcom = PRCOM;
141*1332Sbill 		break;
142*1332Sbill 
143*1332Sbill 	l1:	/* argument is filename */
144*1332Sbill 		finit(args);
145*1332Sbill 		printf("\"%s\"\n", curfile);
146*1332Sbill 		lastcom = PRCOM;
147*1332Sbill 		break;
148*1332Sbill 
149*1332Sbill 	case 'p':
150*1332Sbill 		if (integ) ffind(integ);
151*1332Sbill 		fprint();
152*1332Sbill 		lastcom = PRCOM;
153*1332Sbill 		break;
154*1332Sbill 
155*1332Sbill 	case 'q':
156*1332Sbill 		exit(0);
157*1332Sbill 
158*1332Sbill 	case 'w':
159*1332Sbill 		if (integ) ffind(integ);
160*1332Sbill 		i = fline;
161*1332Sbill 		fback(WINDOW/2);
162*1332Sbill 		fprintn(WINDOW);
163*1332Sbill 		ffind(i);
164*1332Sbill 		lastcom = PRCOM;
165*1332Sbill 		break;
166*1332Sbill 
167*1332Sbill 	case 'Q':
168*1332Sbill 		prdebug();
169*1332Sbill 		break;
170*1332Sbill 
171*1332Sbill 	case 'z':
172*1332Sbill 		if (integ) ffind(integ);
173*1332Sbill 		fprintn(WINDOW);
174*1332Sbill 		lastcom = PRCOM;
175*1332Sbill 		break;
176*1332Sbill 
177*1332Sbill 	case '-':
178*1332Sbill 		fback(integ ? integ : 1);
179*1332Sbill 		fpargs();
180*1332Sbill 		lastcom = PRCOM;
181*1332Sbill 		break;
182*1332Sbill 
183*1332Sbill 	case '+':
184*1332Sbill 		fforward(integ ? integ : 1);
185*1332Sbill 		fpargs();
186*1332Sbill 		lastcom = PRCOM;
187*1332Sbill 		break;
188*1332Sbill 
189*1332Sbill 	case '\n':
190*1332Sbill 		switch (lastcom) {
191*1332Sbill 		case PRCOM:
192*1332Sbill 			fforward(1);
193*1332Sbill 			fprint();
194*1332Sbill 			break;
195*1332Sbill 		case DSCOM:
196*1332Sbill 			oaddr += oincr ? oincr : typetosize(otype, WORDSIZE);
197*1332Sbill 			printf("0x%x/ ", oaddr);
198*1332Sbill 			dispf((ADDR) oaddr, odesc,
199*1332Sbill 			    oclass == N_RSYM ? oclass : N_GSYM, otype, 0, 0, DSP);
200*1332Sbill 			break;
201*1332Sbill 		case DSICOM:
202*1332Sbill 			dot += oincr;
203*1332Sbill 			prisploc();
204*1332Sbill 			dispi(dot, odesc, N_GSYM, 0, 0);
205*1332Sbill 			break;
206*1332Sbill 		}
207*1332Sbill 		break;
208*1332Sbill 
209*1332Sbill 	case '\004':
210*1332Sbill 		if (!isatty(0))
211*1332Sbill 			exit(0);
212*1332Sbill 		switch (lastcom) {
213*1332Sbill 		case PRCOM:
214*1332Sbill 			fforward(1);
215*1332Sbill 			printf("\b");
216*1332Sbill 			fprintn(WINDOW);
217*1332Sbill 			lastcom = PRCOM;
218*1332Sbill 			break;
219*1332Sbill 		case DSICOM:
220*1332Sbill 			printf("\b");
221*1332Sbill 			for (i=0; i<WINDOW; i++) {
222*1332Sbill 				dot += oincr;
223*1332Sbill 				prisploc();
224*1332Sbill 				if (dispi(dot, odesc, N_GSYM, 0, 0) == -1)
225*1332Sbill 					break;
226*1332Sbill 			}
227*1332Sbill 			break;
228*1332Sbill 		case DSCOM:
229*1332Sbill 			printf("\b");
230*1332Sbill 			for (i=0; i<WINDOW; i++) {
231*1332Sbill 				oaddr += oincr ?
232*1332Sbill 					oincr : typetosize(otype, WORDSIZE);
233*1332Sbill 				printf("0x%x/ ", oaddr);
234*1332Sbill 				if (dispf((ADDR) oaddr, odesc,
235*1332Sbill 					oclass == N_RSYM ? oclass :
236*1332Sbill 					N_GSYM, otype, 0, 0, DSP) == -1)
237*1332Sbill 					break;
238*1332Sbill 			}
239*1332Sbill 			break;
240*1332Sbill 		default:
241*1332Sbill 			printf("\n");
242*1332Sbill 		}
243*1332Sbill 		break;
244*1332Sbill 
245*1332Sbill 	case 'r':
246*1332Sbill 		if (args[0] == '\0') getargs();
247*1332Sbill 	case 'R':
248*1332Sbill 		signo = 0;
249*1332Sbill 		cpstr(oldargs, args);
250*1332Sbill 		if (debug) error("calling dopcs");
251*1332Sbill 		if (integ) cntval = integ;
252*1332Sbill 		if (!executing) {
253*1332Sbill 			executing = TRUE;
254*1332Sbill 			if (integ) cntval = integ;
255*1332Sbill 			dopcs('r');
256*1332Sbill 			executing = FALSE;
257*1332Sbill 		}
258*1332Sbill 		if (debug) error("exiting dopcs");
259*1332Sbill 		bkaddr = -1;
260*1332Sbill 		goto f1;
261*1332Sbill 
262*1332Sbill 	case 'c':
263*1332Sbill 		signo = 0;
264*1332Sbill 	case 'C':
265*1332Sbill 		if (proc[0] != '\0' || integ != 0) {
266*1332Sbill 			setdot();
267*1332Sbill 			if (dot == -1) {
268*1332Sbill 				error("Cannot set temporary breakpoint");
269*1332Sbill 				break;
270*1332Sbill 			}
271*1332Sbill 			dopcs('b');
272*1332Sbill 			bkaddr = dot;
273*1332Sbill 		} else
274*1332Sbill 			bkaddr = -1;
275*1332Sbill 		integ = atoi(args);
276*1332Sbill 
277*1332Sbill f1:		if (debug) error("calling dopcs");
278*1332Sbill 		if (integ) cntval = integ;
279*1332Sbill 		dopcs('c');
280*1332Sbill 		if (debug) error("exiting dopcs");
281*1332Sbill 		if (bkaddr != -1) {
282*1332Sbill 			ADDR dotsave;
283*1332Sbill 			dotsave = dot;
284*1332Sbill 			dot = bkaddr;
285*1332Sbill 			dopcs('d');
286*1332Sbill 			dot = dotsave;
287*1332Sbill 		}
288*1332Sbill 		if (!signo) printf("Breakpoint");
289*1332Sbill 		printf(" at\n");
290*1332Sbill 		setcur(1);
291*1332Sbill 		lastcom = NOCOM;
292*1332Sbill 		break;
293*1332Sbill 
294*1332Sbill 	case 'S':
295*1332Sbill 	case 's':
296*1332Sbill 		signo = 0;
297*1332Sbill 		integ = atoi(args);
298*1332Sbill 		singstep(integ ? integ : 1, cmd);
299*1332Sbill 		if (signo) printf("\n");
300*1332Sbill 		setcur(1);
301*1332Sbill 		lastcom = NOCOM;
302*1332Sbill 		break;
303*1332Sbill 
304*1332Sbill 	case 'g':
305*1332Sbill 		if (pid == 0  ||  signo) {
306*1332Sbill 			error("Not stopped at breakpoint");
307*1332Sbill 			break;
308*1332Sbill 		}
309*1332Sbill 		setdot();
310*1332Sbill 		if (dot == -1) {
311*1332Sbill 			error("Bad address");
312*1332Sbill 			break;
313*1332Sbill 		}
314*1332Sbill 		adrflg = 1;
315*1332Sbill 		integ = atoi(args);
316*1332Sbill 		if (integ) cntval = integ;
317*1332Sbill 		dopcs('c');
318*1332Sbill 		if (!signo) printf("Breakpoint");
319*1332Sbill 		printf(" at\n");
320*1332Sbill 		setcur(1);
321*1332Sbill 		lastcom = NOCOM;
322*1332Sbill 		break;
323*1332Sbill 
324*1332Sbill 	case 'k':
325*1332Sbill 		if (scallx) {
326*1332Sbill 	 		userpc = dot = *(ADDR *)(((ADDR)&u)+PC) = pcs;
327*1332Sbill 	 		*(ADDR *)(((ADDR)&u)+FP) = fps;
328*1332Sbill 	 		*(ADDR *)(((ADDR)&u)+AP) = aps;
329*1332Sbill 			if (bkpts)
330*1332Sbill 				bkpts->flag = flagss;
331*1332Sbill 			scallx = 0;
332*1332Sbill 			error("Procedure killed");
333*1332Sbill 			longjmp(env, 0);
334*1332Sbill 		} else {
335*1332Sbill 			dopcs('k');
336*1332Sbill 			printf("\n");
337*1332Sbill 			lastcom = NOCOM;
338*1332Sbill 			break;
339*1332Sbill 		}
340*1332Sbill 
341*1332Sbill 	case 'B':
342*1332Sbill 		prbkpt();
343*1332Sbill 		break;
344*1332Sbill 
345*1332Sbill 	case 'b':
346*1332Sbill 	setbrk:
347*1332Sbill 		if (proc[0] == '\0' && integ == 0) {
348*1332Sbill 			integ = fline;
349*1332Sbill 		}
350*1332Sbill 		setdot();
351*1332Sbill 		if (dot == -1 || dot == 0) {
352*1332Sbill 			error("Cannot set breakpoint");
353*1332Sbill 			break;
354*1332Sbill 		}
355*1332Sbill 		dopcs('b');
356*1332Sbill 		s[0] = ' ';
357*1332Sbill 		s[1] = cmd;
358*1332Sbill 		s[2] = '\n';
359*1332Sbill 		s[3] = 0;
360*1332Sbill 		s[1] = cmd;
361*1332Sbill 		printbkpt(s, adrtoprocp(dot), dot);
362*1332Sbill 		break;
363*1332Sbill 
364*1332Sbill 	case 'd':
365*1332Sbill 		if (proc[0] == '\0' && integ == 0) {
366*1332Sbill 			idbkpt();
367*1332Sbill 			break;
368*1332Sbill 		}
369*1332Sbill 		setdot();
370*1332Sbill 		if (dot == -1) {
371*1332Sbill 			error("Non existent breakpoint");
372*1332Sbill 			break;
373*1332Sbill 		}
374*1332Sbill 		dopcs('d');
375*1332Sbill 		break;
376*1332Sbill 
377*1332Sbill 	case 'D':
378*1332Sbill 		dabkpt();
379*1332Sbill 		error("All breakpoints deleted");
380*1332Sbill 		break;
381*1332Sbill 
382*1332Sbill 	case 'm':
383*1332Sbill 		addr = varaddr(proc[0] ? proc : curproc()->pname, var);
384*1332Sbill 		printf("stopped with value %d\n", monex(addr, 'd'));
385*1332Sbill 		setcur(1);
386*1332Sbill 		lastcom = NOCOM;
387*1332Sbill 		break;
388*1332Sbill 
389*1332Sbill 	case '?':
390*1332Sbill 		if (!(var[0] == '.' && var[1] == '\0'))
391*1332Sbill 			setdot();
392*1332Sbill 		if (errflg) {
393*1332Sbill 			error(errflg);
394*1332Sbill 			break;
395*1332Sbill 		}
396*1332Sbill 		prisploc();
397*1332Sbill 		dispi(dot, args[0] ? args : "i", N_GSYM, 0, 0);
398*1332Sbill 		lastcom = DSICOM;
399*1332Sbill 		break;
400*1332Sbill 
401*1332Sbill 	case '/':
402*1332Sbill 		if (var[0] == '.' && var[1] == '\0') {
403*1332Sbill 			if (integ == 0) integ = oaddr;
404*1332Sbill 			dispf((ADDR) integ, args[0] ? args : odesc,
405*1332Sbill 			    oclass == N_RSYM ? oclass : N_GSYM, otype, 0, 0, DSP);
406*1332Sbill 			oaddr = integ;
407*1332Sbill 		} else
408*1332Sbill 		if (integ && (var[0] == '\0')) {
409*1332Sbill 			dispf((ADDR) integ, args, N_GSYM, 0, 0, 0, DSP);
410*1332Sbill 			oaddr = integ;
411*1332Sbill 			cpstr(odesc, args);
412*1332Sbill 			oclass = N_GSYM;
413*1332Sbill 			otype = 0;
414*1332Sbill 		} else
415*1332Sbill 			dispvar(proc, var, args);
416*1332Sbill 		lastcom = DSCOM;
417*1332Sbill 		break;
418*1332Sbill 
419*1332Sbill 	case '=':
420*1332Sbill 		if (var[0] == '\0') {
421*1332Sbill 			if (proc[0]) {
422*1332Sbill 				addr = getaddr(proc, integ);
423*1332Sbill 				if (addr == -1) {
424*1332Sbill 					error("Unknown address");
425*1332Sbill 					break;
426*1332Sbill 				}
427*1332Sbill 			}
428*1332Sbill 			else
429*1332Sbill 				addr = integ;
430*1332Sbill 			dispf(addr, args[0] ? args : "x", 0, -1, 0, 0, DSP);
431*1332Sbill 		} else
432*1332Sbill 			findvar(proc, var, args[0] ? args : "x", 2);
433*1332Sbill 		break;
434*1332Sbill 
435*1332Sbill 	case '!':
436*1332Sbill 		if (var[0] == '\0')
437*1332Sbill 			addr = getaddr(proc, integ);
438*1332Sbill 		else
439*1332Sbill 			addr = varaddr(proc, var);
440*1332Sbill 		if (addr == -1)
441*1332Sbill 			error("Unknown variable");
442*1332Sbill 		else {
443*1332Sbill 			if (number(args[0]) || eqany(args[0], ".-")) {
444*1332Sbill 				char *p;
445*1332Sbill 				double atof();
446*1332Sbill 				union {
447*1332Sbill 					struct{
448*1332Sbill 						int w1, w2;
449*1332Sbill 					} ww;
450*1332Sbill 					double d;
451*1332Sbill 				} dbl;
452*1332Sbill 
453*1332Sbill 				p = (args[0] == '-') ? args+1 : args;
454*1332Sbill 				for (; *p != '.' && *p != 'e'; p++) {
455*1332Sbill 					if (!number(*p)) goto l2;
456*1332Sbill 				}
457*1332Sbill 				dbl.d = atof(args);
458*1332Sbill 				putval(addr, 'd', dbl.ww.w1);
459*1332Sbill 				if (typetodesc(sl_type,0)[0] == 'g')
460*1332Sbill 					putval(addr+WORDSIZE, 'd', dbl.ww.w2);
461*1332Sbill 				break;
462*1332Sbill 			}
463*1332Sbill l2:			if (percentflag)
464*1332Sbill 				*(ADDR *)(((ADDR)&u)+addr) = argvalue(args);
465*1332Sbill 			else if (sl_class == N_RSYM && addr < 16)
466*1332Sbill 				putreg(addr,typetodesc(sl_type,subflag)[0],
467*1332Sbill 						argvalue(args));
468*1332Sbill 			else
469*1332Sbill 				putval(addr,typetodesc(sl_type,subflag)[0],
470*1332Sbill 						argvalue(args));
471*1332Sbill 		}
472*1332Sbill 		lastcom = NOCOM;
473*1332Sbill 		break;
474*1332Sbill 
475*1332Sbill 	case '"':
476*1332Sbill 		printf(args);
477*1332Sbill 		break;
478*1332Sbill 	}
479*1332Sbill }
480*1332Sbill 
481*1332Sbill fpargs() {
482*1332Sbill 	register int i;
483*1332Sbill 
484*1332Sbill 	switch(args[0]) {
485*1332Sbill 	case 'p':
486*1332Sbill 	case '\0':
487*1332Sbill 		fprint();
488*1332Sbill 		break;
489*1332Sbill case 'w':
490*1332Sbill 		i = fline;
491*1332Sbill 		fback(WINDOW/2);
492*1332Sbill 		fprintn(WINDOW);
493*1332Sbill 		ffind(i);
494*1332Sbill 		break;
495*1332Sbill 	case 'z':
496*1332Sbill 		fprintn(WINDOW);
497*1332Sbill 		break;
498*1332Sbill 	}
499*1332Sbill }
500*1332Sbill 
501*1332Sbill MSG	BADTXT;
502*1332Sbill /* Used by a, b, c, C, d and g commands to find linenumber */
503*1332Sbill setdot() {
504*1332Sbill 	if (ncolonflag) {
505*1332Sbill 		dot = integ;
506*1332Sbill 		get(dot, ISP);
507*1332Sbill 		if (errflg)
508*1332Sbill 			dot = -1;
509*1332Sbill 	} else {
510*1332Sbill 		dot = getaddr(proc, integ);
511*1332Sbill 		if (dot == -1)
512*1332Sbill 			errflg = "Bad line number";
513*1332Sbill 	}
514*1332Sbill }
515