mirror of
https://github.com/plasma-umass/coz.git
synced 2024-09-11 04:55:25 +03:00
Merge pull request #211 from lopukhov/master
[Rust] Replace the usage of `AtomicUsize` with `OneCell`
This commit is contained in:
commit
62a36708a3
@ -34,8 +34,7 @@ use std::sync::atomic::{AtomicUsize, Ordering::SeqCst};
|
|||||||
#[macro_export]
|
#[macro_export]
|
||||||
macro_rules! progress {
|
macro_rules! progress {
|
||||||
() => {{
|
() => {{
|
||||||
static COUNTER: $crate::Counter =
|
static COUNTER: $crate::Counter = $crate::Counter::progress(concat!(file!(), ":", line!()));
|
||||||
$crate::Counter::progress(concat!(file!(), ":", line!()));
|
|
||||||
COUNTER.increment();
|
COUNTER.increment();
|
||||||
}};
|
}};
|
||||||
($name:expr) => {{
|
($name:expr) => {{
|
||||||
@ -212,10 +211,10 @@ impl Counter {
|
|||||||
fn create_counter(&self) -> Option<&'static coz_counter_t> {
|
fn create_counter(&self) -> Option<&'static coz_counter_t> {
|
||||||
let name = CString::new(self.name).unwrap();
|
let name = CString::new(self.name).unwrap();
|
||||||
let ptr = coz_get_counter(self.ty, &name);
|
let ptr = coz_get_counter(self.ty, &name);
|
||||||
if ptr.is_null() {
|
match ptr {
|
||||||
None
|
// SAFETY: Pointer to counter returned by `coz_get_counter` is not null and aligned.
|
||||||
} else {
|
Some(ptr) if !ptr.is_null() => Some(unsafe { &*ptr }),
|
||||||
Some(unsafe { &*ptr })
|
_ => None,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -224,14 +223,12 @@ impl Counter {
|
|||||||
/// coz calls to `begin` and `end` for the duration of a scope, regardless of how
|
/// coz calls to `begin` and `end` for the duration of a scope, regardless of how
|
||||||
/// the scope was exited (e.g. by early return, `?` or panic).
|
/// the scope was exited (e.g. by early return, `?` or panic).
|
||||||
pub struct Guard<'t> {
|
pub struct Guard<'t> {
|
||||||
counter: &'t Counter
|
counter: &'t Counter,
|
||||||
}
|
}
|
||||||
|
|
||||||
impl<'t> Guard<'t> {
|
impl<'t> Guard<'t> {
|
||||||
pub fn new(counter: &'t Counter) -> Self {
|
pub fn new(counter: &'t Counter) -> Self {
|
||||||
Guard {
|
Guard { counter }
|
||||||
counter
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -247,30 +244,37 @@ struct coz_counter_t {
|
|||||||
backoff: libc::size_t,
|
backoff: libc::size_t,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// The type of `_coz_get_counter` as defined in `include/coz.h`
|
||||||
|
///
|
||||||
|
/// `typedef coz_counter_t* (*coz_get_counter_t)(int, const char*);`
|
||||||
|
type GetCounterFn = unsafe extern "C" fn(libc::c_int, *const libc::c_char) -> *mut coz_counter_t;
|
||||||
|
|
||||||
#[cfg(target_os = "linux")]
|
#[cfg(target_os = "linux")]
|
||||||
fn coz_get_counter(ty: libc::c_int, name: &CStr) -> *mut coz_counter_t {
|
fn coz_get_counter(ty: libc::c_int, name: &CStr) -> Option<*mut coz_counter_t> {
|
||||||
static PTR: AtomicUsize = AtomicUsize::new(1);
|
static GET_COUNTER: OnceCell<Option<GetCounterFn>> = OnceCell::new();
|
||||||
let mut ptr = PTR.load(SeqCst);
|
let func = GET_COUNTER.get_or_init(|| {
|
||||||
if ptr == 1 {
|
|
||||||
let name = CStr::from_bytes_with_nul(b"_coz_get_counter\0").unwrap();
|
let name = CStr::from_bytes_with_nul(b"_coz_get_counter\0").unwrap();
|
||||||
ptr = unsafe { libc::dlsym(libc::RTLD_DEFAULT, name.as_ptr() as *const _) as usize };
|
// SAFETY: We are calling an external function that does exist in Linux.
|
||||||
PTR.store(ptr, SeqCst);
|
// No specific invariants that we must uphold have been defined.
|
||||||
}
|
let func = unsafe { libc::dlsym(libc::RTLD_DEFAULT, name.as_ptr()) };
|
||||||
if ptr == 0 {
|
if func.is_null() {
|
||||||
return ptr::null_mut();
|
None
|
||||||
}
|
} else {
|
||||||
|
// SAFETY: If the pointer returned by dlsym is not null it is a valid pointer to the function
|
||||||
|
// identified by the provided symbol. The type of `_coz_get_counter` is defined in `include/coz.h`
|
||||||
|
// as [GetCounterFn].
|
||||||
|
Some(unsafe { mem::transmute(func) })
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
thread_init(); // just in case we haven't already
|
thread_init(); // just in case we haven't already
|
||||||
|
|
||||||
unsafe {
|
// SAFETY: We are calling an external function which exists as it is not None
|
||||||
mem::transmute::<
|
// No specific invariants that we must uphold have been defined.
|
||||||
usize,
|
func.map(|f| unsafe { f(ty, name.as_ptr()) })
|
||||||
unsafe extern "C" fn(libc::c_int, *const libc::c_char) -> *mut coz_counter_t,
|
|
||||||
>(ptr)(ty, name.as_ptr())
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#[cfg(not(target_os = "linux"))]
|
#[cfg(not(target_os = "linux"))]
|
||||||
fn coz_get_counter(_ty: libc::c_int, _name: &CStr) -> *mut coz_counter_t {
|
fn coz_get_counter(_ty: libc::c_int, _name: &CStr) -> Option<*mut coz_counter_t> {
|
||||||
ptr::null_mut()
|
None
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user