diff --git a/src/capability/msi.rs b/src/capability/msi.rs index 6ec65a1..20ec305 100644 --- a/src/capability/msi.rs +++ b/src/capability/msi.rs @@ -78,7 +78,7 @@ impl MsiCapability { /// How many interrupts this device has? #[inline] - pub fn get_multiple_message_capable(&self) -> MultipleMessageSupport { + pub fn multiple_message_capable(&self) -> MultipleMessageSupport { self.multiple_message_capable } @@ -108,31 +108,45 @@ impl MsiCapability { } /// Return how many interrupts the device is using - pub fn get_multiple_message_enable(&self, access: impl ConfigRegionAccess) -> MultipleMessageSupport { + pub fn multiple_message_enable(&self, access: impl ConfigRegionAccess) -> MultipleMessageSupport { let reg = unsafe { access.read(self.address.address, self.address.offset) }; MultipleMessageSupport::try_from(reg.get_bits(4..7) as u8).unwrap_or(MultipleMessageSupport::Int1) } - /// Set where the interrupts will be sent to + /// Set the memory address that will be written to when the interrupt fires, and the data that + /// will be written to it. + pub fn set_message_info(&self, address: u64, data: u32, access: impl ConfigRegionAccess) { + unsafe { + access.write(self.address.address, self.address.offset + 0x04, address.get_bits(0..32) as u32); + if self.is_64bit { + access.write(self.address.address, self.address.offset + 0x08, address.get_bits(32..64) as u32); + } + } + let data_offset = if self.is_64bit { 0x0c } else { 0x08 }; + unsafe { + access.write(self.address.address, self.address.offset + data_offset, data); + } + } + + /// Set the memory address that will be written to when the interrupt fires, and the data that + /// will be written to it, specialised for the message format the LAPIC expects. /// /// # Arguments - /// * `address` - Target Local APIC address (if not changed, can be calculated with `0xFEE00000 | (processor << 12)`) + /// * `address` - Target Local APIC address (if not changed, can be calculated with `0xfee00000 | (processor << 12)`) /// * `vector` - Which interrupt vector should be triggered on LAPIC /// * `trigger_mode` - When interrupt should be triggered /// * `access` - PCI Configuration Space accessor - pub fn set_message_info( + pub fn set_message_info_lapic( &self, - address: u32, + address: u64, vector: u8, trigger_mode: TriggerMode, access: impl ConfigRegionAccess, ) { - unsafe { access.write(self.address.address, self.address.offset + 0x4, address) } - let data_offset = if self.is_64bit { 0xC } else { 0x8 }; - let mut data = unsafe { access.read(self.address.address, self.address.offset + data_offset) }; + let mut data = 0; data.set_bits(0..8, vector as u32); data.set_bits(14..16, trigger_mode as u32); - unsafe { access.write(self.address.address, self.address.offset + data_offset, data) } + self.set_message_info(address, data, access); } /// Get interrupt mask @@ -140,7 +154,7 @@ impl MsiCapability { /// # Note /// Only supported on when device supports 64-bit addressing and per-vector masking. Otherwise /// returns `0` - pub fn get_message_mask(&self, access: impl ConfigRegionAccess) -> u32 { + pub fn message_mask(&self, access: impl ConfigRegionAccess) -> u32 { if self.is_64bit && self.per_vector_masking { unsafe { access.read(self.address.address, self.address.offset + 0x10) } } else { @@ -153,7 +167,7 @@ impl MsiCapability { /// # Note /// Only supported on when device supports 64-bit addressing and per-vector masking. Otherwise /// will do nothing - pub fn set_message_mask(&self, access: impl ConfigRegionAccess, mask: u32) { + pub fn set_message_mask(&self, mask: u32, access: impl ConfigRegionAccess) { if self.is_64bit && self.per_vector_masking { unsafe { access.write(self.address.address, self.address.offset + 0x10, mask) } } @@ -163,7 +177,7 @@ impl MsiCapability { /// /// # Note /// Only supported on when device supports 64-bit addressing. Otherwise will return `0` - pub fn get_pending(&self, access: impl ConfigRegionAccess) -> u32 { + pub fn is_pending(&self, access: impl ConfigRegionAccess) -> u32 { if self.is_64bit { unsafe { access.read(self.address.address, self.address.offset + 0x14) } } else {