13e12c5d1SDavid du Colombier #include <u.h> 23e12c5d1SDavid du Colombier #include <libc.h> 3bd389b36SDavid du Colombier #include <bio.h> 43e12c5d1SDavid du Colombier #include <mach.h> 53e12c5d1SDavid du Colombier #include <ctype.h> 63e12c5d1SDavid du Colombier #define Extern extern 73e12c5d1SDavid du Colombier #include "mips.h" 83e12c5d1SDavid du Colombier 93e12c5d1SDavid du Colombier char buf[128], lastcmd[128]; 103e12c5d1SDavid du Colombier char fmt = 'X'; 113e12c5d1SDavid du Colombier int width = 60; 123e12c5d1SDavid du Colombier int inc; 133e12c5d1SDavid du Colombier 143e12c5d1SDavid du Colombier ulong expr(char*); 153e12c5d1SDavid du Colombier ulong expr1(char*); 163e12c5d1SDavid du Colombier char* term(char*, ulong*); 173e12c5d1SDavid du Colombier 183e12c5d1SDavid du Colombier char * 193e12c5d1SDavid du Colombier nextc(char *p) 203e12c5d1SDavid du Colombier { 213e12c5d1SDavid du Colombier while(*p && (*p == ' ' || *p == '\t') && *p != '\n') 223e12c5d1SDavid du Colombier p++; 233e12c5d1SDavid du Colombier 243e12c5d1SDavid du Colombier if(*p == '\n') 253e12c5d1SDavid du Colombier *p = '\0'; 263e12c5d1SDavid du Colombier 273e12c5d1SDavid du Colombier return p; 283e12c5d1SDavid du Colombier } 293e12c5d1SDavid du Colombier 303e12c5d1SDavid du Colombier char * 313e12c5d1SDavid du Colombier numsym(char *addr, ulong *val) 323e12c5d1SDavid du Colombier { 333e12c5d1SDavid du Colombier char tsym[128], *t; 343e12c5d1SDavid du Colombier static char *delim = "`'<>/\\@*|-~+-/=?\n"; 353e12c5d1SDavid du Colombier Symbol s; 363e12c5d1SDavid du Colombier char c; 373e12c5d1SDavid du Colombier 383e12c5d1SDavid du Colombier t = tsym; 393e12c5d1SDavid du Colombier while(c = *addr) { 403e12c5d1SDavid du Colombier if(strchr(delim, c)) 413e12c5d1SDavid du Colombier break; 423e12c5d1SDavid du Colombier *t++ = c; 433e12c5d1SDavid du Colombier addr++; 443e12c5d1SDavid du Colombier } 453e12c5d1SDavid du Colombier t[0] = '\0'; 463e12c5d1SDavid du Colombier 473e12c5d1SDavid du Colombier if(strcmp(tsym, ".") == 0) { 483e12c5d1SDavid du Colombier *val = dot; 493e12c5d1SDavid du Colombier return addr; 503e12c5d1SDavid du Colombier } 513e12c5d1SDavid du Colombier 523e12c5d1SDavid du Colombier if(lookup(0, tsym, &s)) 533e12c5d1SDavid du Colombier *val = s.value; 543e12c5d1SDavid du Colombier else { 553e12c5d1SDavid du Colombier if(tsym[0] == '#') 563e12c5d1SDavid du Colombier *val = strtoul(tsym+1, 0, 16); 573e12c5d1SDavid du Colombier else 583e12c5d1SDavid du Colombier *val = strtoul(tsym, 0, 0); 593e12c5d1SDavid du Colombier } 603e12c5d1SDavid du Colombier return addr; 613e12c5d1SDavid du Colombier } 623e12c5d1SDavid du Colombier 633e12c5d1SDavid du Colombier ulong 643e12c5d1SDavid du Colombier expr(char *addr) 653e12c5d1SDavid du Colombier { 663e12c5d1SDavid du Colombier ulong t, t2; 673e12c5d1SDavid du Colombier char op; 683e12c5d1SDavid du Colombier 693e12c5d1SDavid du Colombier if(*addr == '\0') 703e12c5d1SDavid du Colombier return dot; 713e12c5d1SDavid du Colombier 723e12c5d1SDavid du Colombier addr = numsym(addr, &t); 733e12c5d1SDavid du Colombier 743e12c5d1SDavid du Colombier if(*addr == '\0') 753e12c5d1SDavid du Colombier return t; 763e12c5d1SDavid du Colombier 773e12c5d1SDavid du Colombier addr = nextc(addr); 783e12c5d1SDavid du Colombier op = *addr++; 793e12c5d1SDavid du Colombier numsym(addr, &t2); 803e12c5d1SDavid du Colombier switch(op) { 813e12c5d1SDavid du Colombier default: 823e12c5d1SDavid du Colombier Bprint(bioout, "expr syntax\n"); 833e12c5d1SDavid du Colombier return 0; 843e12c5d1SDavid du Colombier case '+': 853e12c5d1SDavid du Colombier t += t2; 863e12c5d1SDavid du Colombier break; 873e12c5d1SDavid du Colombier case '-': 883e12c5d1SDavid du Colombier t -= t2; 893e12c5d1SDavid du Colombier break; 903e12c5d1SDavid du Colombier case '%': 913e12c5d1SDavid du Colombier t /= t2; 923e12c5d1SDavid du Colombier break; 933e12c5d1SDavid du Colombier case '&': 943e12c5d1SDavid du Colombier t &= t2; 953e12c5d1SDavid du Colombier break; 963e12c5d1SDavid du Colombier case '|': 973e12c5d1SDavid du Colombier t |= t2; 983e12c5d1SDavid du Colombier break; 993e12c5d1SDavid du Colombier } 1003e12c5d1SDavid du Colombier 1013e12c5d1SDavid du Colombier return t; 1023e12c5d1SDavid du Colombier } 1033e12c5d1SDavid du Colombier 1043e12c5d1SDavid du Colombier int 1053e12c5d1SDavid du Colombier buildargv(char *str, char **args, int max) 1063e12c5d1SDavid du Colombier { 1073e12c5d1SDavid du Colombier int na = 0; 1083e12c5d1SDavid du Colombier 1093e12c5d1SDavid du Colombier while (na < max) { 1103e12c5d1SDavid du Colombier while((*str == ' ' || *str == '\t' || *str == '\n') && *str != '\0') 1113e12c5d1SDavid du Colombier str++; 1123e12c5d1SDavid du Colombier 1133e12c5d1SDavid du Colombier if(*str == '\0') 1143e12c5d1SDavid du Colombier return na; 1153e12c5d1SDavid du Colombier 1163e12c5d1SDavid du Colombier args[na++] = str; 1173e12c5d1SDavid du Colombier while(!(*str == ' ' || *str == '\t'|| *str == '\n') && *str != '\0') 1183e12c5d1SDavid du Colombier str++; 1193e12c5d1SDavid du Colombier 1203e12c5d1SDavid du Colombier if(*str == '\n') 1213e12c5d1SDavid du Colombier *str = '\0'; 1223e12c5d1SDavid du Colombier 1233e12c5d1SDavid du Colombier if(*str == '\0') 1243e12c5d1SDavid du Colombier break; 1253e12c5d1SDavid du Colombier 1263e12c5d1SDavid du Colombier *str++ = '\0'; 1273e12c5d1SDavid du Colombier } 1283e12c5d1SDavid du Colombier return na; 1293e12c5d1SDavid du Colombier } 1303e12c5d1SDavid du Colombier 1313e12c5d1SDavid du Colombier void 1323e12c5d1SDavid du Colombier colon(char *addr, char *cp) 1333e12c5d1SDavid du Colombier { 1343e12c5d1SDavid du Colombier int argc; 1353e12c5d1SDavid du Colombier char *argv[100]; 136*219b2ee8SDavid du Colombier char tbuf[512]; 1373e12c5d1SDavid du Colombier 1383e12c5d1SDavid du Colombier cp = nextc(cp); 1393e12c5d1SDavid du Colombier switch(*cp) { 1403e12c5d1SDavid du Colombier default: 1413e12c5d1SDavid du Colombier Bprint(bioout, "?\n"); 1423e12c5d1SDavid du Colombier return; 1433e12c5d1SDavid du Colombier case 'b': 1443e12c5d1SDavid du Colombier breakpoint(addr, cp+1); 1453e12c5d1SDavid du Colombier return; 1463e12c5d1SDavid du Colombier 1473e12c5d1SDavid du Colombier case 'd': 1483e12c5d1SDavid du Colombier delbpt(addr); 1493e12c5d1SDavid du Colombier return; 1503e12c5d1SDavid du Colombier 1513e12c5d1SDavid du Colombier /* These fall through to print the stopped address */ 1523e12c5d1SDavid du Colombier case 'r': 1533e12c5d1SDavid du Colombier reset(); 1543e12c5d1SDavid du Colombier argc = buildargv(cp+1, argv, 100); 155*219b2ee8SDavid du Colombier initstk(argc, argv); 1563e12c5d1SDavid du Colombier count = 0; 1573e12c5d1SDavid du Colombier atbpt = 0; 1583e12c5d1SDavid du Colombier run(); 1593e12c5d1SDavid du Colombier break; 1603e12c5d1SDavid du Colombier case 'c': 1613e12c5d1SDavid du Colombier count = 0; 1623e12c5d1SDavid du Colombier atbpt = 0; 1633e12c5d1SDavid du Colombier run(); 1643e12c5d1SDavid du Colombier break; 1653e12c5d1SDavid du Colombier case 's': 1663e12c5d1SDavid du Colombier cp = nextc(cp+1); 1673e12c5d1SDavid du Colombier count = 0; 1683e12c5d1SDavid du Colombier if(*cp) 1693e12c5d1SDavid du Colombier count = strtoul(cp, 0, 0); 1703e12c5d1SDavid du Colombier if(count == 0) 1713e12c5d1SDavid du Colombier count = 1; 1723e12c5d1SDavid du Colombier atbpt = 0; 1733e12c5d1SDavid du Colombier run(); 1743e12c5d1SDavid du Colombier break; 1753e12c5d1SDavid du Colombier } 1763e12c5d1SDavid du Colombier 1773e12c5d1SDavid du Colombier dot = reg.pc; 1783e12c5d1SDavid du Colombier Bprint(bioout, "%s at #%lux ", atbpt ? "breakpoint" : "stopped", dot); 179*219b2ee8SDavid du Colombier symoff(tbuf, sizeof(tbuf), dot, CTEXT); 180*219b2ee8SDavid du Colombier Bprint(bioout, tbuf); 1813e12c5d1SDavid du Colombier if(fmt == 'z') 1823e12c5d1SDavid du Colombier printsource(dot); 1833e12c5d1SDavid du Colombier 1843e12c5d1SDavid du Colombier Bprint(bioout, "\n"); 1853e12c5d1SDavid du Colombier } 1863e12c5d1SDavid du Colombier 1873e12c5d1SDavid du Colombier 1883e12c5d1SDavid du Colombier void 1893e12c5d1SDavid du Colombier dollar(char *cp) 1903e12c5d1SDavid du Colombier { 1913e12c5d1SDavid du Colombier cp = nextc(cp); 1923e12c5d1SDavid du Colombier switch(*cp) { 1933e12c5d1SDavid du Colombier default: 1943e12c5d1SDavid du Colombier Bprint(bioout, "?\n"); 1953e12c5d1SDavid du Colombier break; 1963e12c5d1SDavid du Colombier 1973e12c5d1SDavid du Colombier case 'c': 1983e12c5d1SDavid du Colombier stktrace(*cp); 1993e12c5d1SDavid du Colombier break; 2003e12c5d1SDavid du Colombier 2013e12c5d1SDavid du Colombier case 'C': 2023e12c5d1SDavid du Colombier stktrace(*cp); 2033e12c5d1SDavid du Colombier break; 2043e12c5d1SDavid du Colombier 2053e12c5d1SDavid du Colombier case 'b': 2063e12c5d1SDavid du Colombier dobplist(); 2073e12c5d1SDavid du Colombier break; 2083e12c5d1SDavid du Colombier 2093e12c5d1SDavid du Colombier case 'r': 2103e12c5d1SDavid du Colombier dumpreg(); 2113e12c5d1SDavid du Colombier break; 2123e12c5d1SDavid du Colombier 2133e12c5d1SDavid du Colombier case 'R': 2143e12c5d1SDavid du Colombier dumpreg(); 2153e12c5d1SDavid du Colombier 2163e12c5d1SDavid du Colombier case 'f': 2173e12c5d1SDavid du Colombier dumpfreg(); 2183e12c5d1SDavid du Colombier break; 2193e12c5d1SDavid du Colombier 2203e12c5d1SDavid du Colombier case 'F': 2213e12c5d1SDavid du Colombier dumpdreg(); 2223e12c5d1SDavid du Colombier break; 2233e12c5d1SDavid du Colombier 2243e12c5d1SDavid du Colombier case 'q': 2253e12c5d1SDavid du Colombier exits(0); 2263e12c5d1SDavid du Colombier break; 2273e12c5d1SDavid du Colombier 2283e12c5d1SDavid du Colombier case 'Q': 2293e12c5d1SDavid du Colombier isum(); 2303e12c5d1SDavid du Colombier tlbsum(); 2313e12c5d1SDavid du Colombier segsum(); 2323e12c5d1SDavid du Colombier break; 2333e12c5d1SDavid du Colombier 2343e12c5d1SDavid du Colombier case 't': 2353e12c5d1SDavid du Colombier cp++; 2363e12c5d1SDavid du Colombier switch(*cp) { 2373e12c5d1SDavid du Colombier default: 2383e12c5d1SDavid du Colombier Bprint(bioout, ":t[0sic]\n"); 2393e12c5d1SDavid du Colombier break; 2403e12c5d1SDavid du Colombier case '\0': 2413e12c5d1SDavid du Colombier trace = 1; 2423e12c5d1SDavid du Colombier break; 2433e12c5d1SDavid du Colombier case '0': 2443e12c5d1SDavid du Colombier trace = 0; 2453e12c5d1SDavid du Colombier sysdbg = 0; 2463e12c5d1SDavid du Colombier calltree = 0; 2473e12c5d1SDavid du Colombier break; 2483e12c5d1SDavid du Colombier case 's': 2493e12c5d1SDavid du Colombier sysdbg = 1; 2503e12c5d1SDavid du Colombier break; 2513e12c5d1SDavid du Colombier case 'i': 2523e12c5d1SDavid du Colombier trace = 1; 2533e12c5d1SDavid du Colombier break; 2543e12c5d1SDavid du Colombier case 'c': 2553e12c5d1SDavid du Colombier calltree = 1; 2563e12c5d1SDavid du Colombier break; 2573e12c5d1SDavid du Colombier } 2583e12c5d1SDavid du Colombier break; 2593e12c5d1SDavid du Colombier 2603e12c5d1SDavid du Colombier case 'i': 2613e12c5d1SDavid du Colombier cp++; 2623e12c5d1SDavid du Colombier switch(*cp) { 2633e12c5d1SDavid du Colombier default: 2643e12c5d1SDavid du Colombier Bprint(bioout, "$i[itsa]\n"); 2653e12c5d1SDavid du Colombier break; 2663e12c5d1SDavid du Colombier case 'i': 2673e12c5d1SDavid du Colombier isum(); 2683e12c5d1SDavid du Colombier break; 2693e12c5d1SDavid du Colombier case 't': 2703e12c5d1SDavid du Colombier tlbsum(); 2713e12c5d1SDavid du Colombier break; 2723e12c5d1SDavid du Colombier case 's': 2733e12c5d1SDavid du Colombier segsum(); 2743e12c5d1SDavid du Colombier break; 2753e12c5d1SDavid du Colombier case 'a': 2763e12c5d1SDavid du Colombier isum(); 2773e12c5d1SDavid du Colombier tlbsum(); 2783e12c5d1SDavid du Colombier segsum(); 2793e12c5d1SDavid du Colombier iprofile(); 2803e12c5d1SDavid du Colombier break; 2813e12c5d1SDavid du Colombier case 'p': 2823e12c5d1SDavid du Colombier iprofile(); 2833e12c5d1SDavid du Colombier break; 2843e12c5d1SDavid du Colombier } 2853e12c5d1SDavid du Colombier } 2863e12c5d1SDavid du Colombier } 2873e12c5d1SDavid du Colombier 2883e12c5d1SDavid du Colombier int 2893e12c5d1SDavid du Colombier pfmt(char fmt, int mem, ulong val) 2903e12c5d1SDavid du Colombier { 2913e12c5d1SDavid du Colombier int c, i; 2923e12c5d1SDavid du Colombier Symbol s; 2933e12c5d1SDavid du Colombier char *p, ch, str[1024]; 2943e12c5d1SDavid du Colombier 2953e12c5d1SDavid du Colombier c = 0; 2963e12c5d1SDavid du Colombier switch(fmt) { 2973e12c5d1SDavid du Colombier default: 2983e12c5d1SDavid du Colombier Bprint(bioout, "bad modifier\n"); 2993e12c5d1SDavid du Colombier return 0; 3003e12c5d1SDavid du Colombier case 'o': 3013e12c5d1SDavid du Colombier c = Bprint(bioout, "%-4o ", mem ? (ushort)getmem_2(dot) : val); 3023e12c5d1SDavid du Colombier inc = 2; 3033e12c5d1SDavid du Colombier break; 3043e12c5d1SDavid du Colombier 3053e12c5d1SDavid du Colombier case 'O': 3063e12c5d1SDavid du Colombier c = Bprint(bioout, "%-8o ", mem ? getmem_4(dot) : val); 3073e12c5d1SDavid du Colombier inc = 4; 3083e12c5d1SDavid du Colombier break; 3093e12c5d1SDavid du Colombier 3103e12c5d1SDavid du Colombier case 'q': 3113e12c5d1SDavid du Colombier c = Bprint(bioout, "%-4o ", mem ? (short)getmem_2(dot) : val); 3123e12c5d1SDavid du Colombier inc = 2; 3133e12c5d1SDavid du Colombier break; 3143e12c5d1SDavid du Colombier 3153e12c5d1SDavid du Colombier case 'Q': 3163e12c5d1SDavid du Colombier c = Bprint(bioout, "%-8o ", mem ? (long)getmem_4(dot) : val); 3173e12c5d1SDavid du Colombier inc = 4; 3183e12c5d1SDavid du Colombier break; 3193e12c5d1SDavid du Colombier 3203e12c5d1SDavid du Colombier case 'd': 3213e12c5d1SDavid du Colombier c = Bprint(bioout, "%-5ld ", mem ? (short)getmem_2(dot) : val); 3223e12c5d1SDavid du Colombier inc = 2; 3233e12c5d1SDavid du Colombier break; 3243e12c5d1SDavid du Colombier 3253e12c5d1SDavid du Colombier 3263e12c5d1SDavid du Colombier case 'D': 3273e12c5d1SDavid du Colombier c = Bprint(bioout, "%-8ld ", mem ? (long)getmem_4(dot) : val); 3283e12c5d1SDavid du Colombier inc = 4; 3293e12c5d1SDavid du Colombier break; 3303e12c5d1SDavid du Colombier 3313e12c5d1SDavid du Colombier case 'x': 3323e12c5d1SDavid du Colombier c = Bprint(bioout, "#%-4lux ", mem ? (long)getmem_2(dot) : val); 3333e12c5d1SDavid du Colombier inc = 2; 3343e12c5d1SDavid du Colombier break; 3353e12c5d1SDavid du Colombier 3363e12c5d1SDavid du Colombier case 'X': 3373e12c5d1SDavid du Colombier c = Bprint(bioout, "#%-8lux ", mem ? (long)getmem_4(dot) : val); 3383e12c5d1SDavid du Colombier inc = 4; 3393e12c5d1SDavid du Colombier break; 3403e12c5d1SDavid du Colombier 3413e12c5d1SDavid du Colombier case 'u': 3423e12c5d1SDavid du Colombier c = Bprint(bioout, "%-5ld ", mem ? (ushort)getmem_2(dot) : val); 3433e12c5d1SDavid du Colombier inc = 2; 3443e12c5d1SDavid du Colombier break; 3453e12c5d1SDavid du Colombier 3463e12c5d1SDavid du Colombier case 'U': 3473e12c5d1SDavid du Colombier c = Bprint(bioout, "%-8ld ", mem ? (ulong)getmem_4(dot) : val); 3483e12c5d1SDavid du Colombier inc = 4; 3493e12c5d1SDavid du Colombier break; 3503e12c5d1SDavid du Colombier 3513e12c5d1SDavid du Colombier case 'b': 3523e12c5d1SDavid du Colombier c = Bprint(bioout, "%-3d ", mem ? getmem_b(dot) : val); 3533e12c5d1SDavid du Colombier inc = 1; 3543e12c5d1SDavid du Colombier break; 3553e12c5d1SDavid du Colombier 3563e12c5d1SDavid du Colombier case 'c': 3573e12c5d1SDavid du Colombier c = Bprint(bioout, "%c ", mem ? getmem_b(dot) : val); 3583e12c5d1SDavid du Colombier inc = 1; 3593e12c5d1SDavid du Colombier break; 3603e12c5d1SDavid du Colombier 3613e12c5d1SDavid du Colombier case 'C': 3623e12c5d1SDavid du Colombier ch = mem ? getmem_b(dot) : val; 3633e12c5d1SDavid du Colombier if(isprint(ch)) 3643e12c5d1SDavid du Colombier c = Bprint(bioout, "%c ", ch); 3653e12c5d1SDavid du Colombier else 3663e12c5d1SDavid du Colombier c = Bprint(bioout, "\\x%.2x ", ch); 3673e12c5d1SDavid du Colombier inc = 1; 3683e12c5d1SDavid du Colombier break; 3693e12c5d1SDavid du Colombier 3703e12c5d1SDavid du Colombier case 's': 3713e12c5d1SDavid du Colombier i = 0; 3723e12c5d1SDavid du Colombier while(ch = getmem_b(dot+i)) 3733e12c5d1SDavid du Colombier str[i++] = ch; 3743e12c5d1SDavid du Colombier str[i] = '\0'; 3753e12c5d1SDavid du Colombier dot += i; 3763e12c5d1SDavid du Colombier c = Bprint(bioout, "%s", str); 3773e12c5d1SDavid du Colombier inc = 0; 3783e12c5d1SDavid du Colombier break; 3793e12c5d1SDavid du Colombier 3803e12c5d1SDavid du Colombier case 'S': 3813e12c5d1SDavid du Colombier i = 0; 3823e12c5d1SDavid du Colombier while(ch = getmem_b(dot+i)) 3833e12c5d1SDavid du Colombier str[i++] = ch; 3843e12c5d1SDavid du Colombier str[i] = '\0'; 3853e12c5d1SDavid du Colombier dot += i; 3863e12c5d1SDavid du Colombier for(p = str; *p; p++) 3873e12c5d1SDavid du Colombier if(isprint(*p)) 3883e12c5d1SDavid du Colombier c += Bprint(bioout, "%c", *p); 3893e12c5d1SDavid du Colombier else 3903e12c5d1SDavid du Colombier c += Bprint(bioout, "\\x%.2lux", *p); 3913e12c5d1SDavid du Colombier inc = 0; 3923e12c5d1SDavid du Colombier break; 3933e12c5d1SDavid du Colombier 3943e12c5d1SDavid du Colombier case 'Y': 3953e12c5d1SDavid du Colombier p = ctime(mem ? getmem_b(dot) : val); 3963e12c5d1SDavid du Colombier p[30] = '\0'; 3973e12c5d1SDavid du Colombier c = Bprint(bioout, "%s", p); 3983e12c5d1SDavid du Colombier inc = 4; 3993e12c5d1SDavid du Colombier break; 4003e12c5d1SDavid du Colombier 4013e12c5d1SDavid du Colombier case 'a': 402*219b2ee8SDavid du Colombier symoff(str, sizeof(str), dot, CTEXT); 403*219b2ee8SDavid du Colombier c = Bprint(bioout, str); 4043e12c5d1SDavid du Colombier inc = 0; 4053e12c5d1SDavid du Colombier break; 4063e12c5d1SDavid du Colombier 4073e12c5d1SDavid du Colombier case 'e': 4083e12c5d1SDavid du Colombier for (i = 0; globalsym(&s, i); i++) 4093e12c5d1SDavid du Colombier Bprint(bioout, "%-15s #%lux\n", s.name, getmem_4(s.value)); 4103e12c5d1SDavid du Colombier inc = 0; 4113e12c5d1SDavid du Colombier break; 4123e12c5d1SDavid du Colombier 4133e12c5d1SDavid du Colombier case 'i': 414*219b2ee8SDavid du Colombier inc = _mipscoinst(symmap, dot, str, sizeof(str)); 415*219b2ee8SDavid du Colombier if (inc < 0) { 416*219b2ee8SDavid du Colombier Bprint(bioout, "vi: %r\n"); 417*219b2ee8SDavid du Colombier return 0; 418*219b2ee8SDavid du Colombier } 419*219b2ee8SDavid du Colombier c = Bprint(bioout, str); 4203e12c5d1SDavid du Colombier break; 4213e12c5d1SDavid du Colombier 4223e12c5d1SDavid du Colombier case 'n': 4233e12c5d1SDavid du Colombier c = width+1; 4243e12c5d1SDavid du Colombier inc = 0; 4253e12c5d1SDavid du Colombier break; 4263e12c5d1SDavid du Colombier 4273e12c5d1SDavid du Colombier case '-': 4283e12c5d1SDavid du Colombier c = 0; 4293e12c5d1SDavid du Colombier inc = -1; 4303e12c5d1SDavid du Colombier break; 4313e12c5d1SDavid du Colombier 4323e12c5d1SDavid du Colombier case '+': 4333e12c5d1SDavid du Colombier c = 0; 4343e12c5d1SDavid du Colombier inc = 1; 4353e12c5d1SDavid du Colombier break; 4363e12c5d1SDavid du Colombier 4373e12c5d1SDavid du Colombier case '^': 4383e12c5d1SDavid du Colombier c = 0; 4393e12c5d1SDavid du Colombier if(inc > 0) 4403e12c5d1SDavid du Colombier inc = -inc; 4413e12c5d1SDavid du Colombier break; 4423e12c5d1SDavid du Colombier 4433e12c5d1SDavid du Colombier case 'z': 4443e12c5d1SDavid du Colombier if (findsym(dot, CTEXT, &s)) 4453e12c5d1SDavid du Colombier Bprint(bioout, " %s() ", s.name); 4463e12c5d1SDavid du Colombier printsource(dot); 4473e12c5d1SDavid du Colombier inc = 0; 4483e12c5d1SDavid du Colombier break; 4493e12c5d1SDavid du Colombier } 4503e12c5d1SDavid du Colombier return c; 4513e12c5d1SDavid du Colombier } 4523e12c5d1SDavid du Colombier 4533e12c5d1SDavid du Colombier void 4543e12c5d1SDavid du Colombier eval(char *addr, char *p) 4553e12c5d1SDavid du Colombier { 4563e12c5d1SDavid du Colombier ulong val; 4573e12c5d1SDavid du Colombier 4583e12c5d1SDavid du Colombier val = expr(addr); 4593e12c5d1SDavid du Colombier p = nextc(p); 4603e12c5d1SDavid du Colombier if(*p == '\0') { 4613e12c5d1SDavid du Colombier p[0] = fmt; 4623e12c5d1SDavid du Colombier p[1] = '\0'; 4633e12c5d1SDavid du Colombier } 4643e12c5d1SDavid du Colombier pfmt(*p, 0, val); 4653e12c5d1SDavid du Colombier Bprint(bioout, "\n"); 4663e12c5d1SDavid du Colombier } 4673e12c5d1SDavid du Colombier 4683e12c5d1SDavid du Colombier void 4693e12c5d1SDavid du Colombier quesie(char *p) 4703e12c5d1SDavid du Colombier { 4713e12c5d1SDavid du Colombier int c, count, i; 472*219b2ee8SDavid du Colombier char tbuf[512]; 4733e12c5d1SDavid du Colombier 4743e12c5d1SDavid du Colombier c = 0; 475*219b2ee8SDavid du Colombier symoff(tbuf, sizeof(tbuf), dot, CTEXT); 476*219b2ee8SDavid du Colombier Bprint(bioout, "%s?\t", tbuf); 4773e12c5d1SDavid du Colombier 4783e12c5d1SDavid du Colombier while(*p) { 4793e12c5d1SDavid du Colombier p = nextc(p); 4803e12c5d1SDavid du Colombier if(*p == '"') { 4813e12c5d1SDavid du Colombier for(p++; *p && *p != '"'; p++) { 4823e12c5d1SDavid du Colombier Bputc(bioout, *p); 4833e12c5d1SDavid du Colombier c++; 4843e12c5d1SDavid du Colombier } 4853e12c5d1SDavid du Colombier if(*p) 4863e12c5d1SDavid du Colombier p++; 4873e12c5d1SDavid du Colombier continue; 4883e12c5d1SDavid du Colombier } 4893e12c5d1SDavid du Colombier count = 0; 4903e12c5d1SDavid du Colombier while(*p >= '0' && *p <= '9') 4913e12c5d1SDavid du Colombier count = count*10 + (*p++ - '0'); 4923e12c5d1SDavid du Colombier if(count == 0) 4933e12c5d1SDavid du Colombier count = 1; 4943e12c5d1SDavid du Colombier p = nextc(p); 4953e12c5d1SDavid du Colombier if(*p == '\0') { 4963e12c5d1SDavid du Colombier p[0] = fmt; 4973e12c5d1SDavid du Colombier p[1] = '\0'; 4983e12c5d1SDavid du Colombier } 4993e12c5d1SDavid du Colombier for(i = 0; i < count; i++) { 5003e12c5d1SDavid du Colombier c += pfmt(*p, 1, 0); 5013e12c5d1SDavid du Colombier dot += inc; 5023e12c5d1SDavid du Colombier if(c > width) { 5033e12c5d1SDavid du Colombier Bprint(bioout, "\n"); 504*219b2ee8SDavid du Colombier symoff(tbuf, sizeof(tbuf), dot, CTEXT); 505*219b2ee8SDavid du Colombier Bprint(bioout, "%s?\t", tbuf); 5063e12c5d1SDavid du Colombier c = 0; 5073e12c5d1SDavid du Colombier } 5083e12c5d1SDavid du Colombier } 5093e12c5d1SDavid du Colombier fmt = *p++; 5103e12c5d1SDavid du Colombier p = nextc(p); 5113e12c5d1SDavid du Colombier } 5123e12c5d1SDavid du Colombier Bprint(bioout, "\n"); 5133e12c5d1SDavid du Colombier } 5143e12c5d1SDavid du Colombier 5153e12c5d1SDavid du Colombier void 5163e12c5d1SDavid du Colombier catcher(void *a, char *msg) 5173e12c5d1SDavid du Colombier { 5183e12c5d1SDavid du Colombier USED(a); 5193e12c5d1SDavid du Colombier if(strcmp(msg, "interrupt") != 0) 5203e12c5d1SDavid du Colombier noted(NDFLT); 5213e12c5d1SDavid du Colombier 5223e12c5d1SDavid du Colombier count = 1; 5233e12c5d1SDavid du Colombier print("vi\n"); 5243e12c5d1SDavid du Colombier noted(NCONT); 5253e12c5d1SDavid du Colombier } 5263e12c5d1SDavid du Colombier 5273e12c5d1SDavid du Colombier void 5283e12c5d1SDavid du Colombier setreg(char *addr, char *cp) 5293e12c5d1SDavid du Colombier { 5303e12c5d1SDavid du Colombier int rn; 5313e12c5d1SDavid du Colombier 5323e12c5d1SDavid du Colombier dot = expr(addr); 5333e12c5d1SDavid du Colombier cp = nextc(cp); 5343e12c5d1SDavid du Colombier if(strcmp(cp, "pc") == 0) { 5353e12c5d1SDavid du Colombier reg.pc = dot; 5363e12c5d1SDavid du Colombier return; 5373e12c5d1SDavid du Colombier } 5383e12c5d1SDavid du Colombier if(strcmp(cp, "sp") == 0) { 5393e12c5d1SDavid du Colombier reg.r[29] = dot; 5403e12c5d1SDavid du Colombier return; 5413e12c5d1SDavid du Colombier } 5423e12c5d1SDavid du Colombier if(strcmp(cp, "mh") == 0) { 5433e12c5d1SDavid du Colombier reg.mhi = dot; 5443e12c5d1SDavid du Colombier return; 5453e12c5d1SDavid du Colombier } 5463e12c5d1SDavid du Colombier if(strcmp(cp, "ml") == 0) { 5473e12c5d1SDavid du Colombier reg.mlo = dot; 5483e12c5d1SDavid du Colombier return; 5493e12c5d1SDavid du Colombier } 5503e12c5d1SDavid du Colombier if(*cp++ == 'r') { 5513e12c5d1SDavid du Colombier rn = strtoul(cp, 0, 10); 5523e12c5d1SDavid du Colombier if(rn > 0 && rn < 32) { 5533e12c5d1SDavid du Colombier reg.r[rn] = dot; 5543e12c5d1SDavid du Colombier return; 5553e12c5d1SDavid du Colombier } 5563e12c5d1SDavid du Colombier } 5573e12c5d1SDavid du Colombier Bprint(bioout, "bad register\n"); 5583e12c5d1SDavid du Colombier } 5593e12c5d1SDavid du Colombier 5603e12c5d1SDavid du Colombier void 5613e12c5d1SDavid du Colombier cmd(void) 5623e12c5d1SDavid du Colombier { 5633e12c5d1SDavid du Colombier char *p, *a, *cp, *gotint; 5643e12c5d1SDavid du Colombier char addr[128]; 5653e12c5d1SDavid du Colombier static char *cmdlet = ":$?/=>"; 5663e12c5d1SDavid du Colombier int n, i; 5673e12c5d1SDavid du Colombier 5683e12c5d1SDavid du Colombier notify(catcher); 5693e12c5d1SDavid du Colombier 5703e12c5d1SDavid du Colombier dot = reg.pc; 5713e12c5d1SDavid du Colombier setjmp(errjmp); 5723e12c5d1SDavid du Colombier 5733e12c5d1SDavid du Colombier for(;;) { 5743e12c5d1SDavid du Colombier Bflush(bioout); 5753e12c5d1SDavid du Colombier p = buf; 5763e12c5d1SDavid du Colombier n = 0; 5773e12c5d1SDavid du Colombier for(;;) { 5783e12c5d1SDavid du Colombier i = Bgetc(bin); 5793e12c5d1SDavid du Colombier if(i < 0) 5803e12c5d1SDavid du Colombier exits(0); 5813e12c5d1SDavid du Colombier *p++ = i; 5823e12c5d1SDavid du Colombier n++; 5833e12c5d1SDavid du Colombier if(i == '\n') 5843e12c5d1SDavid du Colombier break; 5853e12c5d1SDavid du Colombier } 5863e12c5d1SDavid du Colombier 5873e12c5d1SDavid du Colombier if(buf[0] == '\n') 5883e12c5d1SDavid du Colombier strcpy(buf, lastcmd); 5893e12c5d1SDavid du Colombier else { 5903e12c5d1SDavid du Colombier buf[n-1] = '\0'; 5913e12c5d1SDavid du Colombier strcpy(lastcmd, buf); 5923e12c5d1SDavid du Colombier } 5933e12c5d1SDavid du Colombier p = buf; 5943e12c5d1SDavid du Colombier a = addr; 5953e12c5d1SDavid du Colombier 5963e12c5d1SDavid du Colombier for(;;) { 5973e12c5d1SDavid du Colombier p = nextc(p); 5983e12c5d1SDavid du Colombier if(*p == 0 || strchr(cmdlet, *p)) 5993e12c5d1SDavid du Colombier break; 6003e12c5d1SDavid du Colombier *a++ = *p++; 6013e12c5d1SDavid du Colombier } 6023e12c5d1SDavid du Colombier 6033e12c5d1SDavid du Colombier *a = '\0'; 6043e12c5d1SDavid du Colombier cmdcount = 1; 6053e12c5d1SDavid du Colombier cp = strchr(addr, ','); 6063e12c5d1SDavid du Colombier if(cp != 0) { 6073e12c5d1SDavid du Colombier if(cp[1] == '#') 6083e12c5d1SDavid du Colombier cmdcount = strtoul(cp+2, &gotint, 16); 6093e12c5d1SDavid du Colombier else 6103e12c5d1SDavid du Colombier cmdcount = strtoul(cp+1, &gotint, 0); 6113e12c5d1SDavid du Colombier *cp = '\0'; 6123e12c5d1SDavid du Colombier } 6133e12c5d1SDavid du Colombier 6143e12c5d1SDavid du Colombier switch(*p) { 6153e12c5d1SDavid du Colombier case '$': 6163e12c5d1SDavid du Colombier dollar(p+1); 6173e12c5d1SDavid du Colombier break; 6183e12c5d1SDavid du Colombier case ':': 6193e12c5d1SDavid du Colombier colon(addr, p+1); 6203e12c5d1SDavid du Colombier break; 6213e12c5d1SDavid du Colombier case '/': 6223e12c5d1SDavid du Colombier case '?': 6233e12c5d1SDavid du Colombier dot = expr(addr); 6243e12c5d1SDavid du Colombier for(i = 0; i < cmdcount; i++) 6253e12c5d1SDavid du Colombier quesie(p+1); 6263e12c5d1SDavid du Colombier break; 6273e12c5d1SDavid du Colombier case '=': 6283e12c5d1SDavid du Colombier eval(addr, p+1); 6293e12c5d1SDavid du Colombier break; 6303e12c5d1SDavid du Colombier case '>': 6313e12c5d1SDavid du Colombier setreg(addr, p+1); 6323e12c5d1SDavid du Colombier break; 6333e12c5d1SDavid du Colombier default: 6343e12c5d1SDavid du Colombier Bprint(bioout, "?\n"); 6353e12c5d1SDavid du Colombier break; 6363e12c5d1SDavid du Colombier } 6373e12c5d1SDavid du Colombier } 6383e12c5d1SDavid du Colombier } 639