diff options
Diffstat (limited to 'src/cmd/db/runpcs.c')
-rw-r--r-- | src/cmd/db/runpcs.c | 205 |
1 files changed, 205 insertions, 0 deletions
diff --git a/src/cmd/db/runpcs.c b/src/cmd/db/runpcs.c new file mode 100644 index 00000000..4c05366b --- /dev/null +++ b/src/cmd/db/runpcs.c @@ -0,0 +1,205 @@ +/* + * + * debugger + * + */ + +#include "defs.h" +#include "fns.h" + +BKPT *bkpthead; + +BOOL bpin; + +int pid; +int nnote; +int ending; +char note[NNOTE][ERRMAX]; + +/* service routines for sub process control */ + +int +runpcs(int runmode, int keepnote) +{ + int rc; + BKPT *bkpt; + ADDR x; + + rc = 0; + if (adrflg) + rput(correg, mach->pc, dot); + if(rget(correg, mach->pc, &dot) < 0) + error("%r"); + flush(); + while (--loopcnt >= 0) { + if(loopcnt != 0) + printpc(); + if (runmode == SINGLE) { + bkpt = scanbkpt(dot); + if (bkpt) { + switch(bkpt->flag){ + case BKPTTMP: + bkpt->flag = BKPTCLR; + break; + case BKPTSKIP: + bkpt->flag = BKPTSET; + break; + } + } + runstep(dot, keepnote); + } else { + if(rget(correg, mach->pc, &x) < 0) + error("%r"); + if ((bkpt = scanbkpt(x)) != 0) { + execbkpt(bkpt, keepnote); + keepnote = 0; + } + setbp(); + runrun(keepnote); + } + keepnote = 0; + delbp(); + if(rget(correg, mach->pc, &dot) < 0) + error("%r"); + /* real note? */ + if (nnote > 0) { + keepnote = 1; + rc = 0; + continue; + } + bkpt = scanbkpt(dot); + if(bkpt == 0){ + keepnote = 0; + rc = 0; + continue; + } + /* breakpoint */ + if (bkpt->flag == BKPTTMP) + bkpt->flag = BKPTCLR; + else if (bkpt->flag == BKPTSKIP) { + execbkpt(bkpt, keepnote); + keepnote = 0; + loopcnt++; /* we didn't really stop */ + continue; + } + else { + bkpt->flag = BKPTSKIP; + --bkpt->count; + if ((bkpt->comm[0] == EOR || command(bkpt->comm, ':') != 0) + && bkpt->count != 0) { + execbkpt(bkpt, keepnote); + keepnote = 0; + loopcnt++; + continue; + } + bkpt->count = bkpt->initcnt; + } + rc = 1; + } + return(rc); +} + +/* + * finish the process off; + * kill if still running + */ + +void +endpcs(void) +{ + BKPT *bk; + + if(ending) + return; + ending = 1; + if (pid) { + if(pcsactive){ + killpcs(); + pcsactive = 0; + } + pid=0; + nnote=0; + for (bk=bkpthead; bk; bk = bk->nxtbkpt) + if (bk->flag == BKPTTMP) + bk->flag = BKPTCLR; + else if (bk->flag != BKPTCLR) + bk->flag = BKPTSET; + } + bpin = FALSE; + ending = 0; +} + +/* + * start up the program to be debugged in a child + */ + +void +setup(void) +{ + + nnote = 0; + startpcs(); + bpin = FALSE; + pcsactive = 1; +} + +/* + * skip over a breakpoint: + * remove breakpoints, then single step + * so we can put it back + */ +void +execbkpt(BKPT *bk, int keepnote) +{ + runstep(bk->loc, keepnote); + bk->flag = BKPTSET; +} + +/* + * find the breakpoint at adr, if any + */ + +BKPT * +scanbkpt(ADDR adr) +{ + BKPT *bk; + + for (bk = bkpthead; bk; bk = bk->nxtbkpt) + if (bk->flag != BKPTCLR && bk->loc == adr) + break; + return(bk); +} + +/* + * remove all breakpoints from the process' address space + */ + +void +delbp(void) +{ + BKPT *bk; + + if (bpin == FALSE || pid == 0) + return; + for (bk = bkpthead; bk; bk = bk->nxtbkpt) + if (bk->flag != BKPTCLR) + bkput(bk, 0); + bpin = FALSE; +} + +/* + * install all the breakpoints + */ + +void +setbp(void) +{ + BKPT *bk; + + if (bpin == TRUE || pid == 0) + return; + for (bk = bkpthead; bk; bk = bk->nxtbkpt) + if (bk->flag != BKPTCLR) + bkput(bk, 1); + bpin = TRUE; +} |