utils.rs35.00%
1
// Copyright 2024 Google LLC2
//3
// Licensed under the Apache License, Version 2.0 (the "License");4
// you may not use this file except in compliance with the License.5
// You may obtain a copy of the License at6
//7
// https://www.apache.org/licenses/LICENSE-2.08
//9
// Unless required by applicable law or agreed to in writing, software10
// distributed under the License is distributed on an "AS IS" BASIS,11
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.12
// See the License for the specific language governing permissions and13
// limitations under the License.14
15
pub mod endian;16
#[cfg(target_os = "linux")]17
pub mod uds;18
19
use std::sync::atomic::{AtomicU64, Ordering};20
21
pub fn truncate_u64(val: u64, size: u64) -> u64 {39x22
val & (u64::MAX >> (64 - (size << 3)))39x23
}39x24
25
#[macro_export]26
macro_rules! align_up {27
($num:expr, $bits:expr) => {{28
let mask = (1 << $bits) - 1;29
($num.wrapping_add(mask)) & !mask30
}};31
}32
33
#[macro_export]34
macro_rules! align_up_ty {35
($num:expr, $ty:ty) => {{36
let mask = ::core::mem::align_of::<$ty>() - 1;37
($num.wrapping_add(mask)) & !mask38
}};39
}40
41
#[macro_export]42
macro_rules! align_down {43
($num:expr, $bits:expr) => {{44
let mask = (1 << $bits) - 1;45
$num & !mask46
}};47
}48
49
#[macro_export]50
macro_rules! assign_bits {51
($dst:expr, $src:expr, $mask:expr) => {52
$dst = ($dst & !$mask) | ($src & $mask)53
};54
}55
56
#[macro_export]57
macro_rules! mask_bits {58
($dst:expr, $src:expr, $mask:expr) => {59
($dst & !$mask) | ($src & $mask)60
};61
}62
63
#[inline]64
pub fn wrapping_sum<'a, T>(data: T) -> u865
where66
T: IntoIterator<Item = &'a u8>,67
{68
data.into_iter().fold(0u8, |accu, e| accu.wrapping_add(*e))69
}70
71
pub fn get_atomic_low32(num: &AtomicU64) -> u32 {72
num.load(Ordering::Acquire) as u3273
}74
75
pub fn get_atomic_high32(num: &AtomicU64) -> u32 {76
(num.load(Ordering::Acquire) >> 32) as u3277
}78
79
pub fn set_low32(num: &mut u64, val: u32) {80
*num &= !0xffff_ffff;81
*num |= val as u64;82
}83
84
pub fn set_high32(num: &mut u64, val: u32) {85
*num &= 0xffff_ffff;86
*num |= (val as u64) << 32;87
}88
89
pub fn set_atomic_low32(num: &AtomicU64, val: u32) {90
let mut cur = num.load(Ordering::Acquire);91
set_low32(&mut cur, val);92
num.store(cur, Ordering::Release)93
}94
95
pub fn set_atomic_high32(num: &AtomicU64, val: u32) {96
let mut cur = num.load(Ordering::Acquire);97
set_high32(&mut cur, val);98
num.store(cur, Ordering::Release)99
}100
101
#[macro_export]102
macro_rules! ffi {103
($f:expr) => {{104
let ret = $f;105
if ret <= -1 {106
Err(::std::io::Error::last_os_error())107
} else {108
Ok(ret)109
}110
}};111
($f:expr, $failure:expr) => {{112
let ret = $f;113
if ret == $failure {114
Err(::std::io::Error::last_os_error())115
} else {116
Ok(ret)117
}118
}};119
}120
121
#[macro_export]122
macro_rules! consts {123
(124
$(#[$attr:meta])*125
$vs:vis struct $EnumName:ident($TyName:ty) {126
$( $(#[$vattr:meta])* $VARIANT:ident = $value:expr;)*127
}128
) => {129
#[repr(transparent)]130
#[derive(PartialEq, Eq, Copy, Clone)]131
$(#[$attr])*132
$vs struct $EnumName($TyName);133
134
impl $EnumName {135
$($(#[$vattr])* pub const $VARIANT: $EnumName = $EnumName($value);)*136
137
#[allow(dead_code)]138
pub const fn raw(self) -> $TyName {126x139
self.0126x140
}126x141
142
#[allow(dead_code)]143
pub const fn name(self) -> &'static str {144
match self {145
$($EnumName::$VARIANT => stringify!($VARIANT),)*146
#[allow(unreachable_patterns)]147
_ => "Unknown"148
}149
}150
}151
152
impl ::core::fmt::Debug for $EnumName {153
fn fmt(&self, f: &mut ::core::fmt::Formatter<'_>) -> ::core::fmt::Result {21x154
f.write_str(stringify!($EnumName))?;21x155
match *self {21x156
$($EnumName::$VARIANT => {157
f.write_str("::")?;158
f.write_str(stringify!($VARIANT))159
})*160
#[allow(unreachable_patterns)]161
_ => {162
::core::fmt::Write::write_char(f, '(')?;163
::core::fmt::Debug::fmt(&self.0, f)?;164
::core::fmt::Write::write_char(f, ')')165
}166
}167
}21x168
}169
170
171
impl From<$EnumName> for $TyName {172
fn from(value: $EnumName) -> Self {24x173
value.024x174
}24x175
}176
177
impl From<$TyName> for $EnumName {178
fn from(value: $TyName) -> Self {33x179
$EnumName(value)33x180
}33x181
}182
}183
}184
185
#[macro_export]186
macro_rules! bitflags {187
(188
$(#[$attr:meta])*189
$vs:vis struct $FlagTy:ident($TyName:ty) {190
$(191
$(#[$inner:ident $($args:tt)*])*192
$FALG:ident = $value:expr;193
)*194
}195
) => {196
#[repr(transparent)]197
#[derive(PartialEq, Eq, Copy, Clone, Hash)]198
$(#[$attr])*199
$vs struct $FlagTy($TyName);200
201
::bitflags::bitflags! {202
impl $FlagTy: $TyName {203
$(204
$(#[$inner $($args)*])*205
const $FALG = $value;206
)*207
}208
}209
210
impl ::core::fmt::Debug for $FlagTy {211
fn fmt(&self, f: &mut ::core::fmt::Formatter) -> ::core::fmt::Result {126x212
if self.is_empty() {126x213
write!(f, "0")51x214
} else {215
::bitflags::parser::to_writer(self, f)75x216
}217
}126x218
}219
};220
}221
222
#[cfg(test)]223
#[path = "utils_test.rs"]224
mod tests;225