Annotation of researchv9/jtools/src/pi/memory.c, revision 1.1.1.1

1.1       root        1: #include "core.pub"
                      2: #include "symtab.pub"
                      3: #include "memory.pri"
                      4: #include "parse.h"
                      5: #include "expr.pub"
                      6: #include "frame.pub"
                      7: #include "process.pub"
                      8: #include "format.pub"
                      9: #include "journal.pub"
                     10: SRCFILE("memory.c")
                     11: 
                     12: Memory::Memory(Core *c)
                     13: {
                     14:        core = c;
                     15:        prevpat = 0;
                     16: }
                     17: 
                     18: void Memory::userclose()
                     19: {
                     20:        trace("%d.userclose()", this);  VOK;
                     21:        delete pad;
                     22:        pad = 0;
                     23:        invalidate();
                     24:        Cell *cellsetsib;
                     25:        for( ; cellset; cellset = cellsetsib ){
                     26:                cellsetsib = cellset->sib;              // new malloc
                     27:                delete cellset;
                     28:        }
                     29:        current = 0;
                     30: }
                     31: 
                     32: void Memory::makecell(Cell *model, long addr )
                     33: {
                     34:        Cell *c;
                     35: 
                     36:        trace( "%d.makecell(%d,%d)", this, model, addr );       VOK;
                     37:        if( !model ){
                     38:                model = new Cell(this);
                     39:                model->fmt = F_HEX;
                     40:                model->size = 1;
                     41:        }
                     42:        for( c = cellset; c; c = c->sib )
                     43:                if( addr == c->addr ) break;
                     44:        if( !c ){
                     45:                c = new Cell(this);
                     46:                c->addr = addr;
                     47:                c->sib = cellset;
                     48:                cellset = c;
                     49:        }
                     50:        c->fmt = model->fmt;
                     51:        c->size = model->size;
                     52:        c->display();
                     53:        current = c;
                     54: }
                     55: 
                     56: void Memory::banner()
                     57: {
                     58:        trace( "%d.banner()", this );   VOK;
                     59:        if( pad ){
                     60:                pad->banner("Memory: %s", core->procpath());
                     61:                pad->name("Mem %s", basename(core->procpath()));
                     62:        }
                     63: }
                     64: 
                     65: void Memory::open(long a)
                     66: {
                     67:        trace( "%d.open(%d)", this, a );                VOK;
                     68:        if( !pad ){
                     69:                pad = new Pad((PadRcv*) this);
                     70:                banner();
                     71:        }
                     72:        pad->makecurrent();
                     73:        if( a ) makecell(current,a);
                     74: }
                     75: 
                     76: char *Memory::help()
                     77: {
                     78:        return ".=<expr> {show memory cell at address}";
                     79: }
                     80: 
                     81: char *Memory::kbd(char *s)
                     82: {
                     83:        Parse y(G_DOTEQ_CONEX,0);
                     84:        Expr *e;
                     85:        Bls error;
                     86: 
                     87:        trace( "%d.kbd(%s)", this, s ); OK(0);
                     88:        if( !(e = (Expr*)y.parse(s)) )
                     89:                return sf("%s: %s", y.error, s);
                     90:        e->evaltext(core->process()->globals, error);
                     91:        if( e->evalerr )
                     92:                return sf("%s: %s", s, error.text);
                     93:        makecell(current,e->val.lng);
                     94:        return 0;
                     95: }
                     96: 
                     97: struct FmtSize {
                     98:        long    fmt;
                     99:        long    size;
                    100: };
                    101: 
                    102: FmtSize FS[] = {
                    103:        F_DECIMAL,      7,
                    104:        F_SIGNED,       7,
                    105:        F_OCTAL,        7,
                    106:        F_HEX,          7,
                    107:        F_ASCII,        7,
                    108:        F_SYMBOLIC,     7,
                    109:        F_TIME,         4,
                    110:        F_FLOAT,        4,
                    111:        F_DOUBLE,       8,
                    112:        F_DBLHEX,       8,
                    113:        0,              0
                    114: };
                    115: 
                    116: Index Cell::carte()
                    117: {
                    118:        Menu m, s, f;
                    119: 
                    120:        OK(ZIndex);
                    121:        m.last( spy ? "unspy" : "spy on", (Action)&Cell::setspy, !spy );
                    122:        s.last("1 byte ", (Action)&Cell::resize, 1);
                    123:        s.last("2 bytes", (Action)&Cell::resize, 2);
                    124:        s.last("4 bytes", (Action)&Cell::resize, 4);
                    125:        s.last("8 bytes", (Action)&Cell::resize, 8);
                    126:        m.last(s.index("size"));
                    127: 
                    128:        for( int i = 0; FS[i].fmt; ++i )
                    129:                if( FS[i].size & size ){
                    130:                        long b = FS[i].fmt;
                    131:                        if( fmt&b ) b |= F_TURNOFF;
                    132:                        f.last(FmtName(b), (Action)&Cell::reformat,     b);
                    133:                }
                    134:        m.last(f.index("format"));
                    135:        m.last( ".+1",          (Action)&Cell::relative,        1       );
                    136:        m.last( ".+2",          (Action)&Cell::relative,        2       );
                    137:        m.last( ".+4",          (Action)&Cell::relative,        4       );
                    138:        if( size < 8 )
                    139:                m.last( "* thru .",     (Action)&Cell::indirect,        0       );
                    140:        m.last( ".-1",          (Action)&Cell::relative,        -1      );
                    141:        m.last( ".-2",          (Action)&Cell::relative,        -2      );
                    142:        m.last( ".-4",          (Action)&Cell::relative,        -4      );
                    143: 
                    144:        m.last( "asmblr",       (Action)&Cell::asmblr,          0       );
                    145: 
                    146:        return m.index();
                    147: }
                    148: 
                    149: void Cell::dodisplay(Bls &t)
                    150: {
                    151:        Cslfd *m;
                    152:        long afmt = fmt&~(F_ASCII|F_DOUBLE|F_FLOAT|F_DBLHEX|F_TIME);
                    153:        long cfmt = fmt&~F_SYMBOLIC;
                    154:        switch( size ){
                    155:        case 8:
                    156:                if( !(cfmt &= F_DOUBLE|F_DBLHEX) )
                    157:                        cfmt = F_DOUBLE;
                    158:                break;
                    159:        default:
                    160:                if( !(cfmt &= ~(F_DOUBLE|F_DBLHEX)) )
                    161:                        cfmt = F_HEX;
                    162:        }
                    163:        Format a(afmt?afmt:F_HEX, memory->core->symtab());
                    164:        Format c(cfmt);
                    165:        if( spy ) t.af( ">>> " );
                    166:        t.af( "%s/%d: ", a.f(addr), size );
                    167:        switch( size ){
                    168:                case 1: c.format |= F_MASKEXT8;  break;
                    169:                case 2: c.format |= F_MASKEXT16; break;
                    170:        }
                    171:        if( m = memory->core->peek(addr,0) ){
                    172:                long val;
                    173:                switch( size ){
                    174:                        case 1: c.format |= F_MASKEXT8;
                    175:                                val = m->chr;
                    176:                                break;
                    177:                        case 2: c.format |= F_MASKEXT16;
                    178:                                val = m->sht;
                    179:                                break;
                    180:                        case 4: val = m->lng;
                    181:                        }
                    182:                t.af( "%s", c.f(val, m->dbl) );
                    183:                if( spy ) *spy = *m;
                    184:        } else
                    185:                t.af( "cannot read" );
                    186: }
                    187: 
                    188: void Cell::display(char *error, int j)
                    189: {
                    190:        Bls t;
                    191: 
                    192:        trace( "%d.display()", this );  VOK;
                    193:        dodisplay(t);
                    194:        if( error ) t.af( " %s", error );
                    195:        Attrib attrib = ACCEPT_KBD|SELECTLINE;
                    196:        if( spy ) attrib |= DONT_CUT;
                    197:        memory->pad->insert(addr, attrib, (PadRcv*)this, carte(), "%s", t.text);
                    198:        if( j )
                    199:                memory->core->process()->journal()->insert("%s", t.text);
                    200: }
                    201: 
                    202: int Cell::changed()
                    203: {
                    204:        int changed = 0;
                    205:        Cslfd *m;
                    206: 
                    207:        trace( "%d.changed()" ); OK(0);
                    208:        if( !spy ) return 0;
                    209:        m = memory->core->peek(addr);
                    210:        switch( size ){
                    211:                case 1: if( m->chr != spy->chr ) changed = 1;  break;
                    212:                case 2: if( m->sht != spy->sht ) changed = 1;  break;
                    213:                case 4: if( m->lng != spy->lng ) changed = 1;  break;
                    214:                case 8: if( m->dbl != spy->dbl ) changed = 1;  break;
                    215:        }
                    216:        if( changed ) display(0,1);
                    217:        return changed;
                    218: }
                    219: 
                    220: 
                    221: void Cell::setspy(long s)
                    222: {
                    223:        trace( "%d.setspy(%d)", this, s );      VOK;
                    224:        if( !s && spy ){
                    225:                delete spy;
                    226:                spy = 0;
                    227:        } else if( s )
                    228:                spy = new Cslfd;
                    229:        display();
                    230: }
                    231: 
                    232: void Cell::relative(long a)
                    233: {
                    234:        trace( "%d.relative(%d)", this, a );    VOK;
                    235:        memory->makecell(this,addr+a*size);
                    236: }
                    237: 
                    238: void Cell::indirect()
                    239: {
                    240:        Cslfd *m;
                    241: 
                    242:        trace( "%d.indirect()", this );         VOK;
                    243:        if( !(m = memory->core->peek(addr,0)) )
                    244:            display();                  /* will have same problem */
                    245:        else
                    246:            memory->makecell(this, size==1 ? (unsigned  char) m->chr
                    247:                                 : size==2 ? (unsigned short) m->sht : m->lng);
                    248: }
                    249: 
                    250: char *Cell::help()
                    251: {
                    252:     return "$=<expr> {update cell} | .=<expr> {open cell} | [/?]<string> {search}";
                    253: }
                    254: 
                    255: char *Cell::search(int dir, char *pat)
                    256: {
                    257:        Cell s(memory);
                    258: 
                    259:        trace("%d.search(%d,%s)", this, dir, pat?pat:"0"); OK("Cell::search");
                    260:        if( !pat || !*pat || !strcmp(pat,"?") || !strcmp(pat,"/") )
                    261:                pat = memory->prevpat;
                    262:        memory->prevpat = sf("%s", pat);
                    263:        int patlen = strlen(pat);
                    264:        s = *this;
                    265:        long t0 = time(0);
                    266:        for( s.addr = addr+dir*size; s.addr != addr; s.addr += dir*size ){
                    267:                Cslfd *m = memory->core->peek(s.addr, 0);
                    268:                if( !m ){
                    269:                        memory->makecell(this,s.addr);
                    270:                        return "memory not contiguously readable for search";
                    271:                }
                    272:                Bls t;
                    273:                s.dodisplay(t);
                    274:                register char *p, pat0 = *pat;
                    275:                for( p = t.text; *p; ++p ){
                    276:                        if( *p == pat0 && !strncmp(p, pat, patlen) ){
                    277:                                memory->makecell(this,s.addr);
                    278:                                return 0;
                    279:                        }
                    280:                }
                    281:                const timeout = 10;
                    282:                if( time(0) > t0+timeout ){
                    283:                        memory->makecell(this,s.addr);
                    284:                        return sf("search timeout (%d secs)", timeout);
                    285:                }
                    286:        }
                    287: }
                    288: 
                    289: char *Cell::kbd(char *s)       /* should eval against loader symbol frame */
                    290: {
                    291:        Parse y(G_DOLEQ_CONEX, 0);
                    292:        Expr *e;
                    293:        Bls t;
                    294: 
                    295:        trace( "%d.kbd(%s)", this, s );         OK("kbd");
                    296:        if( !*s ){
                    297:                relative(1);
                    298:                return 0;
                    299:        }
                    300:        if( s[0] == '/' )
                    301:                return search( 1, s+1);
                    302:        if( s[0] == '?' )
                    303:                return search(-1, s+1);
                    304:        if( (e = (Expr*)y.parse(s)) ){
                    305:                e->evaltext(memory->core->process()->globals, t);
                    306:                display(e->evalerr ? t.text
                    307:                                   : memory->core->poke(addr,e->val.lng,size));
                    308:                return 0;
                    309:        }
                    310:        return memory->kbd(s);
                    311: }
                    312: 
                    313: void Cell::reformat(long f)
                    314: {
                    315:        trace( "%d.reformat(0x%X) 0x%X ", this, f, fmt ); VOK;
                    316:        fmt ^= f;
                    317:        if( f&F_TURNOFF )
                    318:                fmt &= ~f;
                    319:        else
                    320:                fmt |= f;
                    321:        display();
                    322: }
                    323: 
                    324: void Cell::resize(int s)
                    325: {
                    326:        trace( "%d.resize(%d) %d", this, s, size ); VOK;
                    327:        size = s;
                    328:        reformat(0);
                    329: }
                    330: 
                    331: void Cell::asmblr()
                    332: {
                    333:        trace( "%d.asmblr()" ); VOK;
                    334:        memory->core->process()->openasm(addr);
                    335: }
                    336: 
                    337: int Memory::changes(long verbose)
                    338: {
                    339:        Cell *c;
                    340:        long changes = 0, key = 0x40000000, spies = 0;  /* !!! */
                    341:        trace( "%d.changes()", this ); OK(0);
                    342: 
                    343:        pad->removeline(key);   
                    344:        for( c = cellset; c; c = c->sib )
                    345:                if( c->spy ){
                    346:                        ++spies;
                    347:                        changes += c->changed();
                    348:                }
                    349:        if( verbose ){
                    350:                if( spies == 0 )
                    351:                        pad->insert( key, SELECTLINE, "no spies" );
                    352:                else if( changes==0 )
                    353:                        pad->insert( key, SELECTLINE, "no spies changed" );
                    354:        }
                    355:        return changes;
                    356: }      

unix.superglobalmegacorp.com

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