Annotation of coherent/b/bin/db/db8.c, revision 1.1.1.1

1.1       root        1: /*
                      2:  * db/db8.c
                      3:  * A debugger.
                      4:  * Child process.
                      5:  * All the machine-independent ptrace() code is here.
                      6:  */
                      7: 
                      8: #include <errno.h>
                      9: #include <signal.h>
                     10: #include <sys/param.h>
                     11: #include <sys/ptrace.h>
                     12: #include "db.h"
                     13: 
                     14: /*
                     15:  * Read 'n' characters starting at address 'a' into the buffer 'bp'
                     16:  * from segment 'f' in the child process.
                     17:  * Return 1 on success, 0 on failure.
                     18:  */
                     19: int
                     20: getp(f, a, bp, n) int f; ADDR_T a; register char *bp; register int n;
                     21: {
                     22:        int d, n1, pcmd;
                     23: 
                     24:        /* Set pcmd to the appropriate ptrace() read command. */
                     25:        switch(f) {
                     26:        case ISEG:      pcmd = PTRACE_RD_TXT;           break;
                     27:        case DSEG:      pcmd = PTRACE_RD_DAT;           break;
                     28:        case USEG:      pcmd = PTRACE_RD_USR;           break;
                     29:        }
                     30: 
                     31:        /* Read in PTSIZE-sized chunks. */
                     32:        for (errno = 0; n != 0; n -= n1, a += n1, bp += n1) {
                     33:                n1 = (n > PTSIZE) ? PTSIZE : n;
                     34:                d = ptrace(pcmd, pid, (int)a, 0);
                     35:                if (errno)
                     36:                        return 0;
                     37:                memcpy(bp, &d, n1);
                     38:        }
                     39:        return 1;
                     40: }
                     41: 
                     42: /*
                     43:  * Infanticide.
                     44:  */
                     45: void
                     46: killc()
                     47: {
                     48:        reg_flag = R_INVALID;
                     49:        if (execflag) {
                     50:                ptrace(PTRACE_TERM, pid, 0, 0);
                     51:                waitc();
                     52:                execflag = 0;
                     53:        }
                     54: #if    0
                     55:        trapstr = NULL;
                     56: #endif
                     57: }
                     58: 
                     59: /*
                     60:  * Write 'n' characters from the buffer 'bp'
                     61:  * to segment 'f' in the child process starting at address 'a'.
                     62:  * Return 1 on success, 0 on failure.
                     63:  */
                     64: int
                     65: putp(f, a, bp, n) int f; ADDR_T a; register char *bp; register int n;
                     66: {
                     67:        int d, n1, pcmd, prcmd;
                     68: 
                     69:        /* Set pcmd to the appropriate ptrace() write command. */
                     70:        switch(f) {
                     71:        case ISEG:      pcmd = PTRACE_WR_TXT;   break;
                     72:        case DSEG:      pcmd = PTRACE_WR_DAT;   break;
                     73:        case USEG:      pcmd = PTRACE_WR_USR;   break;
                     74:        }
                     75:        for (errno = 0; n != 0; n -= n1, a += n1, bp += n1) {
                     76:                if (n < PTSIZE) {
                     77:                        /* Read first so write can leave extra bytes unchanged. */
                     78:                        n1 = n;
                     79:                        switch(f) {
                     80:                        case ISEG:      prcmd = PTRACE_RD_TXT;  break;
                     81:                        case DSEG:      prcmd = PTRACE_RD_DAT;  break;
                     82:                        case USEG:      prcmd = PTRACE_RD_USR;  break;
                     83:                        }
                     84:                        d = ptrace(prcmd, pid, (int)a, 0);
                     85:                } else
                     86:                        n1 = PTSIZE;
                     87:                memcpy(&d, bp, n1);
                     88:                ptrace(pcmd, pid, (int)a, d);
                     89:                if (errno) {
                     90:                        perror("putp()");
                     91:                        return 0;
                     92:                }
                     93:        }
                     94:        return 1;
                     95: }
                     96: 
                     97: /*
                     98:  * Run the child and wait for it to stop.
                     99:  * Return 0 on error.
                    100:  */
                    101: int
                    102: runc()
                    103: {
                    104:        register int pcmd;
                    105: 
                    106:        switch (step_mode) {
                    107:        case SNULL:
                    108:        case SWAIT:
                    109:                pcmd = PTRACE_RESUME;
                    110:                break;
                    111:        case SCALL:
                    112:        case SCONT:
                    113:        case SSTEP:
                    114:                pcmd = PTRACE_SSTEP;
                    115:                break;
                    116:        default:
                    117:                panic("invalid step_mode=%d", step_mode);
                    118:        }
                    119:        errno = 0;
                    120:        reg_flag = R_INVALID;
                    121:        ptrace(pcmd, pid, 1, 0);
                    122:        if (errno) {
                    123:                perror("ptrace");
                    124:                return 0;
                    125:        }
                    126:        if (waitc() == 0)
                    127:                return 0;
                    128:        get_regs(R_SOME);
                    129:        return 1;
                    130: }
                    131: 
                    132: /*
                    133:  * Start execution of the child.
                    134:  * 'argv' is the argument list,
                    135:  * 'ifn' is the name of the input file,
                    136:  * 'ofn' is the name of the output file, and
                    137:  * 'aflag' tells us whether the output file is opened for append or write.
                    138:  */
                    139: int
                    140: startc(argv, ifn, ofn, aflag) char **argv; char *ifn; char *ofn; int aflag;
                    141: {
                    142:        register int n;
                    143: 
                    144:        reg_flag = R_INVALID;
                    145:        if ((pid = fork()) < 0)
                    146:                return printr("Cannot fork");
                    147:        if (pid == 0) {
                    148:                /* Child process. */
                    149:                if (ifn != NULL) {
                    150:                        if ((n=open(ifn, 0)) < 0)
                    151:                                panic("Cannot open \"%s\"", ifn);
                    152:                        dup2(n, 0);
                    153:                        close(n);
                    154:                }
                    155:                if (ofn != NULL) {
                    156:                        n = -1;
                    157:                        if (aflag) {
                    158:                                if ((n = open(ofn, 1)) >= 0)
                    159:                                        lseek(n, 0L, SEEK_END);
                    160:                        }
                    161:                        if (n < 0) {
                    162:                                if ((n=creat(ofn, 0644)) < 0)
                    163:                                        panic("%s: cannot create", ofn);
                    164:                        }
                    165:                        dup2(n, 1);
                    166:                        close(n);
                    167:                }
                    168:                ptrace(PTRACE_SETUP, 0, 0, 0);  /* I hear you, Dad... */
                    169:                execv(lfn, argv);
                    170:                exit(1);
                    171:        }
                    172:        /* Parent process. */
                    173:        if (waitc() == 0)
                    174:                return 0;
                    175: 
                    176:        /*
                    177:         * Now the child is running, so map the child process rather
                    178:         * than the disk file.
                    179:         * FIX_ME The map addresses for DSEG and ISEG here are bogus.
                    180:         */
                    181:        map_init();
                    182:        map_set(DSEG, MIN_ADDR, MAX_ADDR, (off_t)0, MAP_CHILD);
                    183:        map_set(ISEG, MIN_ADDR, MAX_ADDR, (off_t)0, MAP_CHILD);
                    184:        map_set(USEG, MIN_ADDR, (ADDR_T)UPASIZE, (off_t)0, MAP_CHILD);
                    185:        execflag = 1;
                    186:        get_regs(R_SOME);
                    187:        return 1;
                    188: }
                    189: 
                    190: /*
                    191:  * Wait for the child to stop.
                    192:  */
                    193: int
                    194: waitc()
                    195: {
                    196:        register int p;
                    197:        int s;
                    198: 
                    199:        while ((p = wait(&s)) != pid) {
                    200:                if (p >= 0) {
                    201:                        printr("Adopted a child %d", p);
                    202:                        continue;
                    203:                }
                    204:                if (intflag == 0) {
                    205:                        execflag = 0;
                    206:                        return printr("Nonexistent child");
                    207:                }
                    208:                intflag = 0;
                    209:        }
                    210:        if ((s & 0xff) != 0x7f) {
                    211:                execflag = 0;
                    212:                return printr("Child process terminated (0x%X)", (s >> 8) & 0xFF );
                    213:        }
                    214:        return 1;
                    215: }
                    216: 
                    217: #if    DBPTRACE
                    218: #undef ptrace
                    219: int
                    220: dbptrace(cmd, pid, loc, val) int cmd, pid, loc, val;
                    221: {
                    222:        register int n;
                    223: 
                    224:        printf("ptrace(%d, %d, 0x%X, 0x%X) = ", cmd, pid, loc, val);
                    225:        n = ptrace(cmd, pid, loc, val);
                    226:        printf("0x%X\n", n);
                    227:        return n;
                    228: }
                    229: #endif
                    230: 
                    231: /* end of db/db8.c */

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.