Skip to main content

arm_gic_driver/
lib.rs

1#![no_std]
2
3//! # ARM GIC Driver
4//!
5//! A driver for the ARM Generic Interrupt Controller (GIC).
6//!
7//! ## Platform Support
8//!
9//! This driver is designed for ARM AArch64 systems and provides:
10//!
11//! - **GICv2 support**: Available on both 32-bit and 64-bit ARM platforms
12//! - **GICv3 support**: Only available on 64-bit ARM (AArch64) platforms
13//! - **System Register access**: Only available on AArch64 platforms
14//!
15//! ### Platform-Specific Modules
16//!
17//! - The [`v3`] module is **only available on AArch64** (`target_arch = "aarch64"`)
18//!
19//! If you're working on a non-ARM platform, most of this driver's functionality
20//! will not be available at compile time.
21
22pub(crate) mod define;
23pub mod sys_reg;
24
25#[cfg(test)]
26mod tests;
27mod version;
28
29use core::{
30    fmt::{Debug, Display},
31    ptr::NonNull,
32};
33
34pub use define::IntId;
35pub use version::*;
36
37/// Virtual address wrapper for memory-mapped register access.
38///
39/// This type provides a safe wrapper around virtual addresses used for accessing
40/// memory-mapped registers in the GIC. It ensures type safety while allowing
41/// efficient pointer operations.
42///
43/// # Examples
44///
45/// ```no_run
46/// use arm_gic_driver::VirtAddr;
47///
48/// let addr = VirtAddr::new(0xF900_0000);
49/// let ptr: *mut u32 = addr.as_ptr();
50/// ```
51#[repr(transparent)]
52#[derive(Copy, Clone, Debug, Eq, PartialEq)]
53pub struct VirtAddr(usize);
54
55impl VirtAddr {
56    /// Create a new `VirtAddr` from a raw address value.
57    ///
58    /// # Arguments
59    ///
60    /// * `val` - The virtual address as a usize value
61    ///
62    /// # Examples
63    ///
64    /// ```
65    /// use arm_gic_driver::VirtAddr;
66    ///
67    /// let addr = VirtAddr::new(0xF900_0000);
68    /// ```
69    pub const fn new(val: usize) -> Self {
70        Self(val)
71    }
72
73    /// Get the virtual address as a raw pointer of the specified type.
74    ///
75    /// # Type Parameters
76    ///
77    /// * `T` - The target pointer type
78    ///
79    /// # Returns
80    ///
81    /// A raw mutable pointer to type `T`
82    ///
83    /// # Safety
84    ///
85    /// The caller must ensure that:
86    /// - The address is valid for the target type `T`
87    /// - The memory region is properly mapped and accessible
88    /// - Appropriate synchronization is used for concurrent access
89    ///
90    /// # Examples
91    ///
92    /// ```no_run
93    /// use arm_gic_driver::VirtAddr;
94    ///
95    /// let addr = VirtAddr::new(0xF900_0000);
96    /// let ptr: *mut u32 = addr.as_ptr();
97    /// ```
98    pub const fn as_ptr<T>(&self) -> *mut T {
99        self.0 as *mut T
100    }
101}
102
103impl From<usize> for VirtAddr {
104    fn from(addr: usize) -> Self {
105        Self(addr)
106    }
107}
108
109impl From<VirtAddr> for usize {
110    fn from(addr: VirtAddr) -> Self {
111        addr.0
112    }
113}
114
115impl From<*mut u8> for VirtAddr {
116    fn from(addr: *mut u8) -> Self {
117        Self(addr as usize)
118    }
119}
120
121impl<T> From<NonNull<T>> for VirtAddr {
122    fn from(addr: NonNull<T>) -> Self {
123        Self(addr.as_ptr() as usize)
124    }
125}
126
127impl Display for VirtAddr {
128    fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
129        write!(f, "VirtAddr({:#p})", self.0 as *const u8)
130    }
131}