Skip to main content

Module chan

Module chan 

Source
Expand description

Channels — ported from src/runtime/chan.go.

Buffered and unbuffered channels backed by the same G/M/P scheduler used by goroutines. A goroutine that blocks on a channel send or receive is parked via gopark and resumed via goready; no OS thread is ever blocked.

§Public surface

let (tx, rx) = go_lib::chan::chan::<i32>(0);   // unbuffered
let (tx, rx) = go_lib::chan::chan::<i32>(16);  // buffered, capacity 16

tx.send(42_i32);
let v = rx.recv();  // Some(42); None means closed + empty
tx.close();

§Internals

Each channel is an Arc<Hchan<T>>. The lock-protected interior holds a VecDeque<T> ring buffer plus two wait queues (sendq / recvq) of Sudog records (one per blocked goroutine).

Locking uses RawMutex (not std::sync::Mutex) so that selectgo can hold multiple heterogeneous channel locks simultaneously without needing a typed MutexGuard<HchanState<T>> for each one.

§Blocking protocol

When a goroutine must block it:

  1. Allocates a Sudog from the pool.
  2. Heap-allocates a MaybeUninit<T> as the value staging area (sudog.elem).
  3. Enqueues the sudog in sendq / recvq (under the channel lock).
  4. Releases the lock.
  5. Calls goparkpark_fn sets GWAITING on g0’s stack.

The goroutine that completes the operation:

  • Reads or writes through sudog.elem.
  • Sets sudog.success and (*gp).param = sudog as *mut u8.
  • Calls goready, which spins until the target is GWAITING before marking it GRUNNABLE.

§Close semantics (matches Go)

  • Sending on a closed channel panics.
  • Receiving from a closed empty channel returns None.
  • Closing an already-closed channel panics.

Ported from hchan, chansend, chanrecv, closechan in runtime/chan.go.

Structs§

Receiver
The receiving half of a channel. Cheap to clone.
Sender
The sending half of a channel. Cheap to clone.

Functions§

chan
Create a new channel with the given buffer capacity.