home *** CD-ROM | disk | FTP | other *** search
- /* [DOCTOR.C of JUGPDS Vol.18]
- *****************************************************************
- * *
- * Written by Hakuo Katayose (JUG-CP/M No.179) *
- * 49-114 Kawauchi-Sanjuunin-machi *
- * Sendai, Miyagi 980 *
- * Phone: 0222-61-3219 *
- * *
- * Edited & tested by Y. Monma (JUG-C/M Disk Editor) *
- * *
- *****************************************************************
- */
-
- /* doctor - disk doctor */
-
- #define BIOS_CALL(n,bc,de,a) biosh((n),(bc),(de))
-
-
- #define UP 0x05 /* Screen_Edit mode Cursole_up */
- #define DOWN 0x18 /* --II-- Cursole_down */
- #define LEFT 0x13 /* --II-- Cursole_letf */
- #define RIGHT 0x04 /* --II-- Cursole_right */
- #define ESC_CH '@' /* Special command sequence code */
- #define ENDINPUT 'Z' /* Screen_Edit mode exit */
- #define ABORT 'X' /* Screen_Edit mode exit without Write */
-
- /*
- ************************************************************************
- * HOME Cursor Home Positioning *
- * CLRS Clear Screen and Cursor Home Positioning *
- * POS(x,y) Set Cursor position (x,y) *
- ************************************************************************
- */
- #define ESC 0x1b
- #define HOME bios(4,ESC); bios(4,'H')
- #define CLRS bios(4,ESC); bios(4,'E')
- #define POS(x,y) bios(4,ESC); bios(4,'Y'); bios(4,y+32); bios(4,x+32)
-
-
- /*
- * Global DATA defintion
- */
-
- unsigned tpd, bpd, No_Of_Track, No_Of_Sector, No_Of_Block, Block_Length;
-
- /*
- * DPB (disk parameter block) definition for CP/M 2.x
- */
-
- struct dpb {
- int spt; /* logical sector per track */
- char bsh, /* block shift factor */
- blm, /* block mask */
- exm; /* extent mask */
- int dsm, /* disk storage (reacord) */
- drm; /* total directory entry - 1*/
- char al0,al1; /* allocation bit mask */
- int cks; /* size of directory check */
- int off; /* offset (system track) */
- };
-
- /*
- * DPH (disk parameter header) definition for CP/M 2.x
- */
-
-
- struct dph {
- char *xltp; /* logical to physical trans */
- char dmy1[6]; /* system use */
- char *dirb; /* pointer for DIR_BUFFER */
- struct dpb *dpbp; /* pointer for DPB */
- char *csvp, /* pointer for check_size */
- *alvp; /* pointer for allocation */
- };
-
-
- struct dph *DPH;
- struct dpb *DPB;
-
- int bn, bufcnt, es;
- char vflag, logflag, blkflag;
- char queflag, *quep;
- char *hexdigit;
-
- main()
-
- {
- char *p, c, comnd, buf[2048], w[128], *wp;
- int d, i, j, v, len, t, s, n, sc;
-
- hexdigit = "0123456789ABCDEFabcdef";
- queflag = 0;
- vflag = 0;
- logflag = 1;
- blkflag = 0;
- bn = 0;
- s = 1;
- p = buf;
- CLRS;
- POS(0, 0); printf("Disk: "); d = toupper(bios(3, 0)) - 'A';
- seldisk(d);
- t = 0;
- while ( GetSector(d, t, s, p) == 0 ) {
- loopd: POS(0, 4);
- Display(p);
- c = getchr();
- switch ((comnd = tolower(c))) {
- case 'a' :
- Modify(t, s, p, comnd, p);
- break;
- case 'b' :
- POS(57, 0); scanf("%d", &bn);
- if (bn < 0 || bn > DPB->dsm)
- break;
- blkflag = (blkflag) ? 0 : 1;
- logflag = 1;
- sc = bn * ( DPB->blm + 1);
- t = sc / DPB->spt;
- s = sc % DPB->spt + 1;
- break;
- case 'c' :
- setmem(p, 128, 0);
- PutSector(t, s, p);
- break;
- case 'd' :
- POS(5, 0); d = toupper(bios(3, 0)) - 'A';
- seldisk(d);
- break;
- case 'e' :
- exit();
- case 'h' :
- Modify(t, s, p, comnd, p);
- break;
- case 'i' :
- setmem(p, 128, 0x0e5);
- PutSector(t, s, p);
- break;
- case 'l' :
- logflag = logflag ? 0 : 1;
- seldisk(d);
- break;
- case 'q' :
- queflag = queflag ? 0 : 1;
- quep = "++++++++++++++++";
- goto loopd;
- case 't' :
- POS(16,0); scanf("%d", &t);
- break;
- case 's' :
- POS(37,0); scanf("%d", &s);
- break;
- case '+' :
- case ';' :
- if ( ++s > DPB->spt ) {s = 1; t++;}
- break;
- case '-' :
- case '=' :
- if ( --s < 1 ) {s = DPB->spt; t--;}
- break;
- case '>' :
- case '.' :
- t++;
- break;
- case '<' :
- case ',' :
- t--;
- break;
- case ']' :
- case '}' :
- bn++;
- if (bn < 0 || bn > DPB->dsm)
- break;
- blkflag = (blkflag) ? 0 : 1;
- logflag = 1;
- sc = bn * ( DPB->blm + 1);
- t = sc / DPB->spt;
- s = sc % DPB->spt + 1;
- break;
- case '[' :
- case '{' :
- bn--;
- if (bn < 0 || bn > DPB->dsm)
- break;
- blkflag = (blkflag) ? 0 : 1;
- logflag = 1;
- sc = bn * ( DPB->blm + 1);
- t = sc / DPB->spt;
- s = sc % DPB->spt + 1;
- break;
- default :
- goto loopd;
- }
- s = max(1, s);
- s = min(DPB->spt, s);
- t = max(0, t);
- t = min(tpd + DPB->off*logflag, t);
- bn = (t * DPB->spt + s -1)/(DPB->blm+1);
- }
- POS(0,23);
- }
-
-
- GetSector(d, t, s, p)
- char *p;
- {
- int bn;
-
- bn = (t * DPB->spt + s -1)/(DPB->blm+1);
- POS(16,0); printf("%4d ", t);
- POS(37,0); printf("%3d ", s);
- POS(56,0); printf("%4d ", bn);
- BIOS_CALL(10, t+logflag*DPB->off, 0, 0); /* set Track No */
- BIOS_CALL(11, s-1, 0, 0); /* set Sector No */
- BIOS_CALL(12, p, 0, 0); /* set DMA */
- /*
- BIOS_CALL(28, 0, 0, 1); /* for CP/M 3.x */
- */
- BIOS_CALL(13, 0, 0, 0);
- return 0;
- }
-
-
- PutSector(t, s, p)
- int t, s;
- char *p;
- {
- BIOS_CALL(10,t+logflag*DPB->off, 0, 0); /* set track no */
- BIOS_CALL(11, s-1, 0, 0); /* set Sector No */
- BIOS_CALL(12, p, 0, 0); /* set dma */
- /*
- BIOS_CALL(28, 0, 0, 1); /* for CP/M Plus */
- */
- BIOS_CALL(14, 1, 0, 0);
- }
-
-
- getchr()
- {
- if (queflag) {
- if (*(quep+1) == '\0')
- queflag = 0;
- return *quep++;
- }
- return bios(3, 0);
- }
-
-
- Modify(t, s, p, mode, bp)
- char *p, *bp, mode;
- {
- int j, x, y, c, c1, end_flag;
-
- j = 0;
- x = 0; y = 0;
-
- POS(0,12);
- printf(" ");
- POS(0,12);
- printf("%s mode Modify-Data :", mode == 'a' ? "Ascii" : "Hexdec");
- end_flag = 0;
- while (!end_flag) {
- POS(x+x, (mode == 'a' ? y+y+5 : y+y+4));
- switch (c = bios(3,0)) {
- case UP :
- if (y)
- y--;
- break;
- case DOWN :
- if (y < 4)
- y++;
- break;
- case LEFT :
- if (x)
- x--;
- else if (y) {
- x = 31;
- y--;
- }
- break;
- case RIGHT :
- if (x < 31)
- x++;
- else if (y < 3) {
- x = 0;
- y++;
- }
- break;
- default :
- if (c == ESC_CH) {
- if ((c = toupper(bios(3,0))) == ENDINPUT) {
- end_flag = 1;
- break;
- }
- else if (c == ABORT) {
- end_flag = 1;
- break;
- }
- }
- if (mode == 'h') {
- c1 = bios(3, 0);
- c1 = toupper(c1);
- c = toupper(c);
- if ((c1 = index_(hexdigit, c1)) >= 0
- && (c = index_(hexdigit, c)) >= 0) {
- *(p + j) = c*16+c1;
- }
- }
- else
- *(p + j) = c;
- POS(0, 4);
- Display(p);
- if (x < 31)
- x++;
- else if (y < 3) {
- x = 0;
- y++;
- }
- }
- j = (y << 5) + x;
- }
- if (c != ABORT)
- PutSector(t, s, bp);
- POS(0, 12);
- printf(" ");
- }
-
-
- seldisk(d)
- int d;
- {
- unsigned x,y,z;
-
- DPH = BIOS_CALL(9, d, 0, 0); /* select disk */
- DPB = DPH->dpbp;
- x = DPB->blm+1;
- y = DPB->dsm;
- z = DPB->spt;
- No_Of_Sector = z;
- No_Of_Track = (x * y + z - 1)/ z + DPB->off;
- No_Of_Block = y + 1;
- Block_Length = x * 128;
-
- POS(0,21);
- printf("Track_No :=%6d Sector_No :=%6d Block_No :=%6d\n",
- No_Of_Track, No_Of_Sector, No_Of_Block);
- printf("Offset :=%6u Directry :=%6u Block_size :=%6d",
- DPB->off, DPB->drm+1, Block_Length);
- POS(0,0);
- printf("Disk: Track: Sector: Block:");
- POS(5 ,0); putchar(d+'A');
- POS(0 ,2); printf(logflag ? "( Log" : "( Phys");
- POS(6 ,2); printf("ical-CP/M-Sector )");
- tpd = No_Of_Track-1;
- bpd = No_Of_Block-1;
- return DPB->off*logflag;
- }
-
-
- setmem(p, l, d)
- char *p, d;
- int l;
- {
- while (l--) *p++ = d;
- }
-
-
- index_(s, c)
- char *s, c;
- {
- char *p;
-
- for (p = s; *s != c; s++)
- if (!*s)
- return -1;
- return s-p;
- }
-
-
- /* for CP/M Plus
- BIOS_CALL(fn, bcreg, dereg, areg)
- {
- biospb.BIOS_NO = fn;
- biospb.BC_REG = bcreg;
- biospb.DE_REG = dereg;
- biospb.A_REG = areg;
- return bdos(50, &biospb);
- }
- */