From 8dabb2ab591ccaf0721ddf4e81ff8d0b5fa2ff4d Mon Sep 17 00:00:00 2001 From: "H. Peter Anvin" Date: Fri, 21 Sep 2007 16:24:35 -0700 Subject: [PATCH] memdisk: add "nopass" option to completely take over INT 13h Add the "nopass" option to completely remove the system drives. This is a pretty big hammer and is largely for debugging at this stage; it probably needs more polishing before it can be made official. --- memdisk/memdisk.asm | 4 ++- memdisk/setup.c | 70 ++++++++++++++++++++++++++++++----------------------- 2 files changed, 43 insertions(+), 31 deletions(-) diff --git a/memdisk/memdisk.asm b/memdisk/memdisk.asm index a171380..1e27e1e 100644 --- a/memdisk/memdisk.asm +++ b/memdisk/memdisk.asm @@ -91,7 +91,9 @@ Pointers: dw Int13Start dw Int15Start dw PatchArea dw TotalSize + dw IretPtr +IretPtr equ Int13Start.iret Int13Start: ; Swap stack mov [cs:Stack],esp @@ -139,7 +141,7 @@ Int13Start: pop ax pop bp lss esp,[cs:Stack] - iret +.iret: iret .our_drive: ; Set up standard entry frame diff --git a/memdisk/setup.c b/memdisk/setup.c index bacaba4..bffaf7a 100644 --- a/memdisk/setup.c +++ b/memdisk/setup.c @@ -1,6 +1,6 @@ /* ----------------------------------------------------------------------- * * - * Copyright 2001-2006 H. Peter Anvin - All Rights Reserved + * Copyright 2001-2007 H. Peter Anvin - All Rights Reserved * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -29,6 +29,7 @@ struct memdisk_header { uint16_t int15_offs; uint16_t patch_offs; uint16_t total_size; + uint16_t iret_offs; }; /* The Disk Parameter Table may be required */ @@ -762,37 +763,46 @@ void setup(syscall_t cs_syscall, void *cs_bounce) ranges[--nranges].type = -1; } - /* Query drive parameters of this type */ - memset(®s, 0, sizeof regs); - regs.es = 0; - regs.eax.b[1] = 0x08; - regs.edx.b[0] = geometry->driveno & 0x80; - syscall(0x13, ®s, ®s); - - if ( regs.eflags.l & 1 ) { - printf("INT 13 08: Failure, assuming this is the only drive\n"); + if (getcmditem("nopass") != CMD_NOTFOUND) { + /* nopass specified - we're the only drive by definition */ + printf("nopass specified - we're the only drive\n"); + bios_drives = 0; pptr->drivecnt = 0; + pptr->oldint13 = driverptr+hptr->iret_offs; } else { - printf("INT 13 08: Success, count = %u, BPT = %04x:%04x\n", - regs.edx.b[0], regs.es, regs.edi.w[0]); - pptr->drivecnt = regs.edx.b[0]; - } - - /* Compare what INT 13h returned with the appropriate equipment byte */ - if ( geometry->driveno & 0x80 ) { - bios_drives = rdz_8(BIOS_HD_COUNT); - } else { - uint8_t equip = rdz_8(BIOS_EQUIP); - - if (equip & 1) - bios_drives = (equip >> 6)+1; - else - bios_drives = 0; - } - - if (pptr->drivecnt > bios_drives) { - printf("BIOS equipment byte says count = %d, go with that\n", bios_drives); - pptr->drivecnt = bios_drives; + /* Query drive parameters of this type */ + memset(®s, 0, sizeof regs); + regs.es = 0; + regs.eax.b[1] = 0x08; + regs.edx.b[0] = geometry->driveno & 0x80; + syscall(0x13, ®s, ®s); + + if ( regs.eflags.l & 1 ) { + printf("INT 13 08: Failure, assuming this is the only drive\n"); + pptr->drivecnt = 0; + } else { + printf("INT 13 08: Success, count = %u, BPT = %04x:%04x\n", + regs.edx.b[0], regs.es, regs.edi.w[0]); + pptr->drivecnt = regs.edx.b[0]; + } + + /* Compare what INT 13h returned with the appropriate equipment byte */ + if ( geometry->driveno & 0x80 ) { + bios_drives = rdz_8(BIOS_HD_COUNT); + } else { + uint8_t equip = rdz_8(BIOS_EQUIP); + + if (equip & 1) + bios_drives = (equip >> 6)+1; + else + bios_drives = 0; + } + + if (pptr->drivecnt > bios_drives) { + printf("BIOS equipment byte says count = %d, go with that\n", + bios_drives); + pptr->drivecnt = bios_drives; + } } /* Add ourselves to the drive count */ -- 2.7.4