Skip to main content

GenericTimer

Struct GenericTimer 

Source
pub struct GenericTimer<const BITS: u32 = 64>(/* private fields */);
Expand description

The aarch64 generic timer virtual counter (CNTVCT_EL0).

The architecture requires a constant frequency, consistent across cores. Its period must be at least 40 years. Access to this counter may be disabled by the kernel. It is almost always available on Linux.

§Frequency

The frequency of the counter can be read from CNTFRQ_EL0, so it does not need calibration. This value is typically populated by firmware.

From Armv8.6 and Armv9.1 on, the frequency must be exactly 1GHz. Before those, the counter frequency was typically between 1MHz and 50MHz. The clock frequency is represented in 32-bits, which means the frequency will be at most u32::MAX Hz ≈ 4.3GHz.

Note that even on newer systems the resolution may be lower than 1GHz. For example, the counter may atomically increase by 40 every 40ns.

§Bit Size

The hardware counter has 56-64 bits (implementation dependent). From Armv8.6 and Armv9.1 on, the counter must be 64 bits. BITS is the counter width assumed by this clock and must be in 56..=64. A mismatch with the hardware in either direction has downsides. If the width on the target machine is not known, a tradeoff has to be made.

If BITS is greater than the hardware size, calculations involving instants between which the counter rolled over will be incorrect. Typically, CNTVCT_EL0 is reset to 0 at boot, so rollover will occur if a machine stays running for longer than the rollover time. Arm requires the rollover time to be at least 40 years. It is recommended that most applications go with BITS=64.

If BITS is less than the hardware size, the top bits of the value read from CNTVCT_EL0 are discarded. This makes the clock function correctly, but reduces rollover time. In the worst case, rollover time is slightly over 6 months. Keep in mind that instant comparison only works reliably if the two instants are less than half of a rollover time from each other.

Implementations§

Source§

impl<const BITS: u32> GenericTimer<BITS>

Source

pub fn new_assume_accessible() -> Self

Returns a GenericTimer, assuming CNTVCT_EL0 is readable from EL0.

Operating systems that expose a userspace clock without a syscall enable this, which covers Linux and macOS. If it is disabled, Clock::now traps with SIGILL. There is no way to query this from EL0, so prefer GenericTimer::try_new_linux_sys on Linux.

Source

pub fn try_new_linux_sys() -> Result<Self, GenericTimerUnavailable>

Returns Ok(GenericTimer) if the Linux kernel reports arch_sys_counter as an available clocksource.

Source

pub fn read_cntfrq(&self) -> u32

Returns the counter frequency in Hz as reported by CNTFRQ_EL0.

Source

pub fn calibration_from_cntfrq(&self) -> U64Calibration<BITS>

Returns a calibration derived from CNTFRQ_EL0.

§Panics

Panics if CNTFRQ_EL0 is zero, which means firmware did not populate it.

Trait Implementations§

Source§

impl<const BITS: u32> Clock for GenericTimer<BITS>

Source§

type Time = WrappingU64Time<BITS>

Source§

type Calibration = U64Calibration<BITS>

Source§

fn now(&self) -> WrappingU64Instant<BITS>

Returns the current instant.
Source§

impl<const BITS: u32> Clone for GenericTimer<BITS>

Source§

fn clone(&self) -> Self

Returns a duplicate of the value. Read more
1.0.0 (const: unstable) · Source§

fn clone_from(&mut self, source: &Self)

Performs copy-assignment from source. Read more
Source§

impl<const BITS: u32> Copy for GenericTimer<BITS>

Source§

impl<const BITS: u32> Debug for GenericTimer<BITS>

Source§

fn fmt(&self, f: &mut Formatter<'_>) -> Result

Formats the value using the given formatter. Read more
Source§

impl<const BITS: u32> Eq for GenericTimer<BITS>

Source§

impl<const BITS: u32> Hash for GenericTimer<BITS>

Source§

fn hash<__H: Hasher>(&self, state: &mut __H)

Feeds this value into the given Hasher. Read more
1.3.0 · Source§

fn hash_slice<H>(data: &[Self], state: &mut H)
where H: Hasher, Self: Sized,

Feeds a slice of this type into the given Hasher. Read more
Source§

impl<const BITS: u32> PartialEq for GenericTimer<BITS>

Source§

fn eq(&self, other: &Self) -> bool

Equality operator ==. Read more
1.0.0 (const: unstable) · Source§

fn ne(&self, other: &Rhs) -> bool

Inequality operator !=. Read more
Source§

impl<const BITS: u32> StructuralPartialEq for GenericTimer<BITS>

Auto Trait Implementations§

§

impl<const BITS: u32> Freeze for GenericTimer<BITS>

§

impl<const BITS: u32> RefUnwindSafe for GenericTimer<BITS>

§

impl<const BITS: u32> Send for GenericTimer<BITS>

§

impl<const BITS: u32> Sync for GenericTimer<BITS>

§

impl<const BITS: u32> Unpin for GenericTimer<BITS>

§

impl<const BITS: u32> UnsafeUnpin for GenericTimer<BITS>

§

impl<const BITS: u32> UnwindSafe for GenericTimer<BITS>

Blanket Implementations§

Source§

impl<T> Any for T
where T: 'static + ?Sized,

Source§

fn type_id(&self) -> TypeId

Gets the TypeId of self. Read more
Source§

impl<T> Borrow<T> for T
where T: ?Sized,

Source§

fn borrow(&self) -> &T

Immutably borrows from an owned value. Read more
Source§

impl<T> BorrowMut<T> for T
where T: ?Sized,

Source§

fn borrow_mut(&mut self) -> &mut T

Mutably borrows from an owned value. Read more
Source§

impl<T> CloneToUninit for T
where T: Clone,

Source§

unsafe fn clone_to_uninit(&self, dest: *mut u8)

🔬This is a nightly-only experimental API. (clone_to_uninit)
Performs copy-assignment from self to dest. Read more
Source§

impl<T> From<T> for T

Source§

fn from(t: T) -> T

Returns the argument unchanged.

Source§

impl<T, U> Into<U> for T
where U: From<T>,

Source§

fn into(self) -> U

Calls U::from(self).

That is, this conversion is whatever the implementation of From<T> for U chooses to do.

Source§

impl<T> ToOwned for T
where T: Clone,

Source§

type Owned = T

The resulting type after obtaining ownership.
Source§

fn to_owned(&self) -> T

Creates owned data from borrowed data, usually by cloning. Read more
Source§

fn clone_into(&self, target: &mut T)

Uses borrowed data to replace owned data, usually by cloning. Read more
Source§

impl<T, U> TryFrom<U> for T
where U: Into<T>,

Source§

type Error = !

The type returned in the event of a conversion error.
Source§

fn try_from(value: U) -> Result<T, !>

Performs the conversion.
Source§

impl<T, U> TryInto<U> for T
where U: TryFrom<T>,

Source§

type Error = <U as TryFrom<T>>::Error

The type returned in the event of a conversion error.
Source§

fn try_into(self) -> Result<U, <U as TryFrom<T>>::Error>

Performs the conversion.