]> Zhao Yanbai Git Server - kernel.git/commitdiff
开始重写ATA硬盘驱动程序,目前已经获取硬盘基本信息,包括是否支持DMA和LBA48,还有硬盘大小
authoracevest <zhaoyanbai@126.com>
Tue, 9 Nov 2021 12:23:47 +0000 (20:23 +0800)
committeracevest <zhaoyanbai@126.com>
Wed, 10 Nov 2021 11:27:47 +0000 (19:27 +0800)
.bochsrc
drivers/ata.c [new file with mode: 0644]
drivers/ata.h [new file with mode: 0644]
drivers/blk_rw.c
drivers/ide.c
drivers/ide.h
drivers/keyboard.c
kernel/pci.c
kernel/setup.c

index 20bfd9712e02fc9dd7354c5d69d9385cc863fb62..939539de7c357d0bf83fcd9fc836b83d163dd97f 100644 (file)
--- a/.bochsrc
+++ b/.bochsrc
@@ -17,6 +17,7 @@
 #=======================================================================
 #plugin_ctrl: unmapped=0, e1000=1 # unload 'unmapped' and load 'e1000'
 
+
 #=======================================================================
 # CONFIG_INTERFACE
 #
@@ -539,7 +540,7 @@ vga: extension=vbe, update_freq=5, realtime=1, ddc=builtin
 #   mouse: type=serial, enabled=1
 #   mouse: enabled=0, toggle=ctrl+f10
 #=======================================================================
-mouse: enabled=0
+#mouse: enabled=1
 
 #=======================================================================
 # PCI:
@@ -760,7 +761,7 @@ ata3: enabled=0, ioaddr1=0x168, ioaddr2=0x360, irq=9
 #   ata3-master: type=disk, mode=flat, path=483M.sample, cylinders=1024, heads=15, spt=63
 #   ata3-slave:  type=cdrom, path=iso.sample, status=inserted
 #=======================================================================
-ata0-master: type=disk, mode=flat, path="HD.IMG"
+ata0-master: type=disk, mode=flat, path="HD.IMG", model="Generic aBCd"
 #ata0-master: type=disk, mode=flat, path="30M.sample"
 #ata0-master: type=disk, mode=flat, path="30M.sample", cylinders=615, heads=6, spt=17
 #ata0-master: type=disk, mode=flat, path="c.img", cylinders=0 # autodetect
@@ -1190,6 +1191,9 @@ parport1: enabled=1, file="parport.out"
 #usb_uhci: port2=cdrom, options2="path:image.iso"
 #usb_uhci: port1=printer, options1="file:printdata.bin"
 #usb_uhci: port2=floppy, options2="path:vvfat:diskette, model:teac"
+#usb_uhci: enabled=1
+#usb_uhci: port2=disk, options2=""path:uHD.IMG, sect_size:512"
+
 
 #=======================================================================
 # USB_OHCI:
diff --git a/drivers/ata.c b/drivers/ata.c
new file mode 100644 (file)
index 0000000..085d7e7
--- /dev/null
@@ -0,0 +1,82 @@
+/*
+ * ------------------------------------------------------------------------
+ *   File Name: ata.c
+ *      Author: Zhao Yanbai
+ *              2021-11-10 13:55:27 Wednesday CST
+ * Description: none
+ * ------------------------------------------------------------------------
+ */
+
+#include <ata.h>
+#include <io.h>
+#include <system.h>
+#include <types.h>
+
+// 本程序参考文档《AT Attachment with Packet Interface - 6》
+
+// https://wiki.osdev.org/ATA_PIO_Mode
+// To use the IDENTIFY command, select a target drive by sending 0xA0 for the master drive, or 0xB0 for the slave,
+// to the "drive select" IO port. On the Primary bus, this would be port 0x1F6. Then set the Sectorcount, LBAlo,
+// LBAmid, and LBAhi IO ports to 0 (port 0x1F2 to 0x1F5). Then send the IDENTIFY command (0xEC) to the Command IO
+// port (0x1F7).
+// Then read the Status port (0x1F7) again. If the value read is 0, the drive does not exist. For any
+// other value: poll the Status port (0x1F7) until bit 7 (BSY, value = 0x80) clears. Because of some ATAPI drives
+// that do not follow spec, at this point you need to check the LBAmid and LBAhi ports (0x1F4 and 0x1F5) to see if
+// they are non-zero. If so, the drive is not ATA, and you should stop polling. Otherwise, continue polling one of
+// the Status ports until bit 3 (DRQ, value = 8) sets, or until bit 0 (ERR, value = 1) sets. At that point, if ERR
+// is clear, the data is ready to read from the Data port (0x1F0). Read 256 16-bit values, and store them.
+//
+// ATAPI的情况暂时不用考虑,因为不是硬盘相关的
+// https://wiki.osdev.org/ATAPI
+// ATAPI refers to devices that use the Packet Interface of the ATA6 (or higher) standard command set. It is
+// basically a way to issue SCSI commands to a CD-ROM, CD-RW, DVD, or tape drive, attached to the ATA bus.
+//
+// 总结来说,仅考虑ATA硬盘的情况
+// 一个IDE接口能接Master、Slave两个DRIVE。
+// 一个PC机上通常有两个IDE接口(IDE0, IDE1或ATA0, ATA1),通常称通道0、1
+// 对于同一个IDE通道的两个DRIVE,共享同一组寄存器,它们之间的区分是通过Device寄存器的第4个bit位来实现的。0为Master,1为Slave
+//
+// 使用IDENTIFY命令步骤:
+//  1. 选择DRIVE,发送0xA0选择master,发送0xB0选择slave。(发送 0xE0 | (drive << 4)到Device寄存器)
+//  2. 发送0到该DRIVE所在通道的寄存器NSECTOR, LBAL, LBAM, LBAH
+//  3. 发送IDENTIFY(0xEC)命令到该通道的命令寄存器
+// 检查status寄存器:
+//  1. 若为0,就认为没有IDE
+//  2. 等到status的BSY位清除
+//  3. 等到status的DRQ位或ERR位设置
+u16 identify[256];
+void ata_read_identify(int dev) {  // 这里所用的dev是逻辑编号 ATA0、ATA1下的Master、Salve的dev分别为0,1,2,3
+    outb(0x00 | ((dev & 0x01) << 4), REG_DEVICE(dev));  // 根据文档P113,这里不用指定bit5, bit7,直接指示DRIVE就行
+    outb(ATA_CMD_IDENTIFY, REG_CMD(dev));
+    while (1) {
+        u8 status = inb(REG_STATUS(dev));
+        printk("hard disk status: %x %x\n", status, REG_STATUS(dev));
+        if ((status & ATA_STATUS_BSY) == 0 && (status & ATA_STATUS_DRQ) != 0) {
+            break;
+        }
+    }
+
+    // u16 *identify = (u16 *)kmalloc(ATA_NSECTOR, 0);
+    insw(REG_DATA(dev), identify, 512 / sizeof(u16));
+
+    // 第49个word的第8个bit位表示是否支持DMA
+    // 第83个word的第10个bit位表示是否支持LBA48,为1表示支持。
+    // 第100~103个word的八个字节表示user的LBA最大值
+    printk("%04x %04x %d %d\n", identify[49], 1 << 8, identify[49] & (1 << 8), (identify[49] & (1 << 8)) != 0);
+    if ((identify[49] & (1 << 8)) != 0) {
+        printk("support DMA\n");
+    }
+
+    if ((identify[83] & (1 << 10)) != 0) {
+        printk("support LBA48\n");
+
+        u64 lba = *(u64 *)(identify + 100);
+        printk("hard disk size: %u MB\n", (lba * 512) >> 20);
+    }
+}
+
+unsigned int ATA_CHL0_CMD_BASE = 0x1F0;
+unsigned int ATA_CHL1_CMD_BASE = 0x170;
+
+unsigned int ATA_CHL0_CTL_BASE = 0x3F6;
+unsigned int ATA_CHL1_CTL_BASE = 0x376;
\ No newline at end of file
diff --git a/drivers/ata.h b/drivers/ata.h
new file mode 100644 (file)
index 0000000..3f9dcac
--- /dev/null
@@ -0,0 +1,122 @@
+/*
+ * ------------------------------------------------------------------------
+ *   File Name: ata.h
+ *      Author: Zhao Yanbai
+ *              2021-11-10 13:55:29 Wednesday CST
+ * Description: none
+ * ------------------------------------------------------------------------
+ */
+
+#pragma once
+
+extern unsigned int ATA_CHL0_CMD_BASE;
+extern unsigned int ATA_CHL1_CMD_BASE;
+
+// CTL其实不用BASE,只有一个寄存器
+// 这么写纯粹是为了代码好看
+// DEVICE CONTROL REGISTER
+// bit7: HOB    High Order Byte (defined by 48-bit Address feature set).
+// bit[3-6]: -
+// bit2: SRST   Software Reset
+// bit1: IEN    Interrupt Enable
+// bit0: 0
+extern unsigned int ATA_CHL0_CTL_BASE;
+extern unsigned int ATA_CHL1_CTL_BASE;
+
+#define ATA_DATA 0
+#define ATA_FEATURES 1
+#define ATA_ERR 1
+#define ATA_ERR_BB 0x80
+#define ATA_ERR_ECC 0x40
+#define ATA_ERR_ID 0x10
+#define ATA_ERR_AC 0x04
+#define ATA_ERR_TK 0x02
+#define ATA_ERR_DM 0x01
+#define ATA_NSECTOR 2
+#define ATA_LBAL 3
+#define ATA_LBAM 4
+#define ATA_LBAH 5
+
+// DEVICE寄存器
+// bit7: 1
+// bit6: L 如果为1,LBA Mode
+// bit5: 1
+// bit4: DRIVE
+// bit[0, 3] HS 如果L为0就是磁头号Head Number,如果L为1,则为LBA的24-27位
+#define ATA_DEVICE 6
+
+#define ATA_CMD 7
+
+// bit7: BSY Busy. If BSY==1, no other bits in the register are valid
+// bit6: DRDY Drive Ready.
+// bit5: DF/SE Device Fault / Stream Error
+// bit4: # Command dependent. (formerly DSC bit)
+// bit3: DRQ Data Request. (ready to transfer data)
+// bit2: - Obsolete
+// bit1: - Obsolete
+// bit0: ERR
+#define ATA_STATUS 7              /* controller status */
+#define ATA_STATUS_BSY 0x80       /* controller busy */
+#define ATA_STATUS_RDY 0x40       /* drive ready */
+#define ATA_STATUS_WF 0x20        /* write fault */
+#define ATA_STATUS_SEEK_CMPT 0x10 /* seek complete */
+#define ATA_STATUS_DRQ 0x08       /* data transfer request */
+#define ATA_STATUS_CRD 0x04       /* correct data */
+#define ATA_STATUS_IDX 0x02       /* index pulse */
+#define ATA_STATUS_ERR 0x01       /* error */
+
+#define ATA_CMD_IDLE 0x00
+#define ATA_CMD_RECALIBRATE 0x10
+#define ATA_CMD_READ_PIO 0x20     /* read data */
+#define ATA_CMD_READ_PIO_EXT 0x24 /* read data (LBA-48 bit)*/
+#define ATA_CMD_READ_DMA 0xC8
+#define ATA_CMD_READ_DMA_EXT 0x25 /* read data DMA LBA48 */
+#define ATA_CMD_WRITE_PIO 0x30
+#define ATA_CMD_WRITE_PIO_EXT 0x34
+#define ATA_CMD_WRITE_DMA 0xCA
+#define ATA_CMD_WRITE_DMA_EXT 0X35
+#define ATA_CMD_READ_VERIFY 0x40
+#define ATA_CMD_FORMAT 0x50
+#define ATA_CMD_SEEK 0x70
+#define ATA_CMD_DIAG 0x90
+#define ATA_CMD_SPECIFY 0x91
+#define ATA_CMD_IDENTIFY_PACKET 0xA1
+#define ATA_CMD_IDENTIFY 0xEC
+
+#define ATA_CTL 0
+#define ATA_CTL_HOB 0x80 /* high order byte (LBA-48bit) */
+//#define     ATA_CTL_NOECC        0x40  /* disable ecc retry */
+//#define     ATA_CTL_EIGHTHEADS   0x08  /* more than 8 heads */
+#define ATA_CTL_SRST 0x04 /* soft reset controller */
+#define ATA_CTL_NIEN 0x02 /* disable interrupts */
+
+#define ATA_GET_CHL(dev) (0) /* only support channel 0 */
+#define ATA_GET_DEV(dev) (0) /* only support one hard disk */
+
+#define REG_CMD_BASE(dev, offset) (ATA_GET_CHL(dev) ? (ATA_CHL1_CMD_BASE + offset) : (ATA_CHL0_CMD_BASE + offset))
+#define REG_CTL_BASE(dev, offset) (ATA_GET_CHL(dev) ? (ATA_CHL1_CTL_BASE + offset) : (ATA_CHL0_CTL_BASE + offset))
+
+#define REG_DATA(dev) REG_CMD_BASE(dev, ATA_DATA)
+#define REG_ERR(dev) REG_CMD_BASE(dev, ATA_ERR)
+#define REG_NSECTOR(dev) REG_CMD_BASE(dev, ATA_NSECTOR)
+#define REG_LBAL(dev) REG_CMD_BASE(dev, ATA_LBAL)
+#define REG_LBAM(dev) REG_CMD_BASE(dev, ATA_LBAM)
+#define REG_LBAH(dev) REG_CMD_BASE(dev, ATA_LBAH)
+#define REG_DEVICE(dev) REG_CMD_BASE(dev, ATA_DEVICE)
+#define REG_STATUS(dev) REG_CMD_BASE(dev, ATA_STATUS)
+#define REG_FEATURES(dev) REG_CMD_BASE(dev, ATA_FEATURES)
+
+#define REG_CMD(dev) REG_CMD_BASE(dev, ATA_CMD)
+#define REG_CTL(dev) REG_CTL_BASE(dev, ATA_CTL)
+
+#define ATA_IDENT_DEVTYPE 0
+#define ATA_IDENT_CYLINDERS 2
+#define ATA_IDENT_HEADS 6
+#define ATA_IDENT_SECTORS 12
+#define ATA_IDENT_SERIAL 20
+#define ATA_IDENT_MODEL 54
+#define ATA_IDENT_CAPABILITIES 98
+#define ATA_IDENT_FIELDVALID 106
+#define ATA_IDENT_MAX_LBA 120
+#define ATA_IDENT_COMMANDSETS 164
+#define ATA_IDENT_MAX_LBA_EXT 200
index ce2fc36a5d2506dbb9327a7b3ee8203c88a7599a..0e74909a7b65372ae224e82d307213e2008a6436 100644 (file)
 
 // only support read
 void blk_rw(dev_t dev, u64_t offset, u32_t size, char *buf) {
-    assert(DEV_MAJOR(dev) == DEV_MAJOR_HDA);
-    assert(offset % SECT_SIZE == 0);
-    assert(size % SECT_SIZE == 0);
+    // assert(DEV_MAJOR(dev) == DEV_MAJOR_HDA);
+    // assert(offset % SECT_SIZE == 0);
+    // assert(size % SECT_SIZE == 0);
 
-    const part_t *p = ide_get_part(dev);
+    // const part_t *p = ide_get_part(dev);
 
-    u64_t lba = p->lba_start;
-    lba += offset / SECT_SIZE;
+    // u64_t lba = p->lba_start;
+    // lba += offset / SECT_SIZE;
 
-    assert(lba < p->lba_end);
+    // assert(lba < p->lba_end);
 
-    u32_t scnt = size / SECT_SIZE;
+    // u32_t scnt = size / SECT_SIZE;
 
-    printd("%s lba %u scnt %u\n", __func__, (u32_t)lba, scnt);
+    // printd("%s lba %u scnt %u\n", __func__, (u32_t)lba, scnt);
 
-    ide_do_read(lba, scnt, buf);
+    // ide_do_read(lba, scnt, buf);
 }
index 0e26f7fe62841eff7253e3bdb04b51b246ff3495..4bc985dcdb290082ffceb23875ae9ce28dd6774d 100644 (file)
  * ------------------------------------------------------------------------
  */
 
-#include <assert.h>
-#include <ide.h>
-#include <io.h>
-#include <irq.h>
-#include <pci.h>
-#include <printk.h>
-#include <sched.h>
-#include <semaphore.h>
-#include <string.h>
-#include <types.h>
-#include <wait.h>
-
-typedef struct _ide_drv {
-    pci_device_t *pci;
-    unsigned long pio_cnt;
-    unsigned long dma_cnt;
-    unsigned long irq_cnt;
-
-    unsigned int iobase;
-
-    unsigned int bus_cmd;
-    unsigned int bus_status;
-    unsigned int bus_prdt;
-
-    unsigned int read_mode;
-
-    u64_t ext_lba_base;
-    part_t part[MAX_SUPPORT_PARTITION_CNT];
-} ide_drive_t;
-
-typedef struct prd {
-    unsigned int addr;
-    unsigned int cnt : 16;
-    unsigned int reserved : 15;
-    unsigned int eot : 1;
-} prd_t;
-
-typedef struct {
-    u64_t lba;
-    u32_t scnt;
-    u32_t read_scnt;
-    char *buf;
-    bool finish;
-    wait_queue_head_t wait;
-} ide_request_t;
+// #include <assert.h>
+// #include <ide.h>
+// #include <io.h>
+// #include <irq.h>
+// #include <pci.h>
+// #include <printk.h>
+// #include <sched.h>
+// #include <semaphore.h>
+// #include <string.h>
+// #include <types.h>
+// #include <wait.h>
+
+// typedef struct _ide_drv {
+//     pci_device_t *pci;
+//     unsigned long pio_cnt;
+//     unsigned long dma_cnt;
+//     unsigned long irq_cnt;
+
+//     unsigned int iobase;
+
+//     unsigned int bus_cmd;
+//     unsigned int bus_status;
+//     unsigned int bus_prdt;
+
+//     unsigned int read_mode;
+
+//     u64_t ext_lba_base;
+//     part_t part[MAX_SUPPORT_PARTITION_CNT];
+// } ide_drive_t;
+
+// typedef struct prd {
+//     unsigned int addr;
+//     unsigned int cnt : 16;
+//     unsigned int reserved : 15;
+//     unsigned int eot : 1;
+// } prd_t;
+
+// typedef struct {
+//     u64_t lba;
+//     u32_t scnt;
+//     u32_t read_scnt;
+//     char *buf;
+//     bool finish;
+//     wait_queue_head_t wait;
+// } ide_request_t;
 
 typedef void (*ide_intr_func_t)();
 
 void ide_default_intr();
 
-ide_drive_t drv;
-DECLARE_MUTEX(mutex);
-ide_request_t ide_request;
+// ide_drive_t drv;
+// DECLARE_MUTEX(mutex);
+// ide_request_t ide_request;
 
 ide_intr_func_t ide_intr_func = ide_default_intr;
 
-unsigned char *dma_data = 0;
+// unsigned char *dma_data = 0;
 
-unsigned int HD_CHL0_CMD_BASE = 0x1F0;
-unsigned int HD_CHL1_CMD_BASE = 0x170;
+// unsigned int HD_CHL0_CMD_BASE = 0x1F0;
+// unsigned int HD_CHL1_CMD_BASE = 0x170;
 
-unsigned int HD_CHL0_CTL_BASE = 0x3F6;
-unsigned int HD_CHL1_CTL_BASE = 0x376;
+// unsigned int HD_CHL0_CTL_BASE = 0x3F6;
+// unsigned int HD_CHL1_CTL_BASE = 0x376;
 
-void ide_printl() { printl(MPL_IDE, "ide pio cnt %d dma cnt %d irq cnt %d", drv.pio_cnt, drv.dma_cnt, drv.irq_cnt); }
+// void ide_printl() { printl(MPL_IDE, "ide pio cnt %d dma cnt %d irq cnt %d", drv.pio_cnt, drv.dma_cnt, drv.irq_cnt); }
 
-void ide_cmd_out(dev_t dev, u32 sect_cnt, u64 sect_nr, u32 cmd) {
-    drv.pio_cnt++;
-    drv.read_mode = cmd;
+// void ide_cmd_out(dev_t dev, u32 sect_cnt, u64 sect_nr, u32 cmd) {
+//     drv.pio_cnt++;
+//     drv.read_mode = cmd;
 
-    ide_printl();
+//     ide_printl();
 
-    outb(0x00, REG_CTL(dev));
-    outb(0x40 | 0x00, REG_DEVSEL(dev));
+//     outb(0x00, REG_CTL(dev));
+//     outb(0x40 | 0x00, REG_DEVICE(dev));
 
-    outb((u8)((sect_cnt >> 8) & 0xFF), REG_NSECTOR(dev));  // High
-    outb((u8)((sect_nr >> 24) & 0xFF), REG_LBAL(dev));
-    outb((u8)((sect_nr >> 32) & 0xFF), REG_LBAM(dev));
-    outb((u8)((sect_nr >> 40) & 0xFF), REG_LBAH(dev));
+//     outb((u8)((sect_cnt >> 8) & 0xFF), REG_NSECTOR(dev));  // High
+//     outb((u8)((sect_nr >> 24) & 0xFF), REG_LBAL(dev));
+//     outb((u8)((sect_nr >> 32) & 0xFF), REG_LBAM(dev));
+//     outb((u8)((sect_nr >> 40) & 0xFF), REG_LBAH(dev));
 
-    outb((u8)((sect_cnt >> 0) & 0xFF), REG_NSECTOR(dev));  // Low
-    outb((u8)((sect_nr >> 0) & 0xFF), REG_LBAL(dev));
-    outb((u8)((sect_nr >> 8) & 0xFF), REG_LBAM(dev));
-    outb((u8)((sect_nr >> 16) & 0xFF), REG_LBAH(dev));
+//     outb((u8)((sect_cnt >> 0) & 0xFF), REG_NSECTOR(dev));  // Low
+//     outb((u8)((sect_nr >> 0) & 0xFF), REG_LBAL(dev));
+//     outb((u8)((sect_nr >> 8) & 0xFF), REG_LBAM(dev));
+//     outb((u8)((sect_nr >> 16) & 0xFF), REG_LBAH(dev));
 
-    outb(cmd, REG_CMD(dev));
-}
-
-part_t *ide_get_part(dev_t dev) {
-    assert(DEV_MAJOR(dev) == DEV_MAJOR_HDA);
-    assert(DEV_MINOR(dev) < MAX_SUPPORT_PARTITION_CNT);
-
-    return drv.part + DEV_MINOR(dev);
-}
-
-void ide_do_read(u64_t lba, u32_t scnt, char *buf) {
-    bool finish = false;
-    unsigned long flags;
-
-    ide_request_t *r = &ide_request;
-
-    down(&mutex);
-
-    r->lba = lba;
-    r->scnt = scnt;
-    r->read_scnt = 0;
-    r->buf = buf;
-    r->finish = false;
-    init_wait_queue(&r->wait);
-
-    task_union *task = current;
-    DECLARE_WAIT_QUEUE(wait, task);
-    add_wait_queue(&r->wait, &wait);
-
-    ide_cmd_out(0, scnt, lba, HD_CMD_READ_PIO_EXT);
-
-    while (true) {
-        // printd("%s pid %d is going to wait\n", __func__, sysc_getpid());
-        task->state = TASK_WAIT;
-        irq_save(flags);
-        finish = r->finish;
-        // printd("%s pid %d finish %u read_scnt %u scnt %u\n", __func__, sysc_getpid(), r->finish, r->read_scnt,
-        // r->scnt);
-        irq_restore(flags);
-
-        if (finish) break;
-
-        schedule();
-        // printd("%s pid %d is running\n", __func__, sysc_getpid());
-    }
-
-    // printd("%s pid %d is really running\n", __func__, sysc_getpid());
-    task->state = TASK_RUNNING;
-    del_wait_queue(&r->wait, &wait);
-}
-
-unsigned int sys_clock();
-
-void ide_pci_init(pci_device_t *pci) {
-    unsigned int v;
-
-    v = pci_read_config_word(pci_cmd(pci, PCI_COMMAND));
-    printk(" ide pci command %04x\n", v);
-
-    v = pci_read_config_byte(pci_cmd(pci, PCI_PROGIF));
-    printk(" ide pci program interface %02x\n", v);
-
-    unsigned int iobase = pci_read_config_long(pci_cmd(pci, PCI_BAR4));
-    printk(" ide pci Base IO Address Register %08x\n", iobase);
-    iobase &= 0xFFFC;  // 最低为0是内存地址为1是端口地址
-    drv.iobase = iobase;
-    drv.bus_cmd = iobase + PCI_IDE_CMD;
-    drv.bus_status = iobase + PCI_IDE_STATUS;
-    drv.bus_prdt = iobase + PCI_IDE_PRDT;
-
-    int i;
-    printk(" BARS: ");
-    for (i = 0; i < BARS_CNT; ++i) {
-        printk("%08x ", pci->bars[i]);
-        pci->bars[i] &= (~1UL);
-    }
-    printk("\n");
-
-    HD_CHL0_CMD_BASE = pci->bars[0] ? pci->bars[0] : HD_CHL0_CMD_BASE;
-    HD_CHL0_CTL_BASE = pci->bars[1] ? pci->bars[1] : HD_CHL0_CTL_BASE;
-
-    HD_CHL1_CMD_BASE = pci->bars[2] ? pci->bars[2] : HD_CHL1_CMD_BASE;
-    HD_CHL1_CTL_BASE = pci->bars[3] ? pci->bars[3] : HD_CHL1_CTL_BASE;
-
-    printk("channel0: cmd %04x ctl %04x channel1: cmd %04x ctl %04x\n", HD_CHL0_CMD_BASE, HD_CHL0_CTL_BASE,
-           HD_CHL1_CMD_BASE, HD_CHL1_CTL_BASE);
-    // printl(18, "channel0: cmd %04x ctl %04x channel1: cmd %04x ctl %04x", HD_CHL0_CMD_BASE, HD_CHL0_CTL_BASE,
-    // HD_CHL1_CMD_BASE, HD_CHL1_CTL_BASE);
-}
-
-void ide_status() {
-    u8_t idest = inb(REG_STATUS(0));
-    u8_t pcist = inb(drv.bus_status);
-    printk(" ide status %02x pci status %02x\n", idest, pcist);
-}
+//     outb(cmd, REG_CMD(dev));
+// }
 
-void ide_debug() {
-    unsigned int nsect = 1;
-    char *buf = kmalloc(1 * SECT_SIZE, 0);
-    if (buf == 0) panic("out of memory");
+// part_t *ide_get_part(dev_t dev) {
+//     assert(DEV_MAJOR(dev) == DEV_MAJOR_HDA);
+//     assert(DEV_MINOR(dev) < MAX_SUPPORT_PARTITION_CNT);
 
-    ide_do_read(0, nsect, buf);
+//     return drv.part + DEV_MINOR(dev);
+// }
 
-    u16_t sig = *((u16_t *)(buf + 510));
-    printk("%s SIG: %04x\n", __func__, sig);
+// void ide_do_read(u64_t lba, u32_t scnt, char *buf) {
+//     bool finish = false;
+//     unsigned long flags;
 
-    kfree(buf);
-}
-
-void init_pci_controller(unsigned int classcode) {
-    pci_device_t *pci = pci_find_device_by_classcode(classcode);
-    if (pci != 0 && pci->intr_line < 16) {
-        printk("found pci vendor %04x device %04x class %04x intr %d\n", pci->vendor, pci->device, pci->classcode,
-               pci->intr_line);
-        // printl(17, "found pci vendor %04x device %04x class %04x intr %d", pci->vendor, pci->device, pci->classcode,
-        // pci->intr_line);
-        ide_pci_init(pci);
-        drv.pci = pci;
-    }
-}
-
-void ide_default_intr() {
-    // printd("%s\n", __func__);
-    u8_t status = inb(REG_STATUS(0));
-
-    drv.irq_cnt++;
-
-    status = inb(drv.bus_status);
-    if (0 == (status & PCI_IDE_STATUS_INTR)) {
-        return;
-    }
-
-    status |= PCI_IDE_STATUS_INTR;
-    outb(status, drv.bus_status);
-    outb(0x00, drv.bus_cmd);
+//     ide_request_t *r = &ide_request;
 
-    u16_t sig = 0;
-    if (drv.read_mode == HD_CMD_READ_PIO_EXT) {
-        insl(REG_DATA(0), ide_request.buf + ide_request.read_scnt * (SECT_SIZE), (SECT_SIZE) >> 2);
-        ide_request.read_scnt++;
-        sig = *((u16_t *)(ide_request.buf + 510));
-    }
+//     down(&mutex);
 
-    if (drv.read_mode == HD_CMD_READ_DMA_EXT) {
-        sig = *((u16_t *)(dma_data + 510));
-    }
+//     r->lba = lba;
+//     r->scnt = scnt;
+//     r->read_scnt = 0;
+//     r->buf = buf;
+//     r->finish = false;
+//     init_wait_queue(&r->wait);
+
+//     task_union *task = current;
+//     DECLARE_WAIT_QUEUE(wait, task);
+//     add_wait_queue(&r->wait, &wait);
 
-    ide_printl();
+//     ide_cmd_out(0, scnt, lba, HD_CMD_READ_PIO_EXT);
+
+//     while (true) {
+//         // printd("%s pid %d is going to wait\n", __func__, sysc_getpid());
+//         task->state = TASK_WAIT;
+//         irq_save(flags);
+//         finish = r->finish;
+//         // printd("%s pid %d finish %u read_scnt %u scnt %u\n", __func__, sysc_getpid(), r->finish, r->read_scnt,
+//         // r->scnt);
+//         irq_restore(flags);
+
+//         if (finish) break;
+
+//         schedule();
+//         // printd("%s pid %d is running\n", __func__, sysc_getpid());
+//     }
+
+//     // printd("%s pid %d is really running\n", __func__, sysc_getpid());
+//     task->state = TASK_RUNNING;
+//     del_wait_queue(&r->wait, &wait);
+// }
+
+// unsigned int sys_clock();
 
-    // printd(" hard disk sig %04x read mode %x cnt %d\n", sig, drv.read_mode, drv.irq_cnt);
-    printl(MPL_IDE_INTR, "hard disk sig %x read mode %x cnt %d", sig, drv.read_mode, drv.irq_cnt);
+// void ide_pci_init(pci_device_t *pci) {
+//     unsigned int v;
 
-    outb(PCI_IDE_CMD_STOP, drv.bus_cmd);
+//     v = pci_read_config_word(pci_cmd(pci, PCI_COMMAND));
+//     printk(" ide pci command %04x\n", v);
+
+//     v = pci_read_config_byte(pci_cmd(pci, PCI_PROGIF));
+//     printk(" ide pci program interface %02x\n", v);
+
+//     unsigned int iobase = pci_read_config_long(pci_cmd(pci, PCI_BAR4));
+//     printk(" ide pci Base IO Address Register %08x\n", iobase);
+//     iobase &= 0xFFFC;  // 最低为0是内存地址为1是端口地址
+//     drv.iobase = iobase;
+//     drv.bus_cmd = iobase + PCI_IDE_CMD;
+//     drv.bus_status = iobase + PCI_IDE_STATUS;
+//     drv.bus_prdt = iobase + PCI_IDE_PRDT;
 
-    wake_up(&ide_request.wait);
-    if (drv.read_mode == HD_CMD_READ_PIO_EXT) {
-        if (ide_request.read_scnt == ide_request.scnt) ide_request.finish = true;
-    }
-
-    up(&mutex);
-}
+//     int i;
+//     printk(" BARS: ");
+//     for (i = 0; i < BARS_CNT; ++i) {
+//         printk("%08x ", pci->bars[i]);
+//         pci->bars[i] &= (~1UL);
+//     }
+//     printk("\n");
+
+//     HD_CHL0_CMD_BASE = pci->bars[0] ? pci->bars[0] : HD_CHL0_CMD_BASE;
+//     HD_CHL0_CTL_BASE = pci->bars[1] ? pci->bars[1] : HD_CHL0_CTL_BASE;
+
+//     HD_CHL1_CMD_BASE = pci->bars[2] ? pci->bars[2] : HD_CHL1_CMD_BASE;
+//     HD_CHL1_CTL_BASE = pci->bars[3] ? pci->bars[3] : HD_CHL1_CTL_BASE;
+
+//     printk("channel0: cmd %04x ctl %04x channel1: cmd %04x ctl %04x\n", HD_CHL0_CMD_BASE, HD_CHL0_CTL_BASE,
+//            HD_CHL1_CMD_BASE, HD_CHL1_CTL_BASE);
+//     // printl(18, "channel0: cmd %04x ctl %04x channel1: cmd %04x ctl %04x", HD_CHL0_CMD_BASE, HD_CHL0_CTL_BASE,
+//     // HD_CHL1_CMD_BASE, HD_CHL1_CTL_BASE);
+// }
+
+// void ide_status() {
+//     u8_t idest = inb(REG_STATUS(0));
+//     u8_t pcist = inb(drv.bus_status);
+//     printk(" ide status %02x pci status %02x\n", idest, pcist);
+// }
+
+// void ide_debug() {
+//     unsigned int nsect = 1;
+//     char *buf = kmalloc(1 * SECT_SIZE, 0);
+//     if (buf == 0) panic("out of memory");
+
+//     ide_do_read(0, nsect, buf);
+
+//     u16_t sig = *((u16_t *)(buf + 510));
+//     printk("%s SIG: %04x\n", __func__, sig);
+
+//     kfree(buf);
+// }
+
+// void init_pci_controller(unsigned int classcode) {
+//     pci_device_t *pci = pci_find_device_by_classcode(classcode);
+//     if (pci != 0 && pci->intr_line < 16) {
+//         printk("found pci vendor %04x device %04x class %04x intr %d\n", pci->vendor, pci->device, pci->classcode,
+//                pci->intr_line);
+//         // printl(17, "found pci vendor %04x device %04x class %04x intr %d", pci->vendor, pci->device,
+//         pci->classcode,
+//         // pci->intr_line);
+//         ide_pci_init(pci);
+//         drv.pci = pci;
+//     }
+// }
+void ide_default_intr() {}
+// void ide_default_intr() {
+//     // printd("%s\n", __func__);
+//     u8_t status = inb(REG_STATUS(0));
+
+//     drv.irq_cnt++;
+
+//     status = inb(drv.bus_status);
+//     if (0 == (status & PCI_IDE_STATUS_INTR)) {
+//         return;
+//     }
+
+//     status |= PCI_IDE_STATUS_INTR;
+//     outb(status, drv.bus_status);
+//     outb(0x00, drv.bus_cmd);
+
+//     u16_t sig = 0;
+//     if (drv.read_mode == HD_CMD_READ_PIO_EXT) {
+//         insl(REG_DATA(0), ide_request.buf + ide_request.read_scnt * (SECT_SIZE), (SECT_SIZE) >> 2);
+//         ide_request.read_scnt++;
+//         sig = *((u16_t *)(ide_request.buf + 510));
+//     }
+
+//     if (drv.read_mode == HD_CMD_READ_DMA_EXT) {
+//         sig = *((u16_t *)(dma_data + 510));
+//     }
+
+//     ide_printl();
+
+//     // printd(" hard disk sig %04x read mode %x cnt %d\n", sig, drv.read_mode, drv.irq_cnt);
+//     printl(MPL_IDE_INTR, "hard disk sig %x read mode %x cnt %d", sig, drv.read_mode, drv.irq_cnt);
+
+//     outb(PCI_IDE_CMD_STOP, drv.bus_cmd);
+
+//     wake_up(&ide_request.wait);
+//     if (drv.read_mode == HD_CMD_READ_PIO_EXT) {
+//         if (ide_request.read_scnt == ide_request.scnt) ide_request.finish = true;
+//     }
+
+//     up(&mutex);
+// }
 
 void ide_irq() { ide_intr_func(); }
 
-prd_t prd __attribute__((aligned(64 * 1024)));
-unsigned long gprdt = 0;
-
-#define DELAY400NS             \
-    {                          \
-        inb(HD_CHL0_CTL_BASE); \
-        inb(HD_CHL0_CTL_BASE); \
-        inb(HD_CHL0_CTL_BASE); \
-        inb(HD_CHL0_CTL_BASE); \
-    }
-
-void ide_dma_pci_lba48() {
-    drv.dma_cnt++;
-    drv.read_mode = HD_CMD_READ_DMA_EXT;
-#if 1
-    memset((void *)&prd, 0, sizeof(prd));
-    unsigned long addr = alloc_one_page(0);
-    dma_data = (char *)addr;
-    memset(dma_data, 0xBB, 512);
-    prd.addr = va2pa(addr);
-    prd.cnt = 512;
-    prd.eot = 1;
-    gprdt = va2pa(&prd);
-
-    printl(16, "gprdt %08x &prdt %08x prd.addr %08x addr %08x", gprdt, &prd, prd.addr, addr);
-
-    outb(PCI_IDE_CMD_STOP, drv.bus_cmd);
-    unsigned short status = inb(drv.bus_status);
-    outb(status | PCI_IDE_STATUS_INTR | PCI_IDE_STATUS_ERR, drv.bus_status);
-    outl(gprdt, drv.bus_prdt);
-    outb(PCI_IDE_CMD_WRITE, drv.bus_cmd);
-#endif
-
-#if 0
-    while ( 1 )
-    {
-        status = inb(HD_CHL0_CMD_BASE+HD_STATUS);
-        printk(" <%02x> ", status);
-        if((status & (HD_STATUS_BSY | HD_STATUS_DRQ)) == 0)
-        {
-            break;
-        }
-    }
-
-    outb(0x00, HD_CHL0_CMD_BASE+HD_DEVSEL);
-    DELAY400NS;
-
-    while ( 1 )
-    {
-        status = inb(HD_CHL0_CMD_BASE+HD_STATUS);
-        printk(" <%02x> ", status);
-        if((status & (HD_STATUS_BSY | HD_STATUS_DRQ)) == 0)
-        {
-            break;
-        }
-    }
-#endif
-
-    outb(0x00, HD_CHL0_CTL_BASE);  // Device Control
-
-    outb(0x00, HD_CHL0_CMD_BASE + HD_FEATURES);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_NSECTOR);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAL);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAM);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAH);
-
-    outb(0x00, HD_CHL0_CMD_BASE + HD_FEATURES);
-    outb(0x01, HD_CHL0_CMD_BASE + HD_NSECTOR);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAL);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAM);
-    outb(0x00, HD_CHL0_CMD_BASE + HD_LBAH);
-
-    outb(0x40, HD_CHL0_CMD_BASE + HD_DEVSEL);
-
-    outb(HD_CMD_READ_DMA_EXT, HD_CHL0_CMD_BASE + HD_CMD);
-
-    inb(drv.bus_cmd);
-    inb(drv.bus_status);
-    unsigned short w = inb(drv.bus_cmd);
-    outb(w | PCI_IDE_CMD_WRITE | PCI_IDE_CMD_START, drv.bus_cmd);
-    inb(drv.bus_cmd);
-    inb(drv.bus_status);
-}
-
-typedef struct {
-    u8_t a;
-    u8_t b;
-    u16_t lbah;  // lba high
-    u8_t type;
-    u8_t f;
-    u16_t scnth;  // sector count high
-    u32_t lba;    // lba low
-    u32_t scnt;   // sector count
-} hd_part_t;
-
-void ide_read_extended_partition(u64_t lba, unsigned int inx) {
-    if (inx >= MAX_SUPPORT_PARTITION_CNT) return;
-
-    unsigned int i;
-    char *buf = kmalloc(512, 0);
-    if (buf == 0) panic("no memory");
-
-    ide_do_read(lba, 1, buf);
-
-    u16_t sig = *((u16_t *)(buf + 510));
-    if (sig != 0xAA55) panic("bad partition sect");
-
-    hd_part_t *p = (hd_part_t *)(buf + PARTITION_TABLE_OFFSET);
-    printd("%s:%d lba %d \n", __func__, __LINE__, lba);
-
-    for (i = 0; i < PARTITION_CNT; ++i, ++p) {
-        if (p->type == 0) continue;
-
-        // u64_t   part_lba = lba + (p->lba|((p->lbah*1ULL)<<32));
-        // u64_t   part_scnt= p->scnt | ((p->scnth*1ULL)<<32);
-        u64_t part_lba = lba + p->lba;
-        u64_t part_scnt = p->scnt;
-
-        if (p->type != 0x05) {
-            drv.part[inx].lba_start = part_lba;
-            drv.part[inx].lba_end = part_lba + part_scnt;
-            printk("  logic partition[%02d] [%02x] LBA base %10d end %10d\n", inx, p->type,
-                   (unsigned int)(drv.part[inx].lba_start), (unsigned int)(drv.part[inx].lba_end - 1));
-        } else {
-            part_lba = drv.ext_lba_base + p->lba;
-            printk("        extended      [%02x] LBA base %10d end %10d\n", p->type, (unsigned int)(part_lba),
-                   (unsigned int)(part_lba + part_scnt - 1));
-            ide_read_extended_partition(part_lba, inx + 1);
-        }
-    }
-
-    kfree(buf);
-}
-
-void ide_read_partition() {
-    printk("reading partitions....\n");
-    unsigned int i;
-    char *buf = kmalloc(512, 0);
-    if (buf == 0) panic("no memory");
-
-    ide_do_read(0, 1, buf);
-
-    u16_t sig = *((u16_t *)(buf + 510));
-    if (sig != 0xAA55) panic("bad partition sect");
-
-    hd_part_t *p = (hd_part_t *)(buf + PARTITION_TABLE_OFFSET);
-
-    unsigned int ext_inx = ~0U;
-
-    for (i = 0; i < PARTITION_CNT; ++i, ++p) {
-        if (p->type == 0) continue;
-
-        // u64_t   part_lba = p->lba|((p->lbah*1ULL)<<32);
-        // u64_t   part_scnt= p->scnt | ((p->scnth*1ULL)<<32);
-        u64_t part_lba = p->lba;
-        u64_t part_scnt = p->scnt;
-
-        drv.part[i].lba_start = part_lba;
-        drv.part[i].lba_end = part_lba + part_scnt;
-
-        if (p->type == 0x05) {
-            if (drv.ext_lba_base == 0) {
-                drv.ext_lba_base = drv.part[i].lba_start;
-                ext_inx = i;
-            }
-        }
-
-        printk("primary partition[%02d] [%02x] LBA base %10d end %10d\n", i, p->type, (unsigned int)(part_lba),
-               (unsigned int)(part_lba + part_scnt - 1));
-    }
-
-    kfree(buf);
-
-    if (ext_inx != ~0U) ide_read_extended_partition(drv.part[ext_inx].lba_start, 4);
-}
-
+// prd_t prd __attribute__((aligned(64 * 1024)));
+// unsigned long gprdt = 0;
+
+// #define DELAY400NS             \
+//     {                          \
+//         inb(HD_CHL0_CTL_BASE); \
+//         inb(HD_CHL0_CTL_BASE); \
+//         inb(HD_CHL0_CTL_BASE); \
+//         inb(HD_CHL0_CTL_BASE); \
+//     }
+
+// void ide_dma_pci_lba48() {
+//     drv.dma_cnt++;
+//     drv.read_mode = HD_CMD_READ_DMA_EXT;
+// #if 1
+//     memset((void *)&prd, 0, sizeof(prd));
+//     unsigned long addr = alloc_one_page(0);
+//     dma_data = (char *)addr;
+//     memset(dma_data, 0xBB, 512);
+//     prd.addr = va2pa(addr);
+//     prd.cnt = 512;
+//     prd.eot = 1;
+//     gprdt = va2pa(&prd);
+
+//     printl(16, "gprdt %08x &prdt %08x prd.addr %08x addr %08x", gprdt, &prd, prd.addr, addr);
+
+//     outb(PCI_IDE_CMD_STOP, drv.bus_cmd);
+//     unsigned short status = inb(drv.bus_status);
+//     outb(status | PCI_IDE_STATUS_INTR | PCI_IDE_STATUS_ERR, drv.bus_status);
+//     outl(gprdt, drv.bus_prdt);
+//     outb(PCI_IDE_CMD_WRITE, drv.bus_cmd);
+// #endif
+
+// #if 0
+//     while ( 1 )
+//     {
+//         status = inb(HD_CHL0_CMD_BASE+HD_STATUS);
+//         printk(" <%02x> ", status);
+//         if((status & (HD_STATUS_BSY | HD_STATUS_DRQ)) == 0)
+//         {
+//             break;
+//         }
+//     }
+
+//     outb(0x00, HD_CHL0_CMD_BASE+HD_DEVICE);
+//     DELAY400NS;
+
+//     while ( 1 )
+//     {
+//         status = inb(HD_CHL0_CMD_BASE+HD_STATUS);
+//         printk(" <%02x> ", status);
+//         if((status & (HD_STATUS_BSY | HD_STATUS_DRQ)) == 0)
+//         {
+//             break;
+//         }
+//     }
+// #endif
+
+//     outb(0x00, HD_CHL0_CTL_BASE);  // Device Control
+
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_FEATURES);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_NSECTOR);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAL);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAM);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAH);
+
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_FEATURES);
+//     outb(0x01, HD_CHL0_CMD_BASE + HD_NSECTOR);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAL);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAM);
+//     outb(0x00, HD_CHL0_CMD_BASE + HD_LBAH);
+
+//     outb(0x40, HD_CHL0_CMD_BASE + HD_DEVICE);
+
+//     outb(HD_CMD_READ_DMA_EXT, HD_CHL0_CMD_BASE + HD_CMD);
+
+//     inb(drv.bus_cmd);
+//     inb(drv.bus_status);
+//     unsigned short w = inb(drv.bus_cmd);
+//     outb(w | PCI_IDE_CMD_WRITE | PCI_IDE_CMD_START, drv.bus_cmd);
+//     inb(drv.bus_cmd);
+//     inb(drv.bus_status);
+// }
+
+// typedef struct {
+//     u8_t a;
+//     u8_t b;
+//     u16_t lbah;  // lba high
+//     u8_t type;
+//     u8_t f;
+//     u16_t scnth;  // sector count high
+//     u32_t lba;    // lba low
+//     u32_t scnt;   // sector count
+// } hd_part_t;
+
+// void ide_read_extended_partition(u64_t lba, unsigned int inx) {
+//     if (inx >= MAX_SUPPORT_PARTITION_CNT) return;
+
+//     unsigned int i;
+//     char *buf = kmalloc(512, 0);
+//     if (buf == 0) panic("no memory");
+
+//     ide_do_read(lba, 1, buf);
+
+//     u16_t sig = *((u16_t *)(buf + 510));
+//     if (sig != 0xAA55) panic("bad partition sect");
+
+//     hd_part_t *p = (hd_part_t *)(buf + PARTITION_TABLE_OFFSET);
+//     printd("%s:%d lba %d \n", __func__, __LINE__, lba);
+
+//     for (i = 0; i < PARTITION_CNT; ++i, ++p) {
+//         if (p->type == 0) continue;
+
+//         // u64_t   part_lba = lba + (p->lba|((p->lbah*1ULL)<<32));
+//         // u64_t   part_scnt= p->scnt | ((p->scnth*1ULL)<<32);
+//         u64_t part_lba = lba + p->lba;
+//         u64_t part_scnt = p->scnt;
+
+//         if (p->type != 0x05) {
+//             drv.part[inx].lba_start = part_lba;
+//             drv.part[inx].lba_end = part_lba + part_scnt;
+//             printk("  logic partition[%02d] [%02x] LBA base %10d end %10d\n", inx, p->type,
+//                    (unsigned int)(drv.part[inx].lba_start), (unsigned int)(drv.part[inx].lba_end - 1));
+//         } else {
+//             part_lba = drv.ext_lba_base + p->lba;
+//             printk("        extended      [%02x] LBA base %10d end %10d\n", p->type, (unsigned int)(part_lba),
+//                    (unsigned int)(part_lba + part_scnt - 1));
+//             ide_read_extended_partition(part_lba, inx + 1);
+//         }
+//     }
+
+//     kfree(buf);
+// }
+
+// void ide_read_partition() {
+//     printk("reading partitions....\n");
+//     unsigned int i;
+//     char *buf = kmalloc(512, 0);
+//     if (buf == 0) panic("no memory");
+
+//     ide_do_read(0, 1, buf);
+
+//     u16_t sig = *((u16_t *)(buf + 510));
+//     if (sig != 0xAA55) panic("bad partition sect");
+
+//     hd_part_t *p = (hd_part_t *)(buf + PARTITION_TABLE_OFFSET);
+
+//     unsigned int ext_inx = ~0U;
+
+//     for (i = 0; i < PARTITION_CNT; ++i, ++p) {
+//         if (p->type == 0) continue;
+
+//         // u64_t   part_lba = p->lba|((p->lbah*1ULL)<<32);
+//         // u64_t   part_scnt= p->scnt | ((p->scnth*1ULL)<<32);
+//         u64_t part_lba = p->lba;
+//         u64_t part_scnt = p->scnt;
+
+//         drv.part[i].lba_start = part_lba;
+//         drv.part[i].lba_end = part_lba + part_scnt;
+
+//         if (p->type == 0x05) {
+//             if (drv.ext_lba_base == 0) {
+//                 drv.ext_lba_base = drv.part[i].lba_start;
+//                 ext_inx = i;
+//             }
+//         }
+
+//         printk("primary partition[%02d] [%02x] LBA base %10d end %10d\n", i, p->type, (unsigned int)(part_lba),
+//                (unsigned int)(part_lba + part_scnt - 1));
+//     }
+
+//     kfree(buf);
+
+//     if (ext_inx != ~0U) ide_read_extended_partition(drv.part[ext_inx].lba_start, 4);
+// }
+
+// u16 ide_identify_buf[256];
+
+// static void ata_io_wait() {
+//     for (int i = 0; i < 128; i++) {
+//         inb(REG_CTL(0));
+//     }
+// }
+
+// // https://wiki.osdev.org/ATA_PIO_Mode
+// // To use the IDENTIFY command, select a target drive by sending 0xA0 for the master drive, or 0xB0 for the
+// slave,
+// // to the "drive select" IO port. On the Primary bus, this would be port 0x1F6. Then set the Sectorcount, LBAlo,
+// // LBAmid, and LBAhi IO ports to 0 (port 0x1F2 to 0x1F5). Then send the IDENTIFY command (0xEC) to the Command IO
+// // port (0x1F7).
+// // Then read the Status port (0x1F7) again. If the value read is 0, the drive does not exist. For any
+// // other value: poll the Status port (0x1F7) until bit 7 (BSY, value = 0x80) clears. Because of some ATAPI drives
+// // that do not follow spec, at this point you need to check the LBAmid and LBAhi ports (0x1F4 and 0x1F5) to see
+// if
+// // they are non-zero. If so, the drive is not ATA, and you should stop polling. Otherwise, continue polling one
+// of
+// // the Status ports until bit 3 (DRQ, value = 8) sets, or until bit 0 (ERR, value = 1) sets. At that point, if
+// ERR
+// // is clear, the data is ready to read from the Data port (0x1F0). Read 256 16-bit values, and store them.
+// //
+// // ATAPI的情况暂时不用考虑,因为不是硬盘相关的
+// // https://wiki.osdev.org/ATAPI
+// // ATAPI refers to devices that use the Packet Interface of the ATA6 (or higher) standard command set. It is
+// // basically a way to issue SCSI commands to a CD-ROM, CD-RW, DVD, or tape drive, attached to the ATA bus.
+// //
+// // 总结来说,仅考虑ATA硬盘的情况
+// // 一个IDE接口能接Master、Slave两个DRIVE。
+// // 一个PC机上通常有两个IDE接口(IDE0, IDE1或ATA0, ATA1),通常称通道0、1
+// //
+// 对于同一个IDE通道的两个DRIVE,共享同一组寄存器,它们之间的区分是通过Device寄存器的第4个bit位来实现的。0为Master,1为Slave
+// //
+// // 使用IDENTIFY命令步骤:
+// //  1. 选择DRIVE,发送0xA0选择master,发送0xB0选择slave。(发送 0xE0 | (drive << 4)到Device寄存器)
+// //  2. 发送0到该DRIVE所在通道的寄存器NSECTOR, LBAL, LBAM, LBAH
+// //  3. 发送IDENTIFY(0xEC)命令到该通道的命令寄存器
+// // 检查status寄存器:
+// //  1. 若为0,就认为没有IDE
+// //  2. 等到status的BSY位清除
+// //  3. 等到status的DRQ位或ERR位设置
+// void ide_read_identify() {
+//     int dev = 0;  // 这里所用的dev是逻辑编号 ATA0、ATA1下的Master、Salve的dev分别为0,1,2,3
+//     // outb(0xE0 | ((dev & 0x01) << 4), REG_DEVICE(dev));  // 这里可也可以发送(0xA0 | ((dev & 0x0ls1) << 4))
+//     outb(0x00 | ((dev & 0x01) << 4), REG_DEVICE(dev));  // 这里可也可以发送(0xA0 | ((dev & 0x01) << 4))
+//     outb(0x00, REG_NSECTOR(0));
+//     outb(0x00, REG_LBAL(0));
+//     outb(0x00, REG_LBAM(0));
+//     outb(0x00, REG_LBAH(0));
+//     outb(HD_CMD_IDENTIFY, REG_CMD(dev));
+//     while (true) {
+//         u8_t status = inb(REG_STATUS(0));
+//         if (status == 0) {
+//             panic("no hard drive");
+//         }
+//         u8_t error = inb(REG_ERR(0));
+//         printk("hd0 status: %x %x %x\n", status, error, REG_STATUS(0));
+//         if ((status & HD_STATUS_BSY) == 0 && (status & HD_STATUS_DRQ) != 0) {
+//             break;
+//         }
+//     }
+
+//     insw(REG_DATA(0), ide_identify_buf, 256);
+
+//     // 第83个word(2bytes)的第10个bit位表示是否支持LBA48,为1表示支持。
+
+//     for (int i = 0; i < 256; i++) {
+//         if (i % 12 == 0) {
+//             printk("\n%d ", i);
+//         }
+//         printk("%04x ", ide_identify_buf[i]);
+//     }
+
+//     struct iden_info {
+//         int idx;
+//         int len;
+//         char *desc;
+//     } infos[] = {{10, 20, "HD SN"}, {17, 8, "Firmware Revision"}, {27, 40, "HD Model"}};
+
+//     u16 *hdinfo = (u16 *)ide_identify_buf;
+//     char s[64];
+//     for (int i = 0; i < sizeof(infos) / sizeof(infos[0]); i++) {
+//         char *p = (char *)&hdinfo[infos[i].idx];
+//         int j = 0;
+//         for (j = 0; j < infos[i].len / 2; j++) {
+//             s[j * 2 + 1] = *p++;
+//             s[j * 2] = *p++;
+//         }
+//         s[j] = 0;
+//         printk("%s: %s\n", infos[i].desc, s);
+//     }
+// }
+
+// void ide_detect() {
+//     // outb(HD_CTL_SRST, REG_CTL(0));
+//     outb(0xA0 | 0x00, REG_DEVICE(dev));
+//     ata_io_wait();
+
+//     unsigned cl = inb(REG_LBAM(0));
+//     ata_io_wait();
+//     unsigned ch = inb(REG_LBAH(0));
+//     ata_io_wait();
+//     printk("%02x %02x\n", cl, ch);
+// }
+
+void ata_read_identify(int dev);
 void ide_init() {
-    memset((void *)&drv, 0, sizeof(drv));
+    // memset((void *)&drv, 0, sizeof(drv));
+
+    // init_pci_controller(0x0106);
+    // init_pci_controller(0x0101);
 
-    init_pci_controller(0x0106);
-    init_pci_controller(0x0101);
+    // ide_detect();
+    // return;
+    // ide_read_identify();
+    ata_read_identify(0);
+    return;
 
-    ide_read_partition();
+    // // 还没开启中断
+    // ide_read_partition();
 
-    ide_printl();
+    // ide_printl();
 }
index 4859929a2a489160a16878d629a82428e593858d..66b4e4e6f8228668dfaa9c5b99711171db9b7e7d 100644 (file)
 
 #pragma once
 
-#include <system.h>
-
-extern unsigned int HD_CHL0_CMD_BASE;
-extern unsigned int HD_CHL1_CMD_BASE;
-extern unsigned int HD_CHL0_CTL_BASE;
-extern unsigned int HD_CHL1_CTL_BASE;
-
-#define HD_DATA 0
-#define HD_FEATURES 1
-#define HD_ERR 1
-#define HD_ERR_BB 0x80
-#define HD_ERR_ECC 0x40
-#define HD_ERR_ID 0x10
-#define HD_ERR_AC 0x04
-#define HD_ERR_TK 0x02
-#define HD_ERR_DM 0x01
-#define HD_NSECTOR 2
-#define HD_LBAL 3
-#define HD_LBAM 4
-#define HD_LBAH 5
-#define HD_DEVSEL 6
-#define HD_CMD 7
-#define HD_STATUS 7              /* controller status */
-#define HD_STATUS_BSY 0x80       /* controller busy */
-#define HD_STATUS_RDY 0x40       /* drive ready */
-#define HD_STATUS_WF 0x20        /* write fault */
-#define HD_STATUS_SEEK_CMPT 0x10 /* seek complete */
-#define HD_STATUS_DRQ 0x08       /* data transfer request */
-#define HD_STATUS_CRD 0x04       /* correct data */
-#define HD_STATUS_IDX 0x02       /* index pulse */
-#define HD_STATUS_ERR 0x01       /* error */
-
-#define HD_CMD_IDLE 0x00
-#define HD_CMD_RECALIBRATE 0x10
-#define HD_CMD_READ_PIO 0x20     /* read data */
-#define HD_CMD_READ_PIO_EXT 0x24 /* read data (LBA-48 bit)*/
-#define HD_CMD_READ_DMA 0xC8
-#define HD_CMD_READ_DMA_EXT 0x25 /* read data DMA LBA48 */
-#define HD_CMD_WRITE_PIO 0x30
-#define HD_CMD_WRITE_PIO_EXT 0x34
-#define HD_CMD_WRITE_DMA 0xCA
-#define HD_CMD_WRITE_DMA_EXT 0X35
-#define HD_CMD_READ_VERIFY 0x40
-#define HD_CMD_FORMAT 0x50
-#define HD_CMD_SEEK 0x70
-#define HD_CMD_DIAG 0x90
-#define HD_CMD_SPECIFY 0x91
-#define HD_CMD_IDENTIFY_PACKET 0xA1
-#define HD_CMD_IDENTIFY 0xEC
-
-#define HD_CTL 0
-#define HD_CTL_HOB 0x80 /* high order byte (LBA-48bit) */
-//#define     HD_CTL_NOECC        0x40  /* disable ecc retry */
-//#define     HD_CTL_EIGHTHEADS   0x08  /* more than 8 heads */
-#define HD_CTL_SRST 0x04 /* soft reset controller */
-#define HD_CTL_NIEN 0x02 /* disable interrupts */
-
-#define HD_GET_CHL(dev) (0) /* only support channel 0 */
-#define HD_GET_DEV(dev) (0) /* only support one hard disk */
-
-#define REG_CMD_BASE(dev, offset) (HD_GET_CHL(dev) ? (HD_CHL1_CMD_BASE + offset) : (HD_CHL0_CMD_BASE + offset))
-#define REG_CTL_BASE(dev, offset) (HD_GET_CHL(dev) ? (HD_CHL1_CTL_BASE + offset) : (HD_CHL0_CTL_BASE + offset))
-
-#define REG_DATA(dev) REG_CMD_BASE(dev, HD_DATA)
-#define REG_ERR(dev) REG_CMD_BASE(dev, HD_ERR)
-#define REG_NSECTOR(dev) REG_CMD_BASE(dev, HD_NSECTOR)
-#define REG_LBAL(dev) REG_CMD_BASE(dev, HD_LBAL)
-#define REG_LBAM(dev) REG_CMD_BASE(dev, HD_LBAM)
-#define REG_LBAH(dev) REG_CMD_BASE(dev, HD_LBAH)
-#define REG_DEVSEL(dev) REG_CMD_BASE(dev, HD_DEVSEL)
-#define REG_STATUS(dev) REG_CMD_BASE(dev, HD_STATUS)
-#define REG_FEATURES(dev) REG_CMD_BASE(dev, HD_FEATURES)
-#define REG_CMD(dev) REG_CMD_BASE(dev, HD_CMD)
-#define REG_CTL(dev) REG_CTL_BASE(dev, HD_CTL)
-
-#define SECT_SIZE 512
-
-#define hd_rd_data(dev, buf, count) hd_rd_port(REG_DATA(dev), buf, count)
-
-#define hd_bsy(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_BSY))
-#define hd_rdy(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_RDY))
-#define hd_drq(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_DRQ))
-#define hd_err(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_ERR))
-
-#define ATA_IDENT_DEVTYPE 0
-#define ATA_IDENT_CYLINDERS 2
-#define ATA_IDENT_HEADS 6
-#define ATA_IDENT_SECTORS 12
-#define ATA_IDENT_SERIAL 20
-#define ATA_IDENT_MODEL 54
-#define ATA_IDENT_CAPABILITIES 98
-#define ATA_IDENT_FIELDVALID 106
-#define ATA_IDENT_MAX_LBA 120
-#define ATA_IDENT_COMMANDSETS 164
-#define ATA_IDENT_MAX_LBA_EXT 200
-
-#define PCI_IDE_CMD 0
-#define PCI_IDE_CMD_STOP 0x00
-#define PCI_IDE_CMD_READ 0x00
-#define PCI_IDE_CMD_START 0x01
-#define PCI_IDE_CMD_WRITE 0x08
-#define PCI_IDE_STATUS 2
-#define PCI_IDE_STATUS_ACT 0x01
-#define PCI_IDE_STATUS_ERR 0x02
-#define PCI_IDE_STATUS_INTR 0x04
-#define PCI_IDE_STATUS_DRV0 0x20
-#define PCI_IDE_STATUS_DRV1 0x40
-#define PCI_IDE_STATUS_SIMPLEX 0x80
-#define PCI_IDE_PRDT 4
-
-#define PARTITION_CNT 4
-#define PARTITION_TABLE_OFFSET 0x1BE
-#define MAX_SUPPORT_PARTITION_CNT 16
-
-typedef struct {
-    u64_t lba_start;
-    u64_t lba_end;
-} part_t;
-
-void ide_do_read(u64_t lba, u32_t scnt, char *buf);
-part_t *ide_get_part(dev_t dev);
+// #include <system.h>
+
+// extern unsigned int HD_CHL0_CMD_BASE;
+// extern unsigned int HD_CHL1_CMD_BASE;
+
+// // CTL其实不用BASE,只有一个寄存器
+// // 这么写纯粹是为了代码好看
+// // DEVICE CONTROL REGISTER
+// // bit7: HOB    High Order Byte (defined by 48-bit Address feature set).
+// // bit[3-6]: -
+// // bit2: SRST   Software Reset
+// // bit1: IEN    Interrupt Enable
+// // bit0: 0
+// extern unsigned int HD_CHL0_CTL_BASE;
+// extern unsigned int HD_CHL1_CTL_BASE;
+
+// #define HD_DATA 0
+// #define HD_FEATURES 1
+// #define HD_ERR 1
+// #define HD_ERR_BB 0x80
+// #define HD_ERR_ECC 0x40
+// #define HD_ERR_ID 0x10
+// #define HD_ERR_AC 0x04
+// #define HD_ERR_TK 0x02
+// #define HD_ERR_DM 0x01
+// #define HD_NSECTOR 2
+// #define HD_LBAL 3
+// #define HD_LBAM 4
+// #define HD_LBAH 5
+
+// // DEVICE寄存器
+// // bit7: 1
+// // bit6: L 如果为1,LBA Mode
+// // bit5: 1
+// // bit4: DRIVE
+// // bit[0, 3] HS 如果L为0就是磁头号Head Number,如果L为1,则为LBA的24-27位
+// #define HD_DEVICE 6
+
+// #define HD_CMD 7
+
+// // bit7: BSY Busy. If BSY==1, no other bits in the register are valid
+// // bit6: DRDY Drive Ready.
+// // bit5: DF/SE Device Fault / Stream Error
+// // bit4: # Command dependent. (formerly DSC bit)
+// // bit3: DRQ Data Request. (ready to transfer data)
+// // bit2: - Obsolete
+// // bit1: - Obsolete
+// // bit0: ERR
+// #define HD_STATUS 7              /* controller status */
+// #define HD_STATUS_BSY 0x80       /* controller busy */
+// #define HD_STATUS_RDY 0x40       /* drive ready */
+// #define HD_STATUS_WF 0x20        /* write fault */
+// #define HD_STATUS_SEEK_CMPT 0x10 /* seek complete */
+// #define HD_STATUS_DRQ 0x08       /* data transfer request */
+// #define HD_STATUS_CRD 0x04       /* correct data */
+// #define HD_STATUS_IDX 0x02       /* index pulse */
+// #define HD_STATUS_ERR 0x01       /* error */
+
+// #define HD_CMD_IDLE 0x00
+// #define HD_CMD_RECALIBRATE 0x10
+// #define HD_CMD_READ_PIO 0x20     /* read data */
+// #define HD_CMD_READ_PIO_EXT 0x24 /* read data (LBA-48 bit)*/
+// #define HD_CMD_READ_DMA 0xC8
+// #define HD_CMD_READ_DMA_EXT 0x25 /* read data DMA LBA48 */
+// #define HD_CMD_WRITE_PIO 0x30
+// #define HD_CMD_WRITE_PIO_EXT 0x34
+// #define HD_CMD_WRITE_DMA 0xCA
+// #define HD_CMD_WRITE_DMA_EXT 0X35
+// #define HD_CMD_READ_VERIFY 0x40
+// #define HD_CMD_FORMAT 0x50
+// #define HD_CMD_SEEK 0x70
+// #define HD_CMD_DIAG 0x90
+// #define HD_CMD_SPECIFY 0x91
+// #define HD_CMD_IDENTIFY_PACKET 0xA1
+// #define HD_CMD_IDENTIFY 0xEC
+
+// #define HD_CTL 0
+// #define HD_CTL_HOB 0x80 /* high order byte (LBA-48bit) */
+// //#define     HD_CTL_NOECC        0x40  /* disable ecc retry */
+// //#define     HD_CTL_EIGHTHEADS   0x08  /* more than 8 heads */
+// #define HD_CTL_SRST 0x04 /* soft reset controller */
+// #define HD_CTL_NIEN 0x02 /* disable interrupts */
+
+// #define HD_GET_CHL(dev) (0) /* only support channel 0 */
+// #define HD_GET_DEV(dev) (0) /* only support one hard disk */
+
+// #define REG_CMD_BASE(dev, offset) (HD_GET_CHL(dev) ? (HD_CHL1_CMD_BASE + offset) : (HD_CHL0_CMD_BASE + offset))
+// #define REG_CTL_BASE(dev, offset) (HD_GET_CHL(dev) ? (HD_CHL1_CTL_BASE + offset) : (HD_CHL0_CTL_BASE + offset))
+
+// #define REG_DATA(dev) REG_CMD_BASE(dev, HD_DATA)
+// #define REG_ERR(dev) REG_CMD_BASE(dev, HD_ERR)
+// #define REG_NSECTOR(dev) REG_CMD_BASE(dev, HD_NSECTOR)
+// #define REG_LBAL(dev) REG_CMD_BASE(dev, HD_LBAL)
+// #define REG_LBAM(dev) REG_CMD_BASE(dev, HD_LBAM)
+// #define REG_LBAH(dev) REG_CMD_BASE(dev, HD_LBAH)
+// #define REG_DEVICE(dev) REG_CMD_BASE(dev, HD_DEVICE)
+// #define REG_STATUS(dev) REG_CMD_BASE(dev, HD_STATUS)
+// #define REG_FEATURES(dev) REG_CMD_BASE(dev, HD_FEATURES)
+
+// #define REG_CMD(dev) REG_CMD_BASE(dev, HD_CMD)
+// #define REG_CTL(dev) REG_CTL_BASE(dev, HD_CTL)
+
+// #define SECT_SIZE 512
+
+// #define hd_rd_data(dev, buf, count) hd_rd_port(REG_DATA(dev), buf, count)
+
+// #define hd_bsy(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_BSY))
+// #define hd_rdy(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_RDY))
+// #define hd_drq(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_DRQ))
+// #define hd_err(dev) ((inb(REG_STATUS(dev)) & HD_STATUS_ERR))
+
+// #define ATA_IDENT_DEVTYPE 0
+// #define ATA_IDENT_CYLINDERS 2
+// #define ATA_IDENT_HEADS 6
+// #define ATA_IDENT_SECTORS 12
+// #define ATA_IDENT_SERIAL 20
+// #define ATA_IDENT_MODEL 54
+// #define ATA_IDENT_CAPABILITIES 98
+// #define ATA_IDENT_FIELDVALID 106
+// #define ATA_IDENT_MAX_LBA 120
+// #define ATA_IDENT_COMMANDSETS 164
+// #define ATA_IDENT_MAX_LBA_EXT 200
+
+// #define PCI_IDE_CMD 0
+// #define PCI_IDE_CMD_STOP 0x00
+// #define PCI_IDE_CMD_READ 0x00
+// #define PCI_IDE_CMD_START 0x01
+// #define PCI_IDE_CMD_WRITE 0x08
+// #define PCI_IDE_STATUS 2
+// #define PCI_IDE_STATUS_ACT 0x01
+// #define PCI_IDE_STATUS_ERR 0x02
+// #define PCI_IDE_STATUS_INTR 0x04
+// #define PCI_IDE_STATUS_DRV0 0x20
+// #define PCI_IDE_STATUS_DRV1 0x40
+// #define PCI_IDE_STATUS_SIMPLEX 0x80
+// #define PCI_IDE_PRDT 4
+
+// #define PARTITION_CNT 4
+// #define PARTITION_TABLE_OFFSET 0x1BE
+// #define MAX_SUPPORT_PARTITION_CNT 16
+
+// typedef struct {
+//     u64_t lba_start;
+//     u64_t lba_end;
+// } part_t;
+
+// void ide_do_read(u64_t lba, u32_t scnt, char *buf);
+// part_t *ide_get_part(dev_t dev);
index 098502c964bc21fd823bf2da86df8f5eca68aa1d..56b368ccfd696a4a546d1a286d7f88cc00ceb4c2 100644 (file)
@@ -29,7 +29,7 @@ void ide_status();
 void debug_sched();
 void vga_dbg_toggle();
 int debug_wait_queue_put(unsigned int v);
-void ide_dma_pci_lba48();
+// void ide_dma_pci_lba48();
 void vga_switch(unsigned int nr);
 
 void kbd_debug(unsigned char scan_code);
@@ -99,10 +99,10 @@ void kbd_debug(unsigned char scan_code) {
     if (scan_code == 0x42)  // F8
         debug_wait_queue_put(7);
 
-    if (scan_code == 0x43)  // F9
-        ide_dma_pci_lba48();
-    if (scan_code == 0x44)  // F10
-        ide_debug();
+    // if (scan_code == 0x43)  // F9
+    //     ide_dma_pci_lba48();
+    // if (scan_code == 0x44)  // F10
+    //     ide_debug();
     if (scan_code == 0x57)  // F11
     {
         asm("cli;");
index 81c4a657de8107f95a2a2c49ac5275768e8a7a46..5ade79606b49ee994eb9fc286a8e66e1ea7e623e 100644 (file)
@@ -59,13 +59,15 @@ void scan_pci_bus(int bus) {
     u32 cmd;
     u32 v;
     int i;
-    printk("scanning pci bus %d\n", bus);
+    // printk("scanning pci bus %d\n", bus);
 
     for (dev = 0; dev < 32; dev++) {
         for (devfn = 0; devfn < 8; devfn++) {
             cmd = PCI_CMD(bus, dev, devfn, PCI_VENDORID);
             v = pci_read_config_word(cmd);
-            if (v == 0xFFFF) continue;
+            if (v == 0xFFFF) {
+                continue;
+            }
 
             pci_device_t *pci = kmalloc(sizeof(pci_device_t), 0);
             if (0 == pci) {
@@ -167,10 +169,10 @@ void dump_pci_dev() {
             break;
         }
 #else
-        for (int bar_inx = 0; bar_inx < BARS_CNT; bar_inx++) {
-            printk("%08x ", pci->bars[bar_inx]);
-        }
-        printk("\n");
+        // for (int bar_inx = 0; bar_inx < BARS_CNT; bar_inx++) {
+        //     printk("%08x ", pci->bars[bar_inx]);
+        // }
+        // printk("\n");
 #endif
     }
 }
index 8a9d81d612959b90cd1d694d37db146e7989cb2e..1c72a35cb9fc3b5195055148456e27aaad6df779 100644 (file)
@@ -84,6 +84,9 @@ void setup_kernel() {
     setup_irqs();
 
     setup_pci();
+
+    void ide_init();
+    ide_init();
     asm("cli;hlt;");
     extern tty_t monitor_tty;
     // tty_switch(&monitor_tty);
@@ -97,8 +100,6 @@ void setup_kernel() {
 
     // switch_printk_screen();
     system_delay();
-    void ide_init();
-    ide_init();
 
     system_delay();