diff --git a/ylong_ffrt/build.rs b/ylong_ffrt/build.rs index 71ecd3ea3d7d643c8cd2db95eaf84200017f2b8d..adc24dc30499020d6b245076a9400877a1f45328 100644 --- a/ylong_ffrt/build.rs +++ b/ylong_ffrt/build.rs @@ -19,13 +19,13 @@ use std::{env, fs}; fn main() { let library_name = "ffrt"; let root = PathBuf::from(env::var_os("CARGO_MANIFEST_DIR").unwrap()); - let library_dir = fs::canonicalize(root.join("lib")).unwrap(); + //let library_dir = fs::canonicalize(root.join("lib")).unwrap(); - println!("cargo:rustc-link-lib={}", library_name); - println!( - "cargo:rustc-link-search=native={}", - env::join_paths([library_dir]).unwrap().to_str().unwrap() - ); - println!("cargo:rustc-link-lib=pthread"); - println!("cargo:rustc-link-lib=dylib=stdc++"); + // println!("cargo:rustc-link-lib={}", library_name); + // println!( + // "cargo:rustc-link-search=native={}", + // env::join_paths([library_dir]).unwrap().to_str().unwrap() + // ); + // println!("cargo:rustc-link-lib=pthread"); + // println!("cargo:rustc-link-lib=dylib=stdc++"); } diff --git a/ylong_runtime/.idea/.gitignore b/ylong_runtime/.idea/.gitignore new file mode 100644 index 0000000000000000000000000000000000000000..35410cacdc5e87f985c93a96520f5e11a5c822e4 --- /dev/null +++ b/ylong_runtime/.idea/.gitignore @@ -0,0 +1,8 @@ +# 默认忽略的文件 +/shelf/ +/workspace.xml +# 基于编辑器的 HTTP 客户端请求 +/httpRequests/ +# Datasource local storage ignored files +/dataSources/ +/dataSources.local.xml diff --git a/ylong_runtime/.idea/modules.xml b/ylong_runtime/.idea/modules.xml new file mode 100644 index 0000000000000000000000000000000000000000..2f25b8ad2443ccdf6b4c0886ca91d09fb11e2a36 --- /dev/null +++ b/ylong_runtime/.idea/modules.xml @@ -0,0 +1,8 @@ + + + + + + + + \ No newline at end of file diff --git a/ylong_runtime/.idea/vcs.xml b/ylong_runtime/.idea/vcs.xml new file mode 100644 index 0000000000000000000000000000000000000000..6c0b8635858dc7ad44b93df54b762707ce49eefc --- /dev/null +++ b/ylong_runtime/.idea/vcs.xml @@ -0,0 +1,6 @@ + + + + + + \ No newline at end of file diff --git a/ylong_runtime/.idea/ylong_runtime.iml b/ylong_runtime/.idea/ylong_runtime.iml new file mode 100644 index 0000000000000000000000000000000000000000..14d1db0dd0abcc42538e0cb0f38410a8fc5de4cc --- /dev/null +++ b/ylong_runtime/.idea/ylong_runtime.iml @@ -0,0 +1,13 @@ + + + + + + + + + + + + + \ No newline at end of file diff --git a/ylong_runtime/src/sync/mutex.rs b/ylong_runtime/src/sync/mutex.rs index 46df16a88c5a51ee8c5cd178c9baa5ce75cd27de..d062350816b8efbb4c20ce5df408842d189501ff 100644 --- a/ylong_runtime/src/sync/mutex.rs +++ b/ylong_runtime/src/sync/mutex.rs @@ -18,6 +18,7 @@ use std::error::Error; use std::fmt; use std::fmt::{Display, Formatter}; use std::ops::{Deref, DerefMut}; +use std::time::Instant; use crate::sync::semaphore_inner::SemaphoreInner; @@ -97,7 +98,7 @@ impl Mutex { // The result of `acquire()` will be `Err()` only when the semaphore is closed. // `Mutex` will not close, so the result of `acquire()` must be `Ok(())`. self.sem.acquire().await.unwrap(); - MutexGuard(self) + MutexGuard(self, Instant::now()) } /// Attempts to get the mutex. @@ -122,7 +123,7 @@ impl Mutex { /// ``` pub fn try_lock(&self) -> Result, LockError> { match self.sem.try_acquire() { - Ok(_) => Ok(MutexGuard(self)), + Ok(_) => Ok(MutexGuard(self, Instant::now())), Err(_) => Err(LockError), } } @@ -139,13 +140,18 @@ impl Mutex { } /// Mutex guard to access the data after holding the mutex. -pub struct MutexGuard<'a, T: ?Sized>(&'a Mutex); +pub struct MutexGuard<'a, T: ?Sized>(&'a Mutex, Instant); impl MutexGuard<'_, T> { // Unlocks the mutex. Wakes the first future waiting for the mutex. fn unlock(&mut self) { self.0.sem.release(); } + + ///Obtain holding time + pub fn holding_time(&self) -> u128 { + self.1.elapsed().as_millis() + } } unsafe impl Sync for MutexGuard<'_, T> {} @@ -286,4 +292,21 @@ mod tests { assert!(mutex.try_lock().is_ok()); }); } + + ///UT test cases for MutexGuard::holding_time() interface + /// + /// #Brief + /// 1. Creating a Concurrent Mutual Exclusion Lock + /// 2. Perform locking operation + /// 3. Blocking threads + /// 4. Verify the holding time of the lock + #[test] + fn ut_mutex_holding_time_01() { + let mutex = Mutex::new(10); + block_on(async move { + let lock = mutex.lock().await; + thread::sleep(Duration::from_millis(1)); + assert_eq!(lock.holding_time(),1); + }); + } } diff --git a/ylong_runtime/src/sync/oneshot.rs b/ylong_runtime/src/sync/oneshot.rs index f84c378480d888d03addd6231d5153c2a2d7cacc..1bfece16bf15eb093f4f2bcddae5324a6cabd905 100644 --- a/ylong_runtime/src/sync/oneshot.rs +++ b/ylong_runtime/src/sync/oneshot.rs @@ -48,7 +48,6 @@ use std::sync::atomic::Ordering::{AcqRel, Acquire, Release, SeqCst}; use std::sync::Arc; use std::task::Poll::{Pending, Ready}; use std::task::{Context, Poll}; - use super::atomic_waker::AtomicWaker; use super::error::{RecvError, TryRecvError}; diff --git a/ylong_runtime/src/sync/rwlock.rs b/ylong_runtime/src/sync/rwlock.rs index 3ef1d65c9adf1c6f9725794e8ba322cb450160f5..5544e83f29de3d555d15308f9c28ca5291fcd41b 100644 --- a/ylong_runtime/src/sync/rwlock.rs +++ b/ylong_runtime/src/sync/rwlock.rs @@ -18,7 +18,7 @@ use std::fmt; use std::ops::{Deref, DerefMut}; use std::sync::atomic::AtomicI64; use std::sync::atomic::Ordering::{AcqRel, Acquire, Release}; - +use std::time::Instant; use crate::sync::semaphore_inner::SemaphoreInner; use crate::sync::LockError; @@ -117,7 +117,7 @@ impl RwLock { // `RwLock` will not close, so the result of `acquire()` must be `Ok(())`. self.read_sem.acquire().await.unwrap(); } - RwLockReadGuard(self) + RwLockReadGuard(self, Instant::now()) } /// Attempts to get the read lock. If another writer is holding the write @@ -143,7 +143,7 @@ impl RwLock { .read_count .compare_exchange(read_count, read_count + 1, AcqRel, Acquire) { - Ok(_) => return Ok(RwLockReadGuard(self)), + Ok(_) => return Ok(RwLockReadGuard(self, Instant::now())), Err(curr) => read_count = curr, } } @@ -177,7 +177,7 @@ impl RwLock { if read_count >= 0 && self.read_wait.fetch_add(read_count, Release) != -read_count { self.write_sem.acquire().await.unwrap(); } - RwLockWriteGuard(self) + RwLockWriteGuard(self, Instant::now()) } /// Attempts to acquire the write lock. @@ -202,7 +202,7 @@ impl RwLock { .read_count .compare_exchange(0, -MAX_READS, AcqRel, Acquire) { - Ok(_) => Ok(RwLockWriteGuard(self)), + Ok(_) => Ok(RwLockWriteGuard(self, Instant::now())), Err(_) => { self.write_mutex.release(); Err(LockError) @@ -247,7 +247,7 @@ impl RwLock { } /// Read guard to access the data after holding the mutex. -pub struct RwLockReadGuard<'a, T: ?Sized>(&'a RwLock); +pub struct RwLockReadGuard<'a, T: ?Sized>(&'a RwLock, Instant); unsafe impl Send for RwLockReadGuard<'_, T> {} unsafe impl Sync for RwLockReadGuard<'_, T> {} @@ -262,6 +262,10 @@ impl RwLockReadGuard<'_, T> { self.0.write_sem.release(); } } + ///Obtain holding time + pub fn holding_time(&self) -> u128 { + self.1.elapsed().as_millis() + } } /// Unlock the read lock when ReadGuard is dropped. @@ -292,8 +296,14 @@ impl fmt::Display for RwLockReadGuard<'_, T> { } /// RwLock write guard -pub struct RwLockWriteGuard<'a, T: ?Sized>(&'a RwLock); +pub struct RwLockWriteGuard<'a, T: ?Sized>(&'a RwLock, Instant); +impl RwLockWriteGuard<'_, T> { + ///Obtain holding time + pub fn holding_time(&self) -> u128 { + self.1.elapsed().as_millis() + } +} unsafe impl Send for RwLockWriteGuard<'_, T> {} unsafe impl Sync for RwLockWriteGuard<'_, T> {} @@ -335,7 +345,8 @@ impl DerefMut for RwLockWriteGuard<'_, T> { #[cfg(test)] mod tests { use std::sync::Arc; - + use std::thread; + use std::time::Duration; use super::*; use crate::{block_on, spawn}; @@ -529,4 +540,38 @@ mod tests { let lock = RwLock::new(10); assert_eq!(lock.into_inner(), 10); } + + ///UT test cases for RwLockReadGuard::holding_time() interface + /// + /// #Brief + /// 1. Creating a Concurrent Mutual Exclusion Lock + /// 2. Perform locking operation + /// 3. Blocking threads + /// 4. Verify the holding time of the lock + #[test] + fn ut_rwlock_read_holding_time_01() { + block_on(async { + let lock = RwLock::new(10); + let read = lock.read().await; + thread::sleep(Duration::from_millis(1)); + assert_eq!(read.holding_time(),1); + }) + } + + ///UT test cases for RwLockWriteGuard::holding_time() interface + /// + /// #Brief + /// 1. Creating a Concurrent Mutual Exclusion Lock + /// 2. Perform locking operation + /// 3. Blocking threads + /// 4. Verify the holding time of the lock + #[test] + fn ut_rwlock_write_holding_time_01() { + block_on(async { + let lock = RwLock::new(10); + let write = lock.write().await; + thread::sleep(Duration::from_millis(1)); + assert_eq!(write.holding_time(),1); + }) + } } diff --git a/ylong_runtime/src/sync/wake_list.rs b/ylong_runtime/src/sync/wake_list.rs index ac5749a63247456edc03d2e8762d19b3a1769373..aff27e8a8041bd03bc62b41764214d3c70c00125 100644 --- a/ylong_runtime/src/sync/wake_list.rs +++ b/ylong_runtime/src/sync/wake_list.rs @@ -16,7 +16,7 @@ use std::hint::spin_loop; use std::ops::{Deref, DerefMut}; use std::sync::atomic::{AtomicUsize, Ordering}; use std::task::Waker; - +use std::time::Instant; use crate::util::slots::{Slots, SlotsError}; /// The first left most bit represents LOCKED state @@ -97,7 +97,7 @@ impl WakerList { while self.flag.fetch_or(LOCKED, Ordering::Acquire) & LOCKED != 0 { spin_loop(); } - Lock { waker_set: self } + Lock { waker_set: self , _holding_time: Instant::now() } } } @@ -134,8 +134,14 @@ impl Inner { /// The guard holding the WakerList. pub(crate) struct Lock<'a> { waker_set: &'a WakerList, + _holding_time: Instant, +} +impl Lock<'_> { + ///Obtain holding time + pub fn _holding_time(&self) -> u128 { + self._holding_time.elapsed().as_millis() + } } - impl Drop for Lock<'_> { #[inline] fn drop(&mut self) { @@ -173,6 +179,8 @@ enum Notify { #[cfg(test)] mod tests { + use std::thread; + use std::time::Duration; use super::*; /// UT test cases for WakeList::new(). @@ -188,4 +196,20 @@ mod tests { assert_eq!((*wakelist.inner.get()).wake_list.len, 0); } } + + ///UT test cases for Lock::holding_time() interface + /// + /// #Brief + /// 1. Creating a Concurrent Mutual Exclusion Lock + /// 2. Perform locking operation + /// 3. Blocking threads + /// 4. Verify the holding time of the lock + #[test] + fn ut_lock_holding_time_01() { + let wakelist = WakerList::new(); + let lock = wakelist.lock(); + thread::sleep(Duration::from_millis(1)); + assert_eq!(lock._holding_time(), 1); + } + } diff --git a/ylong_runtime/src/sync/watch.rs b/ylong_runtime/src/sync/watch.rs index cd34c3307d8c39912a44d8c1b8406ddd20d843e2..b6a97f4ad333a09f1317292084fbc5684fdc4d86 100644 --- a/ylong_runtime/src/sync/watch.rs +++ b/ylong_runtime/src/sync/watch.rs @@ -20,7 +20,6 @@ use std::sync::atomic::Ordering::{Acquire, Release}; use std::sync::{Arc, RwLock, RwLockReadGuard}; use std::task::Poll::{Pending, Ready}; use std::task::{Context, Poll}; - use crate::futures::poll_fn; use crate::sync::error::{RecvError, SendError}; use crate::sync::wake_list::WakerList; @@ -571,7 +570,6 @@ impl Debug for Channel { #[cfg(test)] mod tests { use std::sync::atomic::Ordering::Acquire; - use crate::sync::error::RecvError; use crate::sync::watch; use crate::{block_on, spawn};