From 8d3ef773f8daea3a0c2b110ab48f235f5d2bf22d Mon Sep 17 00:00:00 2001 From: dzwdz Date: Tue, 5 Oct 2021 20:57:01 +0200 Subject: kill the process that caused an exception instead of panicking --- src/kernel/arch/i386/interrupts/isr.c | 27 +++++++++++++++++++-------- 1 file changed, 19 insertions(+), 8 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/interrupts/isr.c b/src/kernel/arch/i386/interrupts/isr.c index dacecba..6701d58 100644 --- a/src/kernel/arch/i386/interrupts/isr.c +++ b/src/kernel/arch/i386/interrupts/isr.c @@ -1,29 +1,40 @@ #include #include #include +#include #include #include -#define log_n_panic(x) {tty_const(x); panic_unimplemented();} // TODO kill the current process instead of panicking - bool isr_test_interrupt_called = false; +/** Kills the process that caused the exception */ +_Noreturn static void exception_finish(void) { + // TODO check if the exception was in the kernel + process_kill(process_current, 0); // TODO make the return code mean something + process_switch_any(); +} + void isr_stage3(int interrupt) { switch (interrupt) { - case 0x08: log_n_panic("#DF"); // double fault - case 0x0D: log_n_panic("#GP"); // general protection fault + case 0x08: // double fault + tty_const("#DF"); + panic_invalid_state(); + case 0x0D: // general protection fault + exception_finish(); case 0x0E: { // page fault - int cr2; + /*int cr2; tty_const("#PF at "); asm ("mov %%cr2, %0;" : "=r"(cr2) ::); - _tty_var(cr2); - panic_unimplemented(); + _tty_var(cr2);*/ + exception_finish(); } case 0x34: isr_test_interrupt_called = true; return; - default: log_n_panic("unknown interrupt"); + default: + tty_const("unknown interrupt"); + panic_unimplemented(); } } -- cgit v1.2.3 From 1ee734761a3eecbdaf9631a653dee668d2de26ef Mon Sep 17 00:00:00 2001 From: dzwdz Date: Tue, 5 Oct 2021 21:00:02 +0200 Subject: isr: simplify the exception handler --- src/kernel/arch/i386/interrupts/isr.c | 22 +++------------------- 1 file changed, 3 insertions(+), 19 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/interrupts/isr.c b/src/kernel/arch/i386/interrupts/isr.c index 6701d58..9d8bb6c 100644 --- a/src/kernel/arch/i386/interrupts/isr.c +++ b/src/kernel/arch/i386/interrupts/isr.c @@ -7,34 +7,18 @@ bool isr_test_interrupt_called = false; -/** Kills the process that caused the exception */ -_Noreturn static void exception_finish(void) { - // TODO check if the exception was in the kernel - process_kill(process_current, 0); // TODO make the return code mean something - process_switch_any(); -} - void isr_stage3(int interrupt) { switch (interrupt) { case 0x08: // double fault tty_const("#DF"); panic_invalid_state(); - case 0x0D: // general protection fault - exception_finish(); - case 0x0E: { // page fault - /*int cr2; - tty_const("#PF at "); - asm ("mov %%cr2, %0;" : "=r"(cr2) ::); - _tty_var(cr2);*/ - exception_finish(); - } - case 0x34: isr_test_interrupt_called = true; return; default: - tty_const("unknown interrupt"); - panic_unimplemented(); + // TODO check if the exception was in the kernel + process_kill(process_current, interrupt); + process_switch_any(); } } -- cgit v1.2.3 From 7e326b5039bff4d422f66bb8e51267f785193985 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Wed, 6 Oct 2021 22:15:02 +0200 Subject: kernel/i386: implement part of ATA IDENTIFY --- Makefile | 5 +++- src/kernel/arch/i386/ata.c | 65 +++++++++++++++++++++++++++++++++++++++++++++ src/kernel/arch/i386/ata.h | 4 +++ src/kernel/arch/i386/boot.c | 7 +++-- 4 files changed, 78 insertions(+), 3 deletions(-) create mode 100644 src/kernel/arch/i386/ata.c create mode 100644 src/kernel/arch/i386/ata.h (limited to 'src/kernel/arch/i386') diff --git a/Makefile b/Makefile index 08bb5d6..7757c25 100644 --- a/Makefile +++ b/Makefile @@ -19,7 +19,10 @@ endef all: out/boot.iso check boot: all - qemu-system-i386 -cdrom out/boot.iso $(QFLAGS) -no-shutdown + touch out/disk # TODO this is temporary + qemu-system-i386 -cdrom out/boot.iso $(QFLAGS) -no-shutdown \ + -drive file=out/disk,format=raw,media=disk + debug: all qemu-system-i386 -cdrom out/boot.iso $(QFLAGS) -s -S & diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c new file mode 100644 index 0000000..996fa3a --- /dev/null +++ b/src/kernel/arch/i386/ata.c @@ -0,0 +1,65 @@ +#include +#include +#include + +#include + +enum { + LBAlo = 3, + LBAmid = 4, + LBAhi = 5, + DRV = 6, + CMD = 7, + STATUS = 7, +}; // offsets + +// get I/O port base for drive +static uint16_t ata_iobase(int drive) { + bool secondary = drive&2; + return secondary ? 0x170 : 0x1F0; +} + +static void ata_driveselect(int drive, int block) { + uint8_t v = 0xE0; + if (drive&1) // slave? + v |= 0x10; // set drive number bit + // TODO account for block + port_outb(ata_iobase(drive) + DRV, v); +} + +static bool ata_identify(int drive) { + uint16_t iobase = ata_iobase(drive); + uint8_t v; + + ata_driveselect(drive, 0); + for (int i = 2; i < 6; i++) + port_outb(iobase + i, 0); + port_outb(iobase + CMD, 0xEC); // IDENTIFY + + v = port_inb(iobase + STATUS); + if (v == 0) return false; // nonexistent drive + while (port_inb(iobase + STATUS) & 0x80); + + /* check for uncomformant devices, quit early */ + if (port_inb(iobase + LBAmid) || port_inb(iobase + LBAhi)) { + // TODO atapi + return true; + } + /* pool until bit 3 (DRQ) or 0 (ERR) is set */ + while (!((v = port_inb(iobase + STATUS) & 0x9))); + if (v & 1) return false; /* ERR was set, bail */ + + // now I can read 512 bytes of data, TODO + return true; +} + +void ata_init(void) { + tty_const("\n"); + for (int i = 0; i < 4; i++) { + tty_const("probing drive "); + _tty_var(i); + if (ata_identify(i)) + tty_const(" - exists"); + tty_const("\n"); + } +} diff --git a/src/kernel/arch/i386/ata.h b/src/kernel/arch/i386/ata.h new file mode 100644 index 0000000..9137cdb --- /dev/null +++ b/src/kernel/arch/i386/ata.h @@ -0,0 +1,4 @@ +#pragma once +#include + +void ata_init(void); diff --git a/src/kernel/arch/i386/boot.c b/src/kernel/arch/i386/boot.c index bd2a00b..94e9e2f 100644 --- a/src/kernel/arch/i386/boot.c +++ b/src/kernel/arch/i386/boot.c @@ -1,4 +1,5 @@ #include +#include #include #include #include @@ -15,7 +16,9 @@ void kmain_early(struct multiboot_info *multiboot) { gdt_init(); tty_const("idt..."); idt_init(); - + tty_const("ata..."); + ata_init(); + { // find the init module struct multiboot_mod *module = &multiboot->mods[0]; if (multiboot->mods_count < 1) { @@ -25,6 +28,6 @@ void kmain_early(struct multiboot_info *multiboot) { info.init.at = module->start; info.init.size = module->end - module->start; } - + kmain(info); } -- cgit v1.2.3 From fbf6183ef8c9d49a14bd3ff01f378d67eaebc300 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Thu, 7 Oct 2021 06:25:02 +0000 Subject: kernel/i386: rename the port io functions with their bit length --- src/kernel/arch/i386/ata.c | 14 +++++++------- src/kernel/arch/i386/port_io.h | 4 ++-- src/kernel/arch/i386/tty/serial.c | 28 ++++++++++++++-------------- 3 files changed, 23 insertions(+), 23 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index 996fa3a..aaf05ff 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -24,7 +24,7 @@ static void ata_driveselect(int drive, int block) { if (drive&1) // slave? v |= 0x10; // set drive number bit // TODO account for block - port_outb(ata_iobase(drive) + DRV, v); + port_out8(ata_iobase(drive) + DRV, v); } static bool ata_identify(int drive) { @@ -33,20 +33,20 @@ static bool ata_identify(int drive) { ata_driveselect(drive, 0); for (int i = 2; i < 6; i++) - port_outb(iobase + i, 0); - port_outb(iobase + CMD, 0xEC); // IDENTIFY + port_out8(iobase + i, 0); + port_out8(iobase + CMD, 0xEC); // IDENTIFY - v = port_inb(iobase + STATUS); + v = port_in8(iobase + STATUS); if (v == 0) return false; // nonexistent drive - while (port_inb(iobase + STATUS) & 0x80); + while (port_in8(iobase + STATUS) & 0x80); /* check for uncomformant devices, quit early */ - if (port_inb(iobase + LBAmid) || port_inb(iobase + LBAhi)) { + if (port_in8(iobase + LBAmid) || port_in8(iobase + LBAhi)) { // TODO atapi return true; } /* pool until bit 3 (DRQ) or 0 (ERR) is set */ - while (!((v = port_inb(iobase + STATUS) & 0x9))); + while (!((v = port_in8(iobase + STATUS) & 0x9))); if (v & 1) return false; /* ERR was set, bail */ // now I can read 512 bytes of data, TODO diff --git a/src/kernel/arch/i386/port_io.h b/src/kernel/arch/i386/port_io.h index a4d640f..bcf2358 100644 --- a/src/kernel/arch/i386/port_io.h +++ b/src/kernel/arch/i386/port_io.h @@ -1,10 +1,10 @@ #include -static inline void port_outb(uint16_t port, uint8_t val) { +static inline void port_out8(uint16_t port, uint8_t val) { asm volatile("outb %0, %1" : : "a" (val), "Nd" (port)); } -static inline uint8_t port_inb(uint16_t port) { +static inline uint8_t port_in8(uint16_t port) { uint8_t val; asm volatile("inb %1, %0" : "=a" (val) : "Nd" (port)); return val; diff --git a/src/kernel/arch/i386/tty/serial.c b/src/kernel/arch/i386/tty/serial.c index 2b89ecf..f9bb252 100644 --- a/src/kernel/arch/i386/tty/serial.c +++ b/src/kernel/arch/i386/tty/serial.c @@ -7,37 +7,37 @@ static const int COM1 = 0x3f8; static void serial_selftest(void) { char b = 0x69; - port_outb(COM1 + 4, 0b00011110); // enable loopback mode - port_outb(COM1, b); - assert(port_inb(COM1) == b); + port_out8(COM1 + 4, 0b00011110); // enable loopback mode + port_out8(COM1, b); + assert(port_in8(COM1) == b); } void serial_init(void) { // see https://www.sci.muni.cz/docs/pc/serport.txt - port_outb(COM1 + 1, 0x00); // disable interrupts, we won't be using them + port_out8(COM1 + 1, 0x00); // disable interrupts, we won't be using them // set baud rate divisor - port_outb(COM1 + 3, 0b10000000); // enable DLAB - port_outb(COM1 + 0, 0x01); // divisor = 1 (low byte) - port_outb(COM1 + 1, 0x00); // (high byte) + port_out8(COM1 + 3, 0b10000000); // enable DLAB + port_out8(COM1 + 0, 0x01); // divisor = 1 (low byte) + port_out8(COM1 + 1, 0x00); // (high byte) - port_outb(COM1 + 3, 0b00000011); // 8 bits, no parity, one stop bit - port_outb(COM1 + 2, 0b11000111); // enable FIFO with 14-bit trigger level (???) + port_out8(COM1 + 3, 0b00000011); // 8 bits, no parity, one stop bit + port_out8(COM1 + 2, 0b11000111); // enable FIFO with 14-bit trigger level (???) serial_selftest(); - port_outb(COM1 + 4, 0b00001111); // enable everything in the MCR + port_out8(COM1 + 4, 0b00001111); // enable everything in the MCR } static void serial_putchar(char c) { - while ((port_inb(COM1 + 5) & 0x20) == 0); // wait for THRE - port_outb(COM1, c); + while ((port_in8(COM1 + 5) & 0x20) == 0); // wait for THRE + port_out8(COM1, c); } char serial_read(void) { - while ((port_inb(COM1 + 5) & 0x01) == 0); // wait for DR - return port_inb(COM1); + while ((port_in8(COM1 + 5) & 0x01) == 0); // wait for DR + return port_in8(COM1); } void serial_write(const char *buf, size_t len) { -- cgit v1.2.3 From 12ac8f2134d0ca0b103e70515acad3d6ccf9b9c0 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Thu, 7 Oct 2021 06:37:07 +0000 Subject: kernel/i386: add 16bit port io functions --- src/kernel/arch/i386/port_io.h | 10 ++++++++++ 1 file changed, 10 insertions(+) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/port_io.h b/src/kernel/arch/i386/port_io.h index bcf2358..1938c97 100644 --- a/src/kernel/arch/i386/port_io.h +++ b/src/kernel/arch/i386/port_io.h @@ -4,9 +4,19 @@ static inline void port_out8(uint16_t port, uint8_t val) { asm volatile("outb %0, %1" : : "a" (val), "Nd" (port)); } +static inline void port_out16(uint16_t port, uint16_t val) { + asm volatile("outw %0, %1" : : "a" (val), "Nd" (port)); +} + static inline uint8_t port_in8(uint16_t port) { uint8_t val; asm volatile("inb %1, %0" : "=a" (val) : "Nd" (port)); return val; } +static inline uint8_t port_in16(uint16_t port) { + uint16_t val; + asm volatile("inw %1, %0" : "=a" (val) : "Nd" (port)); + return val; +} + -- cgit v1.2.3 From 53d3fd65b47a3e0f9c4f439022f10852d765a9ba Mon Sep 17 00:00:00 2001 From: dzwdz Date: Thu, 7 Oct 2021 21:22:10 +0200 Subject: kernel/i386: fix port_in16's return value size --- src/kernel/arch/i386/port_io.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/port_io.h b/src/kernel/arch/i386/port_io.h index 1938c97..eac9331 100644 --- a/src/kernel/arch/i386/port_io.h +++ b/src/kernel/arch/i386/port_io.h @@ -14,7 +14,7 @@ static inline uint8_t port_in8(uint16_t port) { return val; } -static inline uint8_t port_in16(uint16_t port) { +static inline uint16_t port_in16(uint16_t port) { uint16_t val; asm volatile("inw %1, %0" : "=a" (val) : "Nd" (port)); return val; -- cgit v1.2.3 From 1ad3593c1b97027ffae0f1a97f58508d2980df00 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Thu, 7 Oct 2021 21:53:35 +0200 Subject: ATA: read identify data, detect drive size --- src/kernel/arch/i386/ata.c | 18 +++++++++++++++--- 1 file changed, 15 insertions(+), 3 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index aaf05ff..e33b5af 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -4,6 +4,10 @@ #include +static struct { + uint32_t sectors; +} ata_drives[4]; + enum { LBAlo = 3, LBAmid = 4, @@ -29,8 +33,11 @@ static void ata_driveselect(int drive, int block) { static bool ata_identify(int drive) { uint16_t iobase = ata_iobase(drive); + uint16_t data[256]; uint8_t v; + // TODO test for float + ata_driveselect(drive, 0); for (int i = 2; i < 6; i++) port_out8(iobase + i, 0); @@ -49,7 +56,9 @@ static bool ata_identify(int drive) { while (!((v = port_in8(iobase + STATUS) & 0x9))); if (v & 1) return false; /* ERR was set, bail */ - // now I can read 512 bytes of data, TODO + for (int i = 0; i < 256; i++) + data[i] = port_in16(iobase); + ata_drives[drive].sectors = data[60] | (data[61] << 16); return true; } @@ -58,8 +67,11 @@ void ata_init(void) { for (int i = 0; i < 4; i++) { tty_const("probing drive "); _tty_var(i); - if (ata_identify(i)) - tty_const(" - exists"); + if (ata_identify(i)) { + tty_const(" - "); + _tty_var(ata_drives[i].sectors); + tty_const(" sectors (512b)"); + } tty_const("\n"); } } -- cgit v1.2.3 From 574d2cf63006cabbf9db4a80c55a407b5b33a700 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Thu, 7 Oct 2021 21:59:22 +0200 Subject: ATA: detect device type --- src/kernel/arch/i386/ata.c | 21 +++++++++++++++++---- 1 file changed, 17 insertions(+), 4 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index e33b5af..4bc4293 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -5,6 +5,11 @@ #include static struct { + enum { + DEV_UNKNOWN, + DEV_PATA, + DEV_PATAPI, + } type; uint32_t sectors; } ata_drives[4]; @@ -47,11 +52,19 @@ static bool ata_identify(int drive) { if (v == 0) return false; // nonexistent drive while (port_in8(iobase + STATUS) & 0x80); - /* check for uncomformant devices, quit early */ - if (port_in8(iobase + LBAmid) || port_in8(iobase + LBAhi)) { - // TODO atapi - return true; + /* detect device type */ + switch (port_in8(iobase + LBAmid)) { + case 0: + ata_drives[drive].type = DEV_PATA; + break; + case 0x14: + ata_drives[drive].type = DEV_PATAPI; + return true; + default: + ata_drives[drive].type = DEV_UNKNOWN; + return false; } + /* pool until bit 3 (DRQ) or 0 (ERR) is set */ while (!((v = port_in8(iobase + STATUS) & 0x9))); if (v & 1) return false; /* ERR was set, bail */ -- cgit v1.2.3 From 0c000a03560eeab06154c1fb80b7a59a5c0f9ac7 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Fri, 8 Oct 2021 13:06:42 +0000 Subject: ata: proper drive type detection; soft reset; 400ns delay function --- src/kernel/arch/i386/ata.c | 67 +++++++++++++++++++++++++++++++++------------- 1 file changed, 49 insertions(+), 18 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index 4bc4293..916b918 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -20,6 +20,10 @@ enum { DRV = 6, CMD = 7, STATUS = 7, + + /* note: the OSDev wiki uses a different base port for the control port + * however i can just use this offset and stuff will just work tm */ + CTRL = 0x206, }; // offsets // get I/O port base for drive @@ -28,6 +32,12 @@ static uint16_t ata_iobase(int drive) { return secondary ? 0x170 : 0x1F0; } +static void ata_400ns(void) { + uint16_t base = ata_iobase(0); // doesn't matter + for (int i = 0; i < 4; i++) + port_in8(base + STATUS); +} + static void ata_driveselect(int drive, int block) { uint8_t v = 0xE0; if (drive&1) // slave? @@ -36,6 +46,38 @@ static void ata_driveselect(int drive, int block) { port_out8(ata_iobase(drive) + DRV, v); } +static void ata_softreset(int drive) { + uint16_t iobase = ata_iobase(drive); + port_out8(iobase + CTRL, 4); + port_out8(iobase + CTRL, 0); + ata_400ns(); + + uint16_t timeout = 10000; + while (--timeout) { // TODO separate polling function + uint8_t v = port_in8(iobase + STATUS); + if (v & 0x80) continue; // still BSY, continue + if (v & 0x40) break; // RDY, break + // TODO check for ERR + } +} + +static void ata_detecttype(int drive) { + ata_softreset(drive); + ata_driveselect(drive, 0); + ata_400ns(); + switch (port_in8(ata_iobase(drive) + LBAmid)) { + case 0: + ata_drives[drive].type = DEV_PATA; + break; + case 0x14: + ata_drives[drive].type = DEV_PATAPI; + return true; + default: + ata_drives[drive].type = DEV_UNKNOWN; + return false; + } +} + static bool ata_identify(int drive) { uint16_t iobase = ata_iobase(drive); uint16_t data[256]; @@ -52,19 +94,6 @@ static bool ata_identify(int drive) { if (v == 0) return false; // nonexistent drive while (port_in8(iobase + STATUS) & 0x80); - /* detect device type */ - switch (port_in8(iobase + LBAmid)) { - case 0: - ata_drives[drive].type = DEV_PATA; - break; - case 0x14: - ata_drives[drive].type = DEV_PATAPI; - return true; - default: - ata_drives[drive].type = DEV_UNKNOWN; - return false; - } - /* pool until bit 3 (DRQ) or 0 (ERR) is set */ while (!((v = port_in8(iobase + STATUS) & 0x9))); if (v & 1) return false; /* ERR was set, bail */ @@ -80,11 +109,13 @@ void ata_init(void) { for (int i = 0; i < 4; i++) { tty_const("probing drive "); _tty_var(i); - if (ata_identify(i)) { - tty_const(" - "); - _tty_var(ata_drives[i].sectors); - tty_const(" sectors (512b)"); - } + ata_detecttype(i); + _tty_var(ata_drives[i].type); + // if (ata_identify(i)) { + // tty_const(" - "); + // _tty_var(ata_drives[i].sectors); + // tty_const(" sectors (512b)"); + // } tty_const("\n"); } } -- cgit v1.2.3 From 6a90401ccb0d5a830772b8669113e1a17b6f40b7 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Fri, 8 Oct 2021 13:18:18 +0000 Subject: remove return statements from void function --- src/kernel/arch/i386/ata.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index 916b918..60dbb15 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -71,10 +71,10 @@ static void ata_detecttype(int drive) { break; case 0x14: ata_drives[drive].type = DEV_PATAPI; - return true; + break; default: ata_drives[drive].type = DEV_UNKNOWN; - return false; + break; } } -- cgit v1.2.3 From acf41ff6fee44dd24f9383d96fecd992dcb072e2 Mon Sep 17 00:00:00 2001 From: dzwdz Date: Fri, 8 Oct 2021 19:29:12 +0200 Subject: ATA: implement the IDENTIFY PACKET DEVICE command --- src/kernel/arch/i386/ata.c | 28 +++++++++++++++++++--------- 1 file changed, 19 insertions(+), 9 deletions(-) (limited to 'src/kernel/arch/i386') diff --git a/src/kernel/arch/i386/ata.c b/src/kernel/arch/i386/ata.c index 60dbb15..9224ed6 100644 --- a/src/kernel/arch/i386/ata.c +++ b/src/kernel/arch/i386/ata.c @@ -1,5 +1,6 @@ #include #include +#include #include #include @@ -83,12 +84,18 @@ static bool ata_identify(int drive) { uint16_t data[256]; uint8_t v; - // TODO test for float - ata_driveselect(drive, 0); for (int i = 2; i < 6; i++) port_out8(iobase + i, 0); - port_out8(iobase + CMD, 0xEC); // IDENTIFY + switch (ata_drives[drive].type) { + case DEV_PATA: + port_out8(iobase + CMD, 0xEC); // IDENTIFY + break; + case DEV_PATAPI: + port_out8(iobase + CMD, 0xA1); // IDENTIFY PACKET DEVICE + break; + default: panic_invalid_state(); + } v = port_in8(iobase + STATUS); if (v == 0) return false; // nonexistent drive @@ -110,12 +117,15 @@ void ata_init(void) { tty_const("probing drive "); _tty_var(i); ata_detecttype(i); - _tty_var(ata_drives[i].type); - // if (ata_identify(i)) { - // tty_const(" - "); - // _tty_var(ata_drives[i].sectors); - // tty_const(" sectors (512b)"); - // } + if (ata_drives[i].type != DEV_UNKNOWN) { + if (ata_identify(i)) { + tty_const(" - "); + _tty_var(ata_drives[i].sectors); + tty_const(" sectors (512b)"); + } else { + tty_const(" identify failed"); + } + } tty_const("\n"); } } -- cgit v1.2.3