Esempio n. 1
0
void keyboard_intr(uint8_t scancode) {
    if(nemu_state == RUNNING && newkey == false) {
        i8042_data_port_base[0] = scancode;
        i8259_raise_intr(KEYBOARD_IRQ);
        newkey = true;
    }
}
Esempio n. 2
0
void ide_io_handler(ioaddr_t addr, size_t len, bool is_write) {
    assert(byte_cnt <= 512);
    if(is_write) {
        if(addr - IDE_PORT == 0 && len == 4) {
            assert(ide_write);
            fwrite(ide_port_base, 4, 1, disk_fp);

            byte_cnt += 4;
            if(byte_cnt == 512) {
                ide_port_base[7] = 0x40;
                i8259_raise_intr(IDE_IRQ);
            }
        }
        else if(addr - IDE_PORT == 7) {
            sector = (ide_port_base[6] & 0x1f) << 24 | ide_port_base[5] << 16
                | ide_port_base[4] << 8 | ide_port_base[3];
            disk_idx = sector << 9;
            fseek(disk_fp, disk_idx, SEEK_SET);

            byte_cnt = 0;

            if(ide_port_base[7] == 0x20) {
                ide_write = false;
                fread(ide_port_base, 4, 1, disk_fp);
                ide_port_base[7] = 0x40;
                i8259_raise_intr(IDE_IRQ);
            }
            else if(ide_port_base[7] == 0x30) {
                ide_write = true;
            }
            else {
                assert(0);
            }
        }
    }
    else {
        printf("ide read: addr %x, len %x\n", addr, len);
        if(addr - IDE_PORT == 0 && len == 4) {
            assert(!ide_write);
            fread(ide_port_base, 4, 1, disk_fp);
            byte_cnt += 4;
            if(byte_cnt == 512) {
                ide_port_base[7] = 0x40;
            }
        }
    }
}
Esempio n. 3
0
void bmr_io_handler(ioaddr_t addr, size_t len, bool is_write) {
	int ret;
	if(is_write) {
		if(addr - BMR_PORT == 0) {
			if(bmr_base[0] & 0x1) {
				/* DMA start command */
				if(bmr_base[0] & 0x8) {
					/* DMA read */

					/* the address of Physical Region Descriptor Table */
					hwaddr_t prdt_addr = *(uint32_t *)(bmr_base + 4);

					hwaddr_t addr = hwaddr_read(prdt_addr, 4);
					uint32_t hi_entry = hwaddr_read(prdt_addr + 4, 4);
					uint16_t byte_cnt = hi_entry & 0xffff;

					sector = (ide_port_base[6] & 0x1f) << 24 | ide_port_base[5] << 16
						| ide_port_base[4] << 8 | ide_port_base[3];
					disk_idx = sector << 9;
					fseek(disk_fp, disk_idx, SEEK_SET);

					ret = fread((void *)hwa_to_va(addr), byte_cnt, 1, disk_fp);
					assert(ret == 1|| feof(disk_fp));

					/* We only implement PRDT of single entry. */
					assert(hi_entry & 0x80000000);

					/* finish */
					ide_port_base[7] = 0x40;
					i8259_raise_intr(IDE_IRQ);
				}
				else {
					/* DMA write is not implemented */
					assert(0);
				}
			}
		}
	}
}
Esempio n. 4
0
void ide_io_handler(ioaddr_t addr, size_t len, bool is_write) {
	assert(byte_cnt <= 512);
	int ret;
	if(is_write) {
		if(addr - IDE_PORT == 0 && len == 4) {
			/* write 4 bytes data to disk */
			assert(ide_write);
			ret = fwrite(ide_port_base, 4, 1, disk_fp);
			assert(ret == 1);

			byte_cnt += 4;
			if(byte_cnt == 512) {
				/* finish */
				ide_port_base[7] = 0x40;
			}
		}
		else if(addr - IDE_PORT == 7) {
			if(ide_port_base[7] == 0x20 || ide_port_base[7] == 0x30) {
				/* command: read/write */
				sector = (ide_port_base[6] & 0x1f) << 24 | ide_port_base[5] << 16
					| ide_port_base[4] << 8 | ide_port_base[3];
				disk_idx = sector << 9;
				fseek(disk_fp, disk_idx, SEEK_SET);

				byte_cnt = 0;

				if(ide_port_base[7] == 0x20) {
					/* command: read from disk */
					ide_write = false;
					//ret = fread(ide_port_base, 4, 1, disk_fp);
					//assert(ret == 1);
					ide_port_base[7] = 0x40;
					i8259_raise_intr(IDE_IRQ);
				}
				else {
					/* command: write to disk */
					ide_write = true;
				}
			}
			else if (ide_port_base[7] == 0xc8) {
				/* command: DMA read */

				/* Nothing to do here. The actual read operation is
				 * issued by write commands to the bus master register. */
			}
			else {
				/* not implemented command */
				assert(0);
			}
		}
	}
	else {
		if(addr - IDE_PORT == 0 && len == 4) {
			/* read 4 bytes data from disk */
			assert(!ide_write);
			ret = fread(ide_port_base, 4, 1, disk_fp);
			assert(ret == 1|| feof(disk_fp));

			byte_cnt += 4;
			if(byte_cnt == 512) {
				/* finish */
				ide_port_base[7] = 0x40;
			}
		}
	}
}