rust-async

Concurrency & Async

Safety Notice

This listing is imported from skills.sh public index metadata. Review upstream SKILL.md and repository scripts before running.

Copy this and send it to your AI assistant to learn

Install skill "rust-async" with this command: npx skills add peixotorms/odinlayer-skills/peixotorms-odinlayer-skills-rust-async

Concurrency & Async

Thread Safety

Error Cause Fix

Rc<T> cannot be sent between threads Rc is not Send

Use Arc

RefCell<T> is not Sync

Not thread-safe Use Mutex or RwLock

Cannot mutate through Arc

No interior mutability Arc<Mutex<T>> or Arc<AtomicT>

Deadlock Prevention

  • Lock ordering: Always acquire multiple locks in the same order across all threads

  • Self-deadlock: Never lock the same std::Mutex twice (use parking_lot::ReentrantMutex if needed)

  • Scope locks tightly: Drop guards as soon as possible

  • Atomics for primitives: Use AtomicBool /AtomicUsize instead of Mutex<bool>

  • Choose memory order carefully: Relaxed / Acquire / Release / SeqCst

Async Patterns

Pattern When to Use

tokio::spawn

Fire-and-forget concurrent tasks

tokio::select!

Race multiple futures, cancel losers

mpsc channel Fan-in: many producers, one consumer

oneshot channel Single request-response

broadcast channel One producer, many consumers

watch channel Latest-value state sharing

JoinSet

Manage group of spawned tasks

CancellationToken

Graceful shutdown signaling

Critical Async Mistakes

Mutex Guard Across Await

// BAD: std::Mutex guard held across .await — blocks executor async fn bad() { let guard = mutex.lock().unwrap(); some_async_op().await; // guard held across await! println!("{}", *guard); }

// GOOD: scope the lock, copy what you need async fn good() { let value = { let guard = mutex.lock().unwrap(); *guard // copy value }; // guard dropped here some_async_op().await; println!("{}", value); }

Blocking in Async Context

// BAD: blocking call in async context async fn bad() { std::thread::sleep(Duration::from_secs(1)); // blocks executor! std::fs::read_to_string("file.txt").unwrap(); // blocks! }

// GOOD: use async equivalents async fn good() { tokio::time::sleep(Duration::from_secs(1)).await; tokio::fs::read_to_string("file.txt").await.unwrap(); }

// For CPU work: spawn_blocking let result = tokio::task::spawn_blocking(|| heavy_computation()).await.unwrap();

Forgetting to Poll Futures

// BAD: future not polled — does nothing! fn process() { fetch_data(); // returns Future that's immediately dropped }

// GOOD: await it async fn process() { let data = fetch_data().await; }

Key Rule

// Sync for CPU-bound work, async for I/O-bound work // Don't hold locks across await points

Channel Disconnection

// Iterate until all senders drop for msg in rx { handle(msg); }

// Explicit matching for non-blocking match rx.try_recv() { Ok(msg) => handle(msg), Err(TryRecvError::Empty) => continue, Err(TryRecvError::Disconnected) => break, }

Thread Panic Handling

let handle = std::thread::spawn(|| risky_operation());

match handle.join() { Ok(result) => use_result(result), Err(e) => eprintln!("Thread panicked: {:?}", e), }

Graceful Shutdown Pattern

use tokio_util::sync::CancellationToken;

async fn run(token: CancellationToken) { loop { tokio::select! { _ = token.cancelled() => { tracing::info!("shutting down"); break; } msg = rx.recv() => { if let Some(msg) = msg { handle(msg).await; } } } } }

Source Transparency

This detail page is rendered from real SKILL.md content. Trust labels are metadata-based hints, not a safety guarantee.

Related Skills

Related by shared tags or category signals.

General

elementor-hooks

No summary provided by upstream source.

Repository SourceNeeds Review
General

elementor-themes

No summary provided by upstream source.

Repository SourceNeeds Review
General

elementor-controls

No summary provided by upstream source.

Repository SourceNeeds Review
General

elementor-forms

No summary provided by upstream source.

Repository SourceNeeds Review