use core::marker::PhantomData;
pub struct WriteOnlyAccess;
pub struct ReadWriteAccess;
pub trait IoPortWriteAccess {}
pub trait IoPortReadAccess {}
impl IoPortWriteAccess for WriteOnlyAccess {}
impl IoPortWriteAccess for ReadWriteAccess {}
impl IoPortReadAccess for ReadWriteAccess {}
pub trait PortRead: Sized {
unsafe fn read_from_port(_port: u16) -> Self {
unimplemented!()
}
}
pub trait PortWrite: Sized {
unsafe fn write_to_port(_port: u16, _value: Self) {
unimplemented!()
}
}
impl PortRead for u8 {}
impl PortWrite for u8 {}
impl PortRead for u16 {}
impl PortWrite for u16 {}
impl PortRead for u32 {}
impl PortWrite for u32 {}
pub struct IoPort<T, A> {
port: u16,
value_marker: PhantomData<T>,
access_marker: PhantomData<A>,
}
impl<T, A> IoPort<T, A> {
pub const unsafe fn new(port: u16) -> Self {
Self {
port,
value_marker: PhantomData,
access_marker: PhantomData,
}
}
}
impl<T: PortRead, A: IoPortReadAccess> IoPort<T, A> {
#[inline]
pub fn read(&self) -> T {
unsafe { PortRead::read_from_port(self.port) }
}
}
impl<T: PortWrite, A: IoPortWriteAccess> IoPort<T, A> {
#[inline]
pub fn write(&self, value: T) {
unsafe { PortWrite::write_to_port(self.port, value) }
}
}