iceoryx2_cal/shm_allocator/pointer_offset.rs
1// Copyright (c) 2023 Contributors to the Eclipse Foundation
2//
3// See the NOTICE file(s) distributed with this work for additional
4// information regarding copyright ownership.
5//
6// This program and the accompanying materials are made available under the
7// terms of the Apache Software License 2.0 which is available at
8// https://www.apache.org/licenses/LICENSE-2.0, or the MIT license
9// which is available at https://opensource.org/licenses/MIT.
10//
11// SPDX-License-Identifier: Apache-2.0 OR MIT
12
13use core::fmt::Debug;
14
15pub type SegmentIdUnderlyingType = u8;
16
17/// Defines the [`SegmentId`] of a [`SharedMemory`](crate::shared_memory::SharedMemory)
18#[derive(Debug, Clone, Copy, PartialEq, Eq)]
19pub struct SegmentId(SegmentIdUnderlyingType);
20
21impl SegmentId {
22 /// Creates a new [`SegmentId`] from a given value.
23 pub const fn new(value: SegmentIdUnderlyingType) -> Self {
24 Self(value)
25 }
26
27 /// Returns the underlying value of the [`SegmentId`]
28 pub const fn value(&self) -> SegmentIdUnderlyingType {
29 self.0
30 }
31
32 /// Returns the maximum value the [`SegmentId`] supports.
33 pub const fn max_segment_id() -> SegmentIdUnderlyingType {
34 SegmentIdUnderlyingType::MAX
35 }
36}
37
38/// An offset to a [`SharedMemory`](crate::shared_memory::SharedMemory) address. It requires the
39///
40/// [`SharedMemory::payload_start_address()`](crate::shared_memory::SharedMemory::payload_start_address())
41/// of the corresponding [`SharedMemory`](crate::shared_memory::SharedMemory) to be converted into
42/// an actual pointer.
43///
44/// Contains the offset and the corresponding [`SegmentId`].
45#[derive(Clone, Copy, Eq, PartialEq)]
46pub struct PointerOffset(u64);
47
48impl PointerOffset {
49 /// Creates a new [`PointerOffset`] from the given offset value with the [`SegmentId`] == 0.
50 pub const fn new(offset: usize) -> PointerOffset {
51 const SEGMENT_ID: u8 = 0;
52 Self::from_offset_and_segment_id(offset, SegmentId::new(SEGMENT_ID))
53 }
54
55 /// Creates a new [`PointerOffset`] from an offset and a [`SegmentId`]
56 pub const fn from_offset_and_segment_id(offset: usize, segment_id: SegmentId) -> PointerOffset {
57 Self(((offset as u64) << (SegmentIdUnderlyingType::BITS)) | segment_id.value() as u64)
58 }
59
60 /// Creates a new [`PointerOffset`] from a provided raw value.
61 pub const fn from_value(value: u64) -> PointerOffset {
62 Self(value)
63 }
64
65 /// Returns the underlying raw value of the [`PointerOffset`]
66 pub const fn as_value(&self) -> u64 {
67 self.0
68 }
69
70 /// Sets the [`SegmentId`] of the [`PointerOffset`].
71 pub fn set_segment_id(&mut self, value: SegmentId) {
72 self.0 &= !((1u64 << SegmentIdUnderlyingType::BITS) - 1);
73 self.0 |= value.0 as u64;
74 }
75
76 /// Returns the offset.
77 pub const fn offset(&self) -> usize {
78 (self.0 >> (SegmentIdUnderlyingType::BITS)) as usize
79 }
80
81 /// Returns the [`SegmentId`].
82 pub const fn segment_id(&self) -> SegmentId {
83 SegmentId((self.0 & ((1u64 << SegmentIdUnderlyingType::BITS) - 1)) as u8)
84 }
85}
86
87impl Debug for PointerOffset {
88 fn fmt(&self, f: &mut core::fmt::Formatter<'_>) -> core::fmt::Result {
89 write!(
90 f,
91 "PointerOffset {{ offset: {}, segment_id: {:?} }}",
92 self.offset(),
93 self.segment_id()
94 )
95 }
96}