#include <irq.h>
// #include <printk.h>
+#include <semaphore.h>
#include <task.h>
-// #include <semaphore.h>
// #include <string.h>
// #include <types.h>
#include <wait.h>
// void ata_read_identify(int dev);
+#if 1
+extern semaphore_t disk_intr_sem;
+#else
DECLARE_WAIT_QUEUE_HEAD(ide_wait_queue_head);
void sleep_on_ide() { sleep_on(&ide_wait_queue_head); }
void prepare_to_wait_on_ide() { ide_pci_controller.done = 0; }
void wait_on_ide() { wait_event(&ide_wait_queue_head, ide_pci_controller.done); }
+#endif
extern void *mbr_buf;
uint8_t ata_pci_bus_status();
printk("ide irq %d handler pci status after interrupt: %x\n", irq, ata_pci_bus_status());
+#if 1
+ up(&disk_intr_sem);
+#else
ide_pci_controller.done = 1;
-
wake_up(&ide_wait_queue_head);
+#endif
}
void ide_init() {
void *buf; // 到的缓冲区
disk_request_cmd_t command; // 命令
list_head_t list;
- // wait_queue_head_t wait; // 等待队列
- // 驱动器完全有可能在进程在进程睡眠到等待队列前返回数据并执行唤醒操作
- // 这时等待队列上无进程,就相当于不执行任何操作
- // 然后进程再睡眠到等待队列上,就会造成永远无法唤醒该进程
- // 因此要添加一个字段,标志驱动器已经对该请求做过唤醒操作
- // 进程在睡眠前需要检查该字段
- // int done;
- completion_t completion;
+ // // wait_queue_head_t wait; // 等待队列
+ // // 驱动器完全有可能在进程在进程睡眠到等待队列前返回数据并执行唤醒操作
+ // // 这时等待队列上无进程,就相当于不执行任何操作
+ // // 然后进程再睡眠到等待队列上,就会造成永远无法唤醒该进程
+ // // 因此要添加一个字段,标志驱动器已经对该请求做过唤醒操作
+ // // 进程在睡眠前需要检查该字段
+ // // int done;
+ // completion_t completion;
+ semaphore_t sem;
} disk_request_t;
typedef struct {
#include <disk.h>
#include <sched.h>
-disk_request_queue_t disk_request_queue; // = {.count = 0,
- // .sem = SEMAPHORE_INITIALIZER(disk_request_queue.sem, 0),
- // .list = LIST_HEAD_INIT(disk_request_queue.list)};
+disk_request_queue_t disk_request_queue;
+
+// task disk与中断函数之间的信号量
+semaphore_t disk_intr_sem;
+
+DECLARE_MUTEX(disk_request_mutex);
void disk_init() {
disk_request_queue.count = 0;
- disk_request_queue.sem.cnt = 0;
- INIT_LIST_HEAD(&disk_request_queue.sem.wait_list);
INIT_LIST_HEAD(&disk_request_queue.list);
+ // disk_request_queue.sem.cnt = 0;
+ // INIT_LIST_HEAD(&disk_request_queue.sem.wait_list);
+ semaphore_init(&disk_request_queue.sem, 0);
+
+ semaphore_init(&disk_intr_sem, 0);
}
void send_disk_request(disk_request_t *r) {
panic("null disk request");
}
+ // 这个用来让task_disk唤醒自己
+ semaphore_init(&r->sem, 0);
+
// 校验pos,和pos+count是否大于硬盘返回的最大LBA48
// ...
panic("disk DMA read cross 64K");
}
- // INIT_LIST_HEAD(&r->wait.task_list);
- // r->done = 0;
-
- init_completion(&r->completion);
-
- // r.pos = pos;
- // r.count = count;
- // r.buf = kmalloc(512, 0);
- // r.command = DISK_REQ_IDENTIFY;
- // INIT_LIST_HEAD(&r.wait.task_list);
- // r.done = 0;
-
- // printk("do send disk request: %d %x %x %x\n", list_empty(&disk_request_queue.sem.wait_list),
- // &disk_request_queue.sem.wait_list, disk_request_queue.sem.wait_list.next,
- // disk_request_queue.sem.wait_list.prev);
-
+#if 1
+ mutex_lock(&disk_request_mutex);
+ list_add_tail(&r->list, &disk_request_queue.list);
+ mutex_unlock(&disk_request_mutex);
+#else
// 发送命令
unsigned long flags;
irq_save(flags);
list_add_tail(&r->list, &disk_request_queue.list);
irq_restore(flags);
+#endif
// 唤醒task_disk
- // printk("up sem\n");
up(&disk_request_queue.sem);
- // 等待task_dist结束
- // printk("wait event\n");
- // wait_event(&r->wait, r->done != 0);
- wait_completion(&r->completion);
-
- // printk("wait finished\n");
+ // 等待被task_disk唤醒
+ down(&r->sem);
}
void disk_task_entry() {
int r_cnt = 0;
while (1) {
- void prepare_to_wait_on_ide();
- prepare_to_wait_on_ide();
-
// printk("wait for new hard disk request\n");
down(&disk_request_queue.sem);
// printk("hard disk request: %d\n", disk_request_queue.count++);
+#if 1
+ mutex_lock(&disk_request_mutex);
+ disk_request_t *r;
+ r = list_first_entry(&disk_request_queue.list, disk_request_t, list);
+ if (NULL == r) {
+ panic("no disk request");
+ }
+
+ list_del(&r->list);
+ mutex_unlock(&disk_request_mutex);
+#else
unsigned long flags;
irq_save(flags);
disk_request_t *r;
if (list_empty(&disk_request_queue.list)) {
- } else {
- r = list_first_entry(&disk_request_queue.list, disk_request_t, list);
- if (NULL == r) {
- panic("no disk request");
- }
-
- printk("disk request[%d]: dev %d pos %ld count %d cmd %d\n", r_cnt++, r->dev, r->pos, r->count, r->command);
+ panic("disk request should not empty");
}
- irq_restore(flags);
-
+ r = list_first_entry(&disk_request_queue.list, disk_request_t, list);
if (NULL == r) {
- continue;
+ panic("no disk request");
}
+ printk("disk request[%d]: dev %d pos %ld count %d cmd %d\n", r_cnt++, r->dev, r->pos, r->count, r->command);
+ list_del(&r->list);
+ irq_restore(flags);
+#endif
+
switch (r->command) {
case DISK_REQ_IDENTIFY:
assert(r->count == 1);
}
// 等待硬盘中断
- void wait_on_ide();
- wait_on_ide();
+ down(&disk_intr_sem);
// 读数据
if (DISK_REQ_IDENTIFY == r->command) {
}
// 唤醒等待该请求的进程
- // r->done = 1;
- // wake_up(&r->wait);
- complete(&r->completion);
+ up(&(r->sem));
}
}