xref: /plan9/sys/src/cmd/qi/symbols.c (revision f19e7b749ec99577072cd8e44030fe810f42c7ad)
17d9195a7SDavid du Colombier #include <u.h>
27d9195a7SDavid du Colombier #include <libc.h>
37d9195a7SDavid du Colombier #include <bio.h>
47d9195a7SDavid du Colombier #include <mach.h>
57d9195a7SDavid du Colombier #define Extern extern
67d9195a7SDavid du Colombier #include "power.h"
77d9195a7SDavid du Colombier 
87d9195a7SDavid du Colombier #define	STRINGSZ	128
97d9195a7SDavid du Colombier 
107d9195a7SDavid du Colombier /*
117d9195a7SDavid du Colombier  *	print the value of dot as file:line
127d9195a7SDavid du Colombier  */
137d9195a7SDavid du Colombier void
printsource(long dot)147d9195a7SDavid du Colombier printsource(long dot)
157d9195a7SDavid du Colombier {
167d9195a7SDavid du Colombier 	char str[STRINGSZ];
177d9195a7SDavid du Colombier 
187d9195a7SDavid du Colombier 	if (fileline(str, STRINGSZ, dot))
197d9195a7SDavid du Colombier 		Bprint(bioout, "%s", str);
207d9195a7SDavid du Colombier }
217d9195a7SDavid du Colombier 
227d9195a7SDavid du Colombier void
printlocals(Symbol * fn,ulong fp)237d9195a7SDavid du Colombier printlocals(Symbol *fn, ulong fp)
247d9195a7SDavid du Colombier {
257d9195a7SDavid du Colombier 	int i;
267d9195a7SDavid du Colombier 	Symbol s;
277d9195a7SDavid du Colombier 
287d9195a7SDavid du Colombier 	s = *fn;
297d9195a7SDavid du Colombier 	for (i = 0; localsym(&s, i); i++) {
307d9195a7SDavid du Colombier 		if (s.class != CAUTO)
317d9195a7SDavid du Colombier 			continue;
327d9195a7SDavid du Colombier 		Bprint(bioout, "\t%s=#%lux\n", s.name, getmem_4(fp-s.value));
337d9195a7SDavid du Colombier 	}
347d9195a7SDavid du Colombier }
357d9195a7SDavid du Colombier 
367d9195a7SDavid du Colombier void
printparams(Symbol * fn,ulong fp)377d9195a7SDavid du Colombier printparams(Symbol *fn, ulong fp)
387d9195a7SDavid du Colombier {
397d9195a7SDavid du Colombier 	int i;
407d9195a7SDavid du Colombier 	Symbol s;
417d9195a7SDavid du Colombier 	int first;
427d9195a7SDavid du Colombier 
437d9195a7SDavid du Colombier 	fp += mach->szreg;			/* skip saved pc */
447d9195a7SDavid du Colombier 	s = *fn;
457d9195a7SDavid du Colombier 	for (first = i = 0; localsym(&s, i); i++) {
467d9195a7SDavid du Colombier 		if (s.class != CPARAM)
477d9195a7SDavid du Colombier 			continue;
487d9195a7SDavid du Colombier 		if (first++)
497d9195a7SDavid du Colombier 			Bprint(bioout, ", ");
507d9195a7SDavid du Colombier 		Bprint(bioout, "%s=#%lux", s.name, getmem_4(fp+s.value));
517d9195a7SDavid du Colombier 	}
527d9195a7SDavid du Colombier 	Bprint(bioout, ") ");
537d9195a7SDavid du Colombier }
547d9195a7SDavid du Colombier 
557d9195a7SDavid du Colombier #define STARTSYM	"_main"
567d9195a7SDavid du Colombier #define	FRAMENAME	".frame"
577d9195a7SDavid du Colombier 
587d9195a7SDavid du Colombier void
stktrace(int modif)597d9195a7SDavid du Colombier stktrace(int modif)
607d9195a7SDavid du Colombier {
617d9195a7SDavid du Colombier 	ulong pc, sp;
627d9195a7SDavid du Colombier 	Symbol s, f;
637d9195a7SDavid du Colombier 	int i;
647d9195a7SDavid du Colombier 	char buf[512];
657d9195a7SDavid du Colombier 
667d9195a7SDavid du Colombier 	pc = reg.pc;
677d9195a7SDavid du Colombier 	sp = reg.r[1];
687d9195a7SDavid du Colombier 	i = 0;
697d9195a7SDavid du Colombier 	while (findsym(pc, CTEXT, &s)) {
707d9195a7SDavid du Colombier 		if(strcmp(STARTSYM, s.name) == 0) {
71*f19e7b74SDavid du Colombier 			Bprint(bioout, "%s() at #%llux\n", s.name, s.value);
727d9195a7SDavid du Colombier 			break;
737d9195a7SDavid du Colombier 		}
747d9195a7SDavid du Colombier 		if (pc == s.value)	/* at first instruction */
757d9195a7SDavid du Colombier 			f.value = 0;
767d9195a7SDavid du Colombier 		else if (findlocal(&s, FRAMENAME, &f) == 0)
777d9195a7SDavid du Colombier 			break;
787d9195a7SDavid du Colombier 		if (s.type == 'L' || s.type == 'l' || pc <= s.value+4)
797d9195a7SDavid du Colombier 			pc = reg.lr;
807d9195a7SDavid du Colombier 		else pc = getmem_4(sp);
817d9195a7SDavid du Colombier 		sp += f.value;
827d9195a7SDavid du Colombier 		Bprint(bioout, "%s(", s.name);
837d9195a7SDavid du Colombier 		printparams(&s, sp);
847d9195a7SDavid du Colombier 		printsource(s.value);
857d9195a7SDavid du Colombier 		Bprint(bioout, " called from ");
867d9195a7SDavid du Colombier 		symoff(buf, sizeof(buf), pc-4, CTEXT);
877d9195a7SDavid du Colombier 		Bprint(bioout, buf);
887d9195a7SDavid du Colombier 		printsource(pc-8);
897d9195a7SDavid du Colombier 		Bprint(bioout, "\n");
907d9195a7SDavid du Colombier 		if(modif == 'C')
917d9195a7SDavid du Colombier 			printlocals(&s, sp);
927d9195a7SDavid du Colombier 		if(++i > 40){
937d9195a7SDavid du Colombier 			Bprint(bioout, "(trace truncated)\n");
947d9195a7SDavid du Colombier 			break;
957d9195a7SDavid du Colombier 		}
967d9195a7SDavid du Colombier 	}
977d9195a7SDavid du Colombier }
98