tiny_os/kernel/src/vspace/addr.rs

355 lines
7.1 KiB
Rust
Raw Normal View History

2024-03-23 16:45:24 +08:00
use core::fmt::*;
use core::hash::*;
use core::num::*;
use core::ops::*;
2023-12-12 15:10:01 +08:00
#[inline(always)]
2024-01-26 11:46:02 +08:00
pub fn align_up(addr: usize, align: usize) -> usize {
2023-12-12 15:10:01 +08:00
(addr + align - 1) & !(align - 1)
}
#[inline(always)]
2024-01-26 11:46:02 +08:00
pub fn align_down(addr: usize, align: usize) -> usize {
2023-12-12 15:10:01 +08:00
addr & !(align - 1)
}
#[derive(Copy, Clone, Default, Eq, Ord, PartialOrd, PartialEq)]
2023-12-12 15:10:01 +08:00
pub struct PhysAddr(pub usize);
#[derive(Copy, Clone, Default, Eq, Ord, PartialOrd, PartialEq)]
2023-12-12 15:10:01 +08:00
pub struct VirtAddr(pub usize);
pub trait AddressOps {
2024-01-26 11:46:02 +08:00
fn as_mut_ptr<T>(&self) -> *mut T {
self.as_usize() as *mut T
}
2023-12-12 15:10:01 +08:00
fn as_u32(&self) -> u32;
fn as_u64(&self) -> u64;
fn as_usize(&self) -> usize;
2023-12-18 00:32:36 +08:00
fn as_non_zero_usize(&self) -> Option<NonZeroUsize>;
2023-12-12 15:10:01 +08:00
fn align_up<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize>;
2023-12-12 15:10:01 +08:00
fn align_down<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize>;
2023-12-12 15:10:01 +08:00
fn is_aligned<T>(&self, align: T) -> bool
2024-02-01 19:12:56 +08:00
where T: Into<usize> + Copy {
2023-12-12 15:10:01 +08:00
if align.into().is_power_of_two() {
self.as_usize() & (align.into() - 1) == 0
} else {
false
}
}
}
impl AddressOps for PhysAddr {
fn as_u32(&self) -> u32 {
self.0 as u32
}
fn as_u64(&self) -> u64 {
self.0 as u64
}
fn as_usize(&self) -> usize {
self.0
}
2023-12-18 00:32:36 +08:00
fn as_non_zero_usize(&self) -> Option<NonZeroUsize> {
NonZeroUsize::new(self.0)
}
2023-12-12 15:10:01 +08:00
fn align_up<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize> {
2023-12-12 15:10:01 +08:00
PhysAddr(align_up(self.0, align.into()))
}
fn align_down<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize> {
2023-12-12 15:10:01 +08:00
PhysAddr(align_down(self.0, align.into()))
}
}
impl AddressOps for VirtAddr {
fn as_u32(&self) -> u32 {
self.0 as u32
}
fn as_u64(&self) -> u64 {
self.0 as u64
}
fn as_usize(&self) -> usize {
self.0
}
2023-12-18 00:32:36 +08:00
fn as_non_zero_usize(&self) -> Option<NonZeroUsize> {
NonZeroUsize::new(self.0)
}
2023-12-12 15:10:01 +08:00
fn align_up<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize> {
2023-12-12 15:10:01 +08:00
VirtAddr(align_up(self.0, align.into()))
}
fn align_down<T>(&self, align: T) -> Self
2024-02-01 19:12:56 +08:00
where T: Into<usize> {
2023-12-12 15:10:01 +08:00
VirtAddr(align_down(self.0, align.into()))
}
}
impl Add<usize> for PhysAddr {
type Output = Self;
fn add(self, rhs: usize) -> Self::Output {
Self(self.0 + rhs)
}
}
2024-01-26 11:46:02 +08:00
impl Add<PhysAddr> for PhysAddr {
type Output = Self;
fn add(self, rhs: PhysAddr) -> Self::Output {
Self(self.0 + rhs.0)
}
}
2023-12-12 15:10:01 +08:00
impl AddAssign<usize> for PhysAddr {
fn add_assign(&mut self, rhs: usize) {
*self = PhysAddr::from(self.0 + rhs);
}
}
2024-01-26 11:46:02 +08:00
impl AddAssign<PhysAddr> for PhysAddr {
fn add_assign(&mut self, rhs: PhysAddr) {
*self = PhysAddr::from(self.0 + rhs.0);
}
}
2023-12-12 15:10:01 +08:00
impl Sub<usize> for PhysAddr {
2024-01-26 11:46:02 +08:00
type Output = Self;
2023-12-12 15:10:01 +08:00
fn sub(self, rhs: usize) -> Self::Output {
PhysAddr(self.0 - rhs)
}
}
2024-01-26 11:46:02 +08:00
impl Sub<PhysAddr> for PhysAddr {
type Output = Self;
fn sub(self, rhs: PhysAddr) -> Self::Output {
PhysAddr(self.0 - rhs.0)
}
}
2023-12-12 15:10:01 +08:00
impl SubAssign<usize> for PhysAddr {
fn sub_assign(&mut self, rhs: usize) {
*self = PhysAddr::from(self.0 - rhs);
}
}
2024-01-26 11:46:02 +08:00
impl SubAssign<PhysAddr> for PhysAddr {
fn sub_assign(&mut self, rhs: PhysAddr) {
*self = PhysAddr::from(self.0 - rhs.0);
}
}
2023-12-12 15:10:01 +08:00
impl Add<usize> for VirtAddr {
type Output = Self;
fn add(self, rhs: usize) -> Self::Output {
Self(self.0 + rhs)
}
}
2024-01-26 11:46:02 +08:00
impl Add<VirtAddr> for VirtAddr {
type Output = Self;
fn add(self, rhs: VirtAddr) -> Self::Output {
Self(self.0 + rhs.0)
}
}
2023-12-12 15:10:01 +08:00
impl AddAssign<usize> for VirtAddr {
fn add_assign(&mut self, rhs: usize) {
*self = VirtAddr::from(self.0 + rhs);
}
}
2024-01-26 11:46:02 +08:00
impl AddAssign<VirtAddr> for VirtAddr {
fn add_assign(&mut self, rhs: VirtAddr) {
*self = VirtAddr::from(self.0 + rhs.0);
}
}
2023-12-12 15:10:01 +08:00
impl Sub<usize> for VirtAddr {
type Output = VirtAddr;
fn sub(self, rhs: usize) -> Self::Output {
VirtAddr(self.0 - rhs)
}
}
2024-01-26 11:46:02 +08:00
impl Sub<VirtAddr> for VirtAddr {
type Output = Self;
fn sub(self, rhs: VirtAddr) -> Self::Output {
VirtAddr(self.0 - rhs.0)
}
}
2023-12-12 15:10:01 +08:00
impl SubAssign<usize> for VirtAddr {
fn sub_assign(&mut self, rhs: usize) {
*self = VirtAddr::from(self.0 - rhs);
}
}
2024-01-26 11:46:02 +08:00
impl SubAssign<VirtAddr> for VirtAddr {
fn sub_assign(&mut self, rhs: VirtAddr) {
*self = VirtAddr::from(self.0 - rhs.0);
}
}
2023-12-12 15:10:01 +08:00
impl From<usize> for PhysAddr {
fn from(addr: usize) -> Self {
PhysAddr(addr)
}
}
2024-01-26 11:46:02 +08:00
impl From<NonZeroUsize> for PhysAddr {
fn from(addr: NonZeroUsize) -> Self {
PhysAddr(addr.get())
}
}
impl<T> From<*mut T> for PhysAddr {
fn from(addr: *mut T) -> Self {
PhysAddr(addr as usize)
}
}
impl<T> From<*const T> for PhysAddr {
fn from(addr: *const T) -> Self {
PhysAddr(addr as usize)
}
}
2023-12-12 15:10:01 +08:00
impl From<PhysAddr> for usize {
fn from(addr: PhysAddr) -> Self {
addr.0
}
}
2024-01-26 11:46:02 +08:00
impl From<PhysAddr> for NonZeroUsize {
fn from(addr: PhysAddr) -> Self {
NonZeroUsize::new(addr.0).unwrap()
2023-12-18 00:32:36 +08:00
}
}
2024-01-26 11:46:02 +08:00
impl<T> From<PhysAddr> for *mut T {
2023-12-18 00:32:36 +08:00
fn from(addr: PhysAddr) -> Self {
2024-01-26 11:46:02 +08:00
addr.0 as *mut T
2023-12-18 00:32:36 +08:00
}
}
2023-12-12 15:10:01 +08:00
impl From<usize> for VirtAddr {
fn from(addr: usize) -> Self {
VirtAddr(addr)
}
}
2024-01-26 11:46:02 +08:00
impl From<NonZeroUsize> for VirtAddr {
fn from(addr: NonZeroUsize) -> Self {
VirtAddr(addr.get())
}
}
impl<T> From<*mut T> for VirtAddr {
fn from(addr: *mut T) -> Self {
VirtAddr(addr as usize)
}
}
impl<T> From<*const T> for VirtAddr {
fn from(addr: *const T) -> Self {
VirtAddr(addr as usize)
}
}
2023-12-12 15:10:01 +08:00
impl From<VirtAddr> for usize {
fn from(addr: VirtAddr) -> Self {
addr.0
}
}
2024-01-26 11:46:02 +08:00
impl From<VirtAddr> for NonZeroUsize {
fn from(addr: VirtAddr) -> Self {
NonZeroUsize::new(addr.0).unwrap()
2023-12-18 00:32:36 +08:00
}
}
2024-01-26 11:46:02 +08:00
impl<T> From<VirtAddr> for *mut T {
2023-12-18 00:32:36 +08:00
fn from(addr: VirtAddr) -> Self {
2024-01-26 11:46:02 +08:00
addr.0 as *mut T
2023-12-18 00:32:36 +08:00
}
}
2023-12-12 15:10:01 +08:00
impl Debug for PhysAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "PhysAddr({:#x})", self.0)
}
}
2023-12-17 20:17:30 +08:00
impl Display for PhysAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#x}", self.0)
}
}
2023-12-12 15:10:01 +08:00
impl LowerHex for PhysAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#x}", self.0)
}
}
impl UpperHex for PhysAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#X}", self.0)
}
}
impl Debug for VirtAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "VirtAddr({:#x})", self.0)
}
}
2023-12-17 20:17:30 +08:00
impl Display for VirtAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#x}", self.0)
}
}
2023-12-12 15:10:01 +08:00
impl LowerHex for VirtAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#x}", self.0)
}
}
impl UpperHex for VirtAddr {
fn fmt(&self, f: &mut Formatter) -> Result {
write!(f, "{:#X}", self.0)
}
}
impl Hash for PhysAddr {
fn hash<H: core::hash::Hasher>(&self, state: &mut H) {
self.0.hash(state);
}
}
impl Hash for VirtAddr {
fn hash<H: core::hash::Hasher>(&self, state: &mut H) {
self.0.hash(state);
}
}