Enhance tool documentation and add new features
- Added module-level documentation for memory tools (`remember`, `recall`, `forget`) to clarify their purpose. - Improved documentation in `recall.rs` and `remember.rs` to describe the functionality and flow of memory entry operations. - Updated `mod.rs` to include descriptions for the tool trait and execution context. - Enhanced `plan.rs` with detailed comments on plan-mode signaling tools. - Documented text search tools in `search.rs` to explain their functionality. - Improved sequential-thinking tool documentation in `seqthink.rs`. - Added safety filter documentation in `shell_filter` for credential and git operations. - Enhanced utility tools documentation, including `cd`, `dir_cache_update`, and `todowrite`. - Improved rendering documentation in view modules (`chat`, `markdown`, `status`, `workflow`) to clarify rendering flows and purposes.
This commit is contained in:
@@ -1,12 +1,19 @@
|
||||
//! PID-file based advisory lock preventing two processes from operating on
|
||||
//! the same session directory concurrently.
|
||||
|
||||
use std::path::{Path, PathBuf};
|
||||
use std::fs;
|
||||
|
||||
/// A PID-file lock (`<session_dir>/.lock`) tied to the current process,
|
||||
/// auto-removed on drop.
|
||||
pub struct SessionLock {
|
||||
path: PathBuf,
|
||||
pid: u32,
|
||||
}
|
||||
|
||||
impl SessionLock {
|
||||
/// Construct a lock handle for a session directory (does not acquire
|
||||
/// the lock yet — call `try_lock`).
|
||||
pub fn new(session_dir: &Path) -> Self {
|
||||
SessionLock {
|
||||
path: session_dir.join(".lock"),
|
||||
@@ -14,6 +21,19 @@ impl SessionLock {
|
||||
}
|
||||
}
|
||||
|
||||
/// Attempt to acquire the session lock.
|
||||
///
|
||||
/// Flow: if `.lock` exists, read the PID inside it and check
|
||||
/// `is_alive` — if that process is still running, fail to acquire →
|
||||
/// otherwise (no lock file, unreadable PID, or dead owner) write our
|
||||
/// own PID into `.lock` and succeed.
|
||||
///
|
||||
/// Why: a stale lock file from a crashed process must not permanently
|
||||
/// block new sessions, so liveness is re-checked via `kill(pid, 0)`
|
||||
/// rather than trusting the file's mere existence.
|
||||
///
|
||||
/// Return: `Ok(true)` if acquired, `Ok(false)` if another live
|
||||
/// process holds it, `Err` on I/O failure.
|
||||
pub fn try_lock(&self) -> std::io::Result<bool> {
|
||||
if self.path.exists() {
|
||||
let content = fs::read_to_string(&self.path).unwrap_or_default();
|
||||
@@ -27,10 +47,12 @@ impl SessionLock {
|
||||
Ok(true)
|
||||
}
|
||||
|
||||
/// Explicitly release the lock by removing the lock file.
|
||||
pub fn unlock(&self) {
|
||||
let _ = fs::remove_file(&self.path);
|
||||
}
|
||||
|
||||
/// Check whether a process with the given PID is currently alive.
|
||||
fn is_alive(&self, pid: u32) -> bool {
|
||||
// SAFETY: `libc::kill(pid, 0)` does not send a signal; it only checks
|
||||
// whether the process exists and the caller has permission to signal
|
||||
@@ -40,6 +62,8 @@ impl SessionLock {
|
||||
}
|
||||
|
||||
impl Drop for SessionLock {
|
||||
/// Release the lock automatically when the guard goes out of scope,
|
||||
/// so an ungracefully-exited process doesn't leave a dangling lock.
|
||||
fn drop(&mut self) {
|
||||
let _ = fs::remove_file(&self.path);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user