Newer
Older
use core::{mem, ptr};
use redoxfs::{BLOCK_SIZE, Disk};
use crate::{DISK_ADDRESS_PACKET_ADDR, DISK_BIOS_ADDR, ThunkData};
#[derive(Clone, Copy)]
#[repr(packed)]
pub struct DiskAddressPacket {
size: u8,
reserved: u8,
blocks: u16,
buffer: u16,
segment: u16,
address: u64,
}
impl DiskAddressPacket {
pub fn from_block(block: u64) -> DiskAddressPacket {
let blocks = BLOCK_SIZE / 512;
DiskAddressPacket {
blocks: blocks as u16,
buffer: DISK_BIOS_ADDR as u16,
segment: 0,
address: block * blocks,
}
}
}
pub struct DiskBios {
pub fn new(boot_disk: u8, thunk13: extern "C" fn()) -> Self {
Self { boot_disk, thunk13 }
fn read_at(&mut self, block: u64, buffer: &mut [u8]) -> Result<usize> {
for (i, chunk) in buffer.chunks_mut(BLOCK_SIZE as usize).enumerate() {
unsafe {
let mut dap = DiskAddressPacket::from_block(block);
ptr::write(DISK_ADDRESS_PACKET_ADDR as *mut DiskAddressPacket, dap);
data.eax = 0x4200;
data.edx = self.boot_disk as u32;
data.esi = DISK_ADDRESS_PACKET_ADDR as u32;
//TODO: check blocks transferred
dap = ptr::read(DISK_ADDRESS_PACKET_ADDR as *mut DiskAddressPacket);
ptr::copy(DISK_BIOS_ADDR as *const u8, chunk.as_mut_ptr(), chunk.len());
}
fn write_at(&mut self, block: u64, buffer: &[u8]) -> Result<usize> {
log::error!(
"DiskBios::write_at(0x{:X}, 0x{:X}:0x{:X}) not allowed",
block,
buffer.as_ptr() as usize,
buffer.len()
);
Err(Error::new(EIO))
log::error!("DiskBios::size not implemented");
Err(Error::new(EIO))