diff options
author | Kevin O'Connor <kevin@koconnor.net> | 2009-08-18 22:38:49 -0400 |
---|---|---|
committer | Kevin O'Connor <kevin@koconnor.net> | 2009-08-18 22:38:49 -0400 |
commit | 51cfbe76701c382a33070c490eedd00d3db8c0ee (patch) | |
tree | 75bb699ef335df5345a9a374a30d755fb510d2c1 | |
parent | e6f527a719377134f41bd2eab6906e03205a789b (diff) | |
download | seabios-51cfbe76701c382a33070c490eedd00d3db8c0ee.tar.gz |
Merge cdrom 13xx handlers with main disk 13xx handlers.
Most of the cdrom_13 code did the same thing as disk_13 - so merge
them together.
Add definitions for 0xe0 (EXTSTART_CD) and 0x80 (EXTSTART_HD).
This changes the behavior for cdroms on 1315 and 1316 calls -
previously 1315 returned an error and set ah=2, now it sets ah=1
and doesn't return an error; previously 1316 returned ok, not it
returns EPARAM.
-rw-r--r-- | src/cdrom.c | 173 | ||||
-rw-r--r-- | src/disk.c | 136 | ||||
-rw-r--r-- | src/disk.h | 3 |
3 files changed, 124 insertions, 188 deletions
diff --git a/src/cdrom.c b/src/cdrom.c index 6f9f00df..1801d22f 100644 --- a/src/cdrom.c +++ b/src/cdrom.c @@ -13,173 +13,15 @@ /**************************************************************** - * CDROM functions + * CD emulation ****************************************************************/ -// read disk drive size -static void -cdrom_1315(struct bregs *regs, u8 driveid) -{ - disk_ret(regs, DISK_RET_EADDRNOTFOUND); -} - -// lock -static void -cdrom_134500(struct bregs *regs, u8 driveid) -{ - u16 ebda_seg = get_ebda_seg(); - u8 locks = GET_EBDA2(ebda_seg, cdrom_locks[driveid]); - if (locks == 0xff) { - regs->al = 1; - disk_ret(regs, DISK_RET_ETOOMANYLOCKS); - return; - } - SET_EBDA2(ebda_seg, cdrom_locks[driveid], locks + 1); - regs->al = 1; - disk_ret(regs, DISK_RET_SUCCESS); -} - -// unlock -static void -cdrom_134501(struct bregs *regs, u8 driveid) -{ - u16 ebda_seg = get_ebda_seg(); - u8 locks = GET_EBDA2(ebda_seg, cdrom_locks[driveid]); - if (locks == 0x00) { - regs->al = 0; - disk_ret(regs, DISK_RET_ENOTLOCKED); - return; - } - locks--; - SET_EBDA2(ebda_seg, cdrom_locks[driveid], locks); - regs->al = (locks ? 1 : 0); - disk_ret(regs, DISK_RET_SUCCESS); -} - -// status -static void -cdrom_134502(struct bregs *regs, u8 driveid) -{ - u8 locks = GET_EBDA(cdrom_locks[driveid]); - regs->al = (locks ? 1 : 0); - disk_ret(regs, DISK_RET_SUCCESS); -} - -static void -cdrom_1345XX(struct bregs *regs, u8 driveid) -{ - disk_ret(regs, DISK_RET_EPARAM); -} - -// IBM/MS lock/unlock drive -static void -cdrom_1345(struct bregs *regs, u8 driveid) -{ - switch (regs->al) { - case 0x00: cdrom_134500(regs, driveid); break; - case 0x01: cdrom_134501(regs, driveid); break; - case 0x02: cdrom_134502(regs, driveid); break; - default: cdrom_1345XX(regs, driveid); break; - } -} - -// IBM/MS eject media -static void -cdrom_1346(struct bregs *regs, u8 driveid) -{ - u8 locks = GET_EBDA(cdrom_locks[driveid]); - if (locks != 0) { - disk_ret(regs, DISK_RET_ELOCKED); - return; - } - - // FIXME should handle 0x31 no media in device - // FIXME should handle 0xb5 valid request failed - - // Call removable media eject - struct bregs br; - memset(&br, 0, sizeof(br)); - br.ah = 0x52; - call16_int(0x15, &br); - - if (br.ah || br.flags & F_CF) { - disk_ret(regs, DISK_RET_ELOCKED); - return; - } - disk_ret(regs, DISK_RET_SUCCESS); -} - -// IBM/MS extended media change -static void -cdrom_1349(struct bregs *regs, u8 driveid) -{ - set_fail(regs); - // always send changed ?? - regs->ah = DISK_RET_ECHANGED; -} - -static void -cdrom_ok(struct bregs *regs, u8 driveid) -{ - disk_ret(regs, DISK_RET_SUCCESS); -} - static void -cdrom_wp(struct bregs *regs, u8 driveid) +cdemu_wp(struct bregs *regs, u8 driveid) { disk_ret(regs, DISK_RET_EWRITEPROTECT); } -void -cdrom_13(struct bregs *regs, u8 driveid) -{ - //debug_stub(regs); - - switch (regs->ah) { - case 0x15: cdrom_1315(regs, driveid); break; - case 0x45: cdrom_1345(regs, driveid); break; - case 0x46: cdrom_1346(regs, driveid); break; - case 0x49: cdrom_1349(regs, driveid); break; - - // These functions are the same as for hard disks - case 0x01: - case 0x41: - case 0x42: - case 0x44: - case 0x47: - case 0x48: - case 0x4e: - disk_13(regs, driveid); - break; - - // all these functions return SUCCESS - case 0x00: // disk controller reset - case 0x09: // initialize drive parameters - case 0x0c: // seek to specified cylinder - case 0x0d: // alternate disk reset - case 0x10: // check drive ready - case 0x11: // recalibrate - case 0x14: // controller internal diagnostic - case 0x16: // detect disk change - cdrom_ok(regs, driveid); - break; - - // all these functions return disk write-protected - case 0x03: // write disk sectors - case 0x05: // format disk track - case 0x43: // IBM/MS extended write - cdrom_wp(regs, driveid); - break; - - default: disk_13XX(regs, driveid); break; - } -} - - -/**************************************************************** - * CD emulation - ****************************************************************/ - static void cdemu_1302(struct bregs *regs, u8 driveid) { @@ -232,11 +74,14 @@ cdemu_13(struct bregs *regs) case 0x04: cdemu_1304(regs, driveid); break; case 0x08: cdemu_1308(regs, driveid); break; + case 0x03: + case 0x05: + cdemu_wp(regs, driveid); + break; + // These functions are the same as standard CDROM. case 0x00: case 0x01: - case 0x03: - case 0x05: case 0x09: case 0x0c: case 0x0d: @@ -245,7 +90,7 @@ cdemu_13(struct bregs *regs) case 0x14: case 0x15: case 0x16: - cdrom_13(regs, driveid); + disk_13(regs, driveid); break; default: disk_13XX(regs, driveid); break; @@ -479,7 +324,7 @@ cdrom_boot(int cdid) if (media == 0) { // No emulation requested - return success. - SET_EBDA2(ebda_seg, cdemu.emulated_extdrive, 0xE0 + cdid); + SET_EBDA2(ebda_seg, cdemu.emulated_extdrive, EXTSTART_CD + cdid); return 0; } @@ -23,7 +23,7 @@ void __disk_ret(struct bregs *regs, u32 linecode, const char *fname) { u8 code = linecode; - if (regs->dl < 0x80) + if (regs->dl < EXTSTART_HD) SET_BDA(floppy_last_status, code); else SET_BDA(disk_last_status, code); @@ -213,7 +213,7 @@ static void disk_1301(struct bregs *regs, u8 driveid) { u8 v; - if (regs->dl < 0x80) + if (regs->dl < EXTSTART_HD) // Floppy v = GET_BDA(floppy_last_status); else @@ -281,7 +281,7 @@ disk_1308(struct bregs *regs, u8 driveid) u16 nlh = GET_GLOBAL(Drives.drives[driveid].lchs.heads) - 1; u16 nlspt = GET_GLOBAL(Drives.drives[driveid].lchs.spt); u8 count; - if (regs->dl < 0x80) { + if (regs->dl < EXTSTART_HD) { // Floppy count = GET_GLOBAL(Drives.floppycount); @@ -290,10 +290,14 @@ disk_1308(struct bregs *regs, u8 driveid) // set es & di to point to 11 byte diskette param table in ROM regs->es = SEG_BIOS; regs->di = (u32)&diskette_param_table2; - } else { + } else if (regs->dl < EXTSTART_CD) { // Hard drive count = GET_BDA(hdcount); nlc--; // last sector reserved + } else { + // Not supported on CDROM + disk_ret(regs, DISK_RET_EPARAM); + return; } regs->al = 0; @@ -358,8 +362,8 @@ static void disk_1315(struct bregs *regs, u8 driveid) { disk_ret(regs, DISK_RET_SUCCESS); - if (regs->dl < 0x80) { - // Floppy + if (regs->dl < EXTSTART_HD || regs->dl >= EXTSTART_CD) { + // Floppy or cdrom regs->ah = 1; return; } @@ -380,7 +384,7 @@ disk_1315(struct bregs *regs, u8 driveid) static void disk_1316(struct bregs *regs, u8 driveid) { - if (regs->dl >= 0x80) { + if (regs->dl >= EXTSTART_HD) { // Hard drive disk_ret(regs, DISK_RET_EPARAM); return; @@ -419,20 +423,102 @@ disk_1344(struct bregs *regs, u8 driveid) extended_access(regs, driveid, CMD_VERIFY); } +// lock +static void +disk_134500(struct bregs *regs, u8 driveid) +{ + u16 ebda_seg = get_ebda_seg(); + u8 locks = GET_EBDA2(ebda_seg, cdrom_locks[driveid]); + if (locks == 0xff) { + regs->al = 1; + disk_ret(regs, DISK_RET_ETOOMANYLOCKS); + return; + } + SET_EBDA2(ebda_seg, cdrom_locks[driveid], locks + 1); + regs->al = 1; + disk_ret(regs, DISK_RET_SUCCESS); +} + +// unlock +static void +disk_134501(struct bregs *regs, u8 driveid) +{ + u16 ebda_seg = get_ebda_seg(); + u8 locks = GET_EBDA2(ebda_seg, cdrom_locks[driveid]); + if (locks == 0x00) { + regs->al = 0; + disk_ret(regs, DISK_RET_ENOTLOCKED); + return; + } + locks--; + SET_EBDA2(ebda_seg, cdrom_locks[driveid], locks); + regs->al = (locks ? 1 : 0); + disk_ret(regs, DISK_RET_SUCCESS); +} + +// status +static void +disk_134502(struct bregs *regs, u8 driveid) +{ + u8 locks = GET_EBDA(cdrom_locks[driveid]); + regs->al = (locks ? 1 : 0); + disk_ret(regs, DISK_RET_SUCCESS); +} + +static void +disk_1345XX(struct bregs *regs, u8 driveid) +{ + disk_ret(regs, DISK_RET_EPARAM); +} + // IBM/MS lock/unlock drive static void disk_1345(struct bregs *regs, u8 driveid) { - // Always success for HD - disk_ret(regs, DISK_RET_SUCCESS); + if (regs->dl < EXTSTART_CD) { + // Always success for HD + disk_ret(regs, DISK_RET_SUCCESS); + return; + } + + switch (regs->al) { + case 0x00: disk_134500(regs, driveid); break; + case 0x01: disk_134501(regs, driveid); break; + case 0x02: disk_134502(regs, driveid); break; + default: disk_1345XX(regs, driveid); break; + } } // IBM/MS eject media static void disk_1346(struct bregs *regs, u8 driveid) { - // Volume Not Removable - disk_ret(regs, DISK_RET_ENOTREMOVABLE); + if (regs->dl < EXTSTART_CD) { + // Volume Not Removable + disk_ret(regs, DISK_RET_ENOTREMOVABLE); + return; + } + + u8 locks = GET_EBDA(cdrom_locks[driveid]); + if (locks != 0) { + disk_ret(regs, DISK_RET_ELOCKED); + return; + } + + // FIXME should handle 0x31 no media in device + // FIXME should handle 0xb5 valid request failed + + // Call removable media eject + struct bregs br; + memset(&br, 0, sizeof(br)); + br.ah = 0x52; + call16_int(0x15, &br); + + if (br.ah || br.flags & F_CF) { + disk_ret(regs, DISK_RET_ELOCKED); + return; + } + disk_ret(regs, DISK_RET_SUCCESS); } // IBM/MS extended seek @@ -588,8 +674,14 @@ disk_1348(struct bregs *regs, u8 driveid) static void disk_1349(struct bregs *regs, u8 driveid) { - // Always success for HD - disk_ret(regs, DISK_RET_SUCCESS); + if (regs->dl < EXTSTART_CD) { + // Always success for HD + disk_ret(regs, DISK_RET_SUCCESS); + return; + } + set_fail(regs); + // always send changed ?? + regs->ah = DISK_RET_ECHANGED; } static void @@ -730,7 +822,7 @@ handle_legacy_disk(struct bregs *regs, u8 extdrive) return; } - if (extdrive < 0x80) { + if (extdrive < EXTSTART_HD) { int driveid = get_driveid(regs, EXTTYPE_FLOPPY, extdrive); if (driveid < 0) goto fail; @@ -738,15 +830,11 @@ handle_legacy_disk(struct bregs *regs, u8 extdrive) return; } - if (extdrive >= 0xe0) { - int driveid = get_driveid(regs, EXTTYPE_CD, extdrive - 0xe0); - if (driveid < 0) - goto fail; - cdrom_13(regs, driveid); - return; - } - - int driveid = get_driveid(regs, EXTTYPE_HD, extdrive - 0x80); + int driveid; + if (extdrive >= EXTSTART_CD) + driveid = get_driveid(regs, EXTTYPE_CD, extdrive - EXTSTART_CD); + else + driveid = get_driveid(regs, EXTTYPE_HD, extdrive - EXTSTART_HD); if (driveid < 0) goto fail; disk_13(regs, driveid); @@ -783,7 +871,7 @@ handle_13(struct bregs *regs) cdemu_13(regs); return; } - if (extdrive < 0xe0 && ((emudrive ^ extdrive) & 0x80) == 0) + if (extdrive < EXTSTART_CD && ((emudrive ^ extdrive) & 0x80) == 0) extdrive--; } } @@ -210,6 +210,9 @@ struct drives_s { #define EXTTYPE_HD 1 #define EXTTYPE_CD 2 +#define EXTSTART_HD 0x80 +#define EXTSTART_CD 0xE0 + /**************************************************************** * Function defs |