Annotation of 43BSDTahoe/bin/adb/adb.tahoe/access.c, revision 1.1

1.1     ! root        1: #ifndef lint
        !             2: static char sccsid[] = "@(#)access.c   1.1 (Berkeley) 2/25/86";
        !             3: #endif
        !             4: /*
        !             5:  * Adb: access data in file/process address space.
        !             6:  *
        !             7:  * The routines in this file access referenced data using
        !             8:  * the maps to access files, ptrace to access subprocesses,
        !             9:  * or the system page tables when debugging the kernel,
        !            10:  * to translate virtual to physical addresses.
        !            11:  */
        !            12: 
        !            13: #include "defs.h"
        !            14: 
        !            15: MAP            txtmap;
        !            16: MAP            datmap;
        !            17: INT            wtflag;
        !            18: STRING         errflg;
        !            19: INT            errno;
        !            20: 
        !            21: L_INT          pid;
        !            22: 
        !            23: /*
        !            24:  * Primitives: put a value in a space, get a value from a space
        !            25:  * and get a word or byte not returning if an error occurred.
        !            26:  */
        !            27: put(addr, space, value) 
        !            28:     off_t addr; { (void) access(WT, addr, space, value); }
        !            29: 
        !            30: u_int
        !            31: get(addr, space)
        !            32:     off_t addr; { return (access(RD, addr, space, 0)); };
        !            33: 
        !            34: u_int
        !            35: chkget(addr, space)
        !            36:     off_t addr; { u_int w = get(addr, space); chkerr(); return(w); }
        !            37: 
        !            38: u_int
        !            39: bchkget(addr, space) 
        !            40:     off_t addr; { return (byte(chkget(addr, space))); }
        !            41: 
        !            42: /*
        !            43:  * Read/write according to mode at address addr in i/d space.
        !            44:  * Value is quantity to be written, if write.
        !            45:  *
        !            46:  * This routine decides whether to get the data from the subprocess
        !            47:  * address space with ptrace, or to get it from the files being
        !            48:  * debugged.  
        !            49:  *
        !            50:  * When the kernel is being debugged with the -k flag we interpret
        !            51:  * the system page tables for data space, mapping p0 and p1 addresses
        !            52:  * relative to the ``current'' process (as specified by its p_addr in
        !            53:  * <p) and mapping system space addresses through the system page tables.
        !            54:  */
        !            55: access(mode, addr, space, value)
        !            56:        int mode, space, value;
        !            57:        off_t addr;
        !            58: {
        !            59:        int rd = mode == RD;
        !            60:        int file, w;
        !            61: 
        !            62:        if (space == NSP)
        !            63:                return(0);
        !            64:        if (pid) {
        !            65:                int pmode = (space&DSP?(rd?RDUSER:WDUSER):(rd?RIUSER:WIUSER));
        !            66: 
        !            67:                w = ptrace(pmode, pid, addr, value);
        !            68:                if (errno)
        !            69:                        rwerr(space);
        !            70:                return (w);
        !            71:        }
        !            72:        w = 0;
        !            73:        if (mode==WT && wtflag==0)
        !            74:                error("not in write mode");
        !            75:        if (!chkmap(&addr, space))
        !            76:                return (0);
        !            77:        file = (space&DSP) ? datmap.ufd : txtmap.ufd;
        !            78:        if (kernel && space == DSP) {
        !            79:                addr = vtophys(addr);
        !            80:                if (addr < 0)
        !            81:                        return (0);
        !            82:        }
        !            83:        if (physrw(file, addr, rd ? &w : &value, rd) < 0)
        !            84:                rwerr(space);
        !            85:        return (w);
        !            86: }
        !            87: 
        !            88: /*
        !            89:  * When looking at kernel data space through /dev/mem or
        !            90:  * with a core file, do virtual memory mapping.
        !            91:  */
        !            92: vtophys(addr)
        !            93:        off_t addr;
        !            94: {
        !            95:        int oldaddr = addr;
        !            96:        int v;
        !            97:        struct pte pte;
        !            98: 
        !            99:        addr &= ~0xc0000000;
        !           100:        v = btop(addr);
        !           101:        switch (oldaddr&0xc0000000) {
        !           102: 
        !           103:        case 0xc0000000:
        !           104:                /*
        !           105:                 * In system space get system pte.  If
        !           106:                 * valid or reclaimable then physical address
        !           107:                 * is combination of its page number and the page
        !           108:                 * offset of the original address.
        !           109:                 */
        !           110:                if (v >= slr)
        !           111:                        goto oor;
        !           112:                addr = ((long)(sbr+v)) &~ 0xc0000000;
        !           113:                goto simple;
        !           114: 
        !           115:        case 0x80000000:
        !           116:                /*
        !           117:                 * In p2 spce must not be in shadow region.
        !           118:                 */
        !           119:                if (v < pcb.pcb_p2lr)
        !           120:                        goto oor;
        !           121:                addr = (long)(pcb.pcb_p2br+v);
        !           122:                break;
        !           123: 
        !           124:        case 0x40000000:
        !           125:                /*
        !           126:                 * In p1 space everything is verboten (for now).
        !           127:                 */
        !           128:                goto oor;
        !           129: 
        !           130:        case 0x00000000:
        !           131:                /*
        !           132:                 * In p0 space must not be off end of region.
        !           133:                 */
        !           134:                if (v >= pcb.pcb_p0lr)
        !           135:                        goto oor;
        !           136:                addr = (long)(pcb.pcb_p0br+v);
        !           137:                break;
        !           138:        oor:
        !           139:                errflg = "address out of segment";
        !           140:                return (-1);
        !           141:        }
        !           142:        /*
        !           143:         * For p0/p1/p2 address, user-level page table should
        !           144:         * be in kernel vm.  Do second-level indirect by recursing.
        !           145:         */
        !           146:        if ((addr & 0xc0000000) != 0xc0000000) {
        !           147:                errflg = "bad p0br, p1br, or p2br in pcb";
        !           148:                return (-1);
        !           149:        }
        !           150:        addr = vtophys(addr);
        !           151: simple:
        !           152:        /*
        !           153:         * Addr is now address of the pte of the page we
        !           154:         * are interested in; get the pte and paste up the
        !           155:         * physical address.
        !           156:         */
        !           157:        if (physrw(fcor, addr, (int *)&pte, 1) < 0) {
        !           158:                errflg = "page table botch";
        !           159:                return (-1);
        !           160:        }
        !           161:        /* SHOULD CHECK NOT I/O ADDRESS; NEED CPU TYPE! */
        !           162:        if (pte.pg_v == 0 && (pte.pg_fod || pte.pg_pfnum == 0)) {
        !           163:                errflg = "page not valid/reclaimable";
        !           164:                return (-1);
        !           165:        }
        !           166:        return ((long)(ptob(pte.pg_pfnum) + (oldaddr & PGOFSET)));
        !           167: }
        !           168: 
        !           169: rwerr(space)
        !           170:        int space;
        !           171: {
        !           172: 
        !           173:        if (space & DSP)
        !           174:                errflg = "data address not found";
        !           175:        else
        !           176:                errflg = "text address not found";
        !           177: }
        !           178: 
        !           179: physrw(file, addr, aw, rd)
        !           180:        off_t addr;
        !           181:        int *aw, rd;
        !           182: {
        !           183: 
        !           184:        if (longseek(file,addr)==0 ||
        !           185:            (rd ? read(file,aw,sizeof(int)) : write(file,aw,sizeof(int))) < 1)
        !           186:                return (-1);
        !           187:        return (0);
        !           188: }
        !           189: 
        !           190: chkmap(addr,space)
        !           191:        REG L_INT       *addr;
        !           192:        REG INT         space;
        !           193: {
        !           194:        REG MAPPTR amap;
        !           195: 
        !           196:        amap=((space&DSP?&datmap:&txtmap));
        !           197:        IF space&STAR ORF !within(*addr,amap->b1,amap->e1)
        !           198:        THEN IF within(*addr,amap->b2,amap->e2)
        !           199:             THEN *addr += (amap->f2)-(amap->b2);
        !           200:             ELSE rwerr(space); return(0);
        !           201:             FI
        !           202:        ELSE *addr += (amap->f1)-(amap->b1);
        !           203:        FI
        !           204:        return(1);
        !           205: }
        !           206: 
        !           207: within(addr,lbd,ubd)
        !           208:     u_int addr, lbd, ubd; { return(addr>=lbd && addr<ubd); }
        !           209: 
        !           210: longseek(f, a)
        !           211:     off_t a; { return(lseek(f, a, 0) != -1); }

unix.superglobalmegacorp.com

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