plan9port

fork of plan9port with libvec, libstr and libsdb
Log | Files | Refs | README | LICENSE

format.c (6970B)


      1 /*
      2  *
      3  *	debugger
      4  *
      5  */
      6 
      7 #include "defs.h"
      8 #include "fns.h"
      9 
     10 void
     11 scanform(long icount, int prt, char *ifp, Map *map, int literal)
     12 {
     13 	char	*fp;
     14 	char	c;
     15 	int	fcount;
     16 	ADDR	savdot;
     17 	int firstpass;
     18 
     19 	firstpass = 1;
     20 	while (icount) {
     21 		fp=ifp;
     22 		savdot=dot;
     23 		/*now loop over format*/
     24 		while (*fp) {
     25 			if (!isdigit((uchar)*fp))
     26 				fcount = 1;
     27 			else {
     28 				fcount = 0;
     29 				while (isdigit((uchar)(c = *fp++))) {
     30 					fcount *= 10;
     31 					fcount += c-'0';
     32 				}
     33 				fp--;
     34 			}
     35 			if (*fp==0)
     36 				break;
     37 			fp=exform(fcount,prt,fp,map,literal,firstpass);
     38 			firstpass = 0;
     39 		}
     40 		dotinc=dot-savdot;
     41 		dot=savdot;
     42 		if (--icount)
     43 			dot=inkdot(dotinc);
     44 	}
     45 }
     46 
     47 char *
     48 exform(int fcount, int prt, char *ifp, Map *map, int literal, int firstpass)
     49 {
     50 	/* execute single format item `fcount' times
     51 	 * sets `dotinc' and moves `dot'
     52 	 * returns address of next format item
     53 	 */
     54 	vlong	v;
     55 	WORD	w;
     56 	ulong	savdot;
     57 	u16int	u2;
     58 	u32int	u4;
     59 	u64int	u8;
     60 	char	*fp;
     61 	char	c, modifier;
     62 	int	i;
     63 	ushort sh;
     64 	uchar ch, *cp;
     65 	Symbol s;
     66 	char buf[512];
     67 	extern int printcol;
     68 
     69 	fp = 0;
     70 	while (fcount > 0) {
     71 		fp = ifp;
     72 		c = *fp;
     73 		modifier = *fp++;
     74 		if (firstpass) {
     75 			firstpass = 0;
     76 			if (!literal  && (c == 'i' || c == 'I' || c == 'M')
     77 					&& (dot & (mach->pcquant-1))) {
     78 				dprint("warning: instruction not aligned");
     79 				printc('\n');
     80 			}
     81 			if (prt && modifier != 'a' && modifier != 'A') {
     82 				symoff(buf, 512, dot, CANY);
     83 				dprint("%s%c%16t", buf, map==symmap? '?':'/');
     84 			}
     85 		}
     86 		if (printcol==0 && modifier != 'a' && modifier != 'A')
     87 			dprint("\t\t");
     88 		switch(modifier) {
     89 
     90 		case SPC:
     91 		case TB:
     92 			dotinc = 0;
     93 			break;
     94 
     95 		case 't':
     96 		case 'T':
     97 			dprint("%*t", fcount);
     98 			dotinc = 0;
     99 			return(fp);
    100 
    101 		case 'a':
    102 			symoff(buf, sizeof(buf), dot, CANY);
    103 			dprint("%s%c%16t", buf, map==symmap? '?':'/');
    104 			dotinc = 0;
    105 			break;
    106 
    107 		case 'A':
    108 			dprint("%#lux%10t", dot);
    109 			dotinc = 0;
    110 			break;
    111 
    112 		case 'p':
    113 			if (get4(map, dot, &u4) < 0)
    114 				error("%r");
    115 			w = u4;
    116 			symoff(buf, sizeof(buf), w, CANY);
    117 			dprint("%s%16t", buf);
    118 			dotinc = mach->szaddr;
    119 			break;
    120 
    121 		case 'u':
    122 		case 'd':
    123 		case 'x':
    124 		case 'o':
    125 		case 'q':
    126 			if (literal)
    127 				u2 = (ushort) dot;
    128 			else if (get2(map, dot, &u2) < 0)
    129 				error("%r");
    130 			w = u2;
    131 			dotinc = 2;
    132 			if (c == 'u')
    133 				dprint("%-8lud", w);
    134 			else if (c == 'x')
    135 				dprint("%-8#lux", w);
    136 			else if (c == 'd')
    137 				dprint("%-8ld", w);
    138 			else if (c == 'o')
    139 				dprint("%-8#luo", w);
    140 			else if (c == 'q')
    141 				dprint("%-8#lo", w);
    142 			break;
    143 
    144 		case 'U':
    145 		case 'D':
    146 		case 'X':
    147 		case 'O':
    148 		case 'Q':
    149 			if (literal)
    150 				u4 = (long) dot;
    151 			else if (get4(map, dot, &u4) < 0)
    152 				error("%r");
    153 			dotinc = 4;
    154 			if (c == 'U')
    155 				dprint("%-16lud", u4);
    156 			else if (c == 'X')
    157 				dprint("%-16#lux", u4);
    158 			else if (c == 'D')
    159 				dprint("%-16ld", u4);
    160 			else if (c == 'O')
    161 				dprint("%-#16luo", u4);
    162 			else if (c == 'Q')
    163 				dprint("%-#16lo", u4);
    164 			break;
    165 		case 'Z':
    166 		case 'V':
    167 		case 'Y':
    168 			if (literal)
    169 				v = dot;
    170 			else if (get8(map, dot, &u8) < 0)
    171 				error("%r");
    172 			dotinc = 8;
    173 			if (c == 'Y')
    174 				dprint("%-20#llux", u8);
    175 			else if (c == 'V')
    176 				dprint("%-20lld", u8);
    177 			else if (c == 'Z')
    178 				dprint("%-20llud", u8);
    179 			break;
    180 		case 'B':
    181 		case 'b':
    182 		case 'c':
    183 		case 'C':
    184 			if (literal)
    185 				ch = (uchar) dot;
    186 			else if (get1(map, dot, &ch, 1)  < 0)
    187 				error("%r");
    188 			if (modifier == 'C')
    189 				printesc(ch);
    190 			else if (modifier == 'B' || modifier == 'b')
    191 				dprint("%-8#lux", (long) ch);
    192 			else
    193 				printc(ch);
    194 			dotinc = 1;
    195 			break;
    196 
    197 		case 'r':
    198 			if (literal)
    199 				sh = (ushort) dot;
    200 			else if (get2(map, dot, &sh) < 0)
    201 				error("%r");
    202 			dprint("%C", sh);
    203 			dotinc = 2;
    204 			break;
    205 
    206 		case 'R':
    207 			if (literal) {
    208 				u16int sp[2];
    209 				memmove(&sp, &dot, 4);
    210 				dprint("%C%C", sp[0], sp[1]);
    211 				endline();
    212 				dotinc = 4;
    213 				break;
    214 			}
    215 			savdot=dot;
    216 			while ((i = get2(map, dot, &u2) > 0) && u2) {
    217 				dot=inkdot(2);
    218 				dprint("%C", u2);
    219 				endline();
    220 			}
    221 			if (i < 0)
    222 				error("%r");
    223 			dotinc = dot-savdot+2;
    224 			dot=savdot;
    225 			break;
    226 
    227 		case 's':
    228 			if (literal) {
    229 				cp = (uchar*)(void*)&dot;
    230 				for (i = 0; i < 4; i++)
    231 					buf[i] = cp[i];
    232 				buf[i] = 0;
    233 				dprint("%s", buf);
    234 				endline();
    235 				dotinc = 4;
    236 				break;
    237 			}
    238 			savdot = dot;
    239 			for(;;){
    240 				i = 0;
    241 				do{
    242 					if (get1(map, dot, (uchar*)(void*)&buf[i], 1) < 0)
    243 						error("%r");
    244 					dot = inkdot(1);
    245 					i++;
    246 				}while(!fullrune(buf, i));
    247 				if(buf[0] == 0)
    248 					break;
    249 				buf[i] = 0;
    250 				dprint("%s", buf);
    251 				endline();
    252 			}
    253 			dotinc = dot-savdot+1;
    254 			dot = savdot;
    255 			break;
    256 
    257 		case 'S':
    258 			if (literal) {
    259 				cp = (uchar*) &dot;
    260 				for (i = 0; i < 4; i++)
    261 					printesc(cp[i]);
    262 				endline();
    263 				dotinc = 4;
    264 				break;
    265 			}
    266 			savdot=dot;
    267 			while ((i = get1(map, dot, &ch, 1) > 0) && ch) {
    268 				dot=inkdot(1);
    269 				printesc(ch);
    270 				endline();
    271 			}
    272 			if (i < 0)
    273 				error("%r");
    274 			dotinc = dot-savdot+1;
    275 			dot=savdot;
    276 			break;
    277 
    278 
    279 		case 'I':
    280 		case 'i':
    281 			dotinc = mach->das(map, dot, modifier, buf, sizeof(buf));
    282 			if (dotinc < 0)
    283 				error("%r");
    284 			dprint("%s\n", buf);
    285 			break;
    286 
    287 		case 'M':
    288 			dotinc = mach->hexinst(map, dot, buf, sizeof(buf));
    289 			if (dotinc < 0)
    290 				error("%r");
    291 			dprint("%s", buf);
    292 			if (*fp) {
    293 				dotinc = 0;
    294 				dprint("%48t");
    295 			} else
    296 				dprint("\n");
    297 			break;
    298 
    299 		case 'f':
    300 			/* BUG: 'f' and 'F' assume szdouble is sizeof(vlong) in the literal case */
    301 			if (literal) {
    302 				v = mach->swap8((ulong)dot);
    303 				memmove(buf, &v, mach->szfloat);
    304 			}else if (get1(map, dot, (uchar*)buf, mach->szfloat) < 0)
    305 				error("%r");
    306 			mach->ftoa32(buf, sizeof(buf), (void*) buf);
    307 			dprint("%s\n", buf);
    308 			dotinc = mach->szfloat;
    309 			break;
    310 
    311 		case 'F':
    312 			/* BUG: 'f' and 'F' assume szdouble is sizeof(vlong) in the literal case */
    313 			if (literal) {
    314 				v = mach->swap8(dot);
    315 				memmove(buf, &v, mach->szdouble);
    316 			}else if (get1(map, dot, (uchar*)buf, mach->szdouble) < 0)
    317 				error("%r");
    318 			mach->ftoa64(buf, sizeof(buf), (void*) buf);
    319 			dprint("%s\n", buf);
    320 			dotinc = mach->szdouble;
    321 			break;
    322 
    323 		case 'n':
    324 		case 'N':
    325 			printc('\n');
    326 			dotinc=0;
    327 			break;
    328 
    329 		case '"':
    330 			dotinc=0;
    331 			while (*fp != '"' && *fp)
    332 				printc(*fp++);
    333 			if (*fp)
    334 				fp++;
    335 			break;
    336 
    337 		case '^':
    338 			dot=inkdot(-dotinc*fcount);
    339 			return(fp);
    340 
    341 		case '+':
    342 			dot=inkdot((WORD)fcount);
    343 			return(fp);
    344 
    345 		case '-':
    346 			dot=inkdot(-(WORD)fcount);
    347 			return(fp);
    348 
    349 		case 'z':
    350 			if (findsym(locaddr(dot), CTEXT, &s) >= 0)
    351 				dprint("%s() ", s.name);
    352 			printsource(dot);
    353 			printc(EOR);
    354 			return fp;
    355 
    356 		default:
    357 			error("bad modifier");
    358 		}
    359 		if (map->seg[0].fd >= 0)
    360 			dot=inkdot(dotinc);
    361 		fcount--;
    362 		endline();
    363 	}
    364 
    365 	return(fp);
    366 }
    367 
    368 void
    369 printesc(int c)
    370 {
    371 	static char hex[] = "0123456789abcdef";
    372 
    373 	if (c < SPC || c >= 0177)
    374 		dprint("\\x%c%c", hex[(c&0xF0)>>4], hex[c&0xF]);
    375 	else
    376 		printc(c);
    377 }
    378 
    379 ADDR
    380 inkdot(WORD incr)
    381 {
    382 	ADDR	newdot;
    383 
    384 	newdot=dot+incr;
    385 	if ((incr >= 0 && newdot < dot)
    386 	||  (incr < 0 && newdot > dot))
    387 		error("address wraparound");
    388 	return(newdot);
    389 }