Pin

Rust’s `Pin` type and the broader async model are criticized as powerful but conceptually hard to grasp, largely because pinning only matters for a narrow class of non-`Unpin` types such as self-referential futures. Commenters debate whether this complexity is an inevitable consequence of Rust’s existing `&mut` semantics and zero-cost abstractions, or a design misstep that could have been avoided with different primitives like move constructors or better thread models. Many agree that tooling, documentation, and higher‑level abstractions make day‑to‑day use bearable, but several engineers still find async Rust significantly more demanding than async in languages like Go or JavaScript.

Scope of Pin and &mut in Rust

  • Several commenters note that &mut is “too powerful”: it allows moving via mem::swap, mem::replace, Option::take, etc.
  • Some argue that if moving through &mut were restricted (or those functions were unsafe), self‑referential values could be safe without Pin.
  • Others counter this would be a non‑starter: it would break large amounts of existing code and there are many move‑via‑reference patterns in the wild.

Move semantics, !Move, and alternative designs

  • Proposed alternative: a language‑level Move trait (analogous to Copy) or split traits for trivial vs custom moves, enabling self‑referential types and richer movement semantics.
  • Some see this as a cleaner long‑term design that could avoid Pin; others argue move constructors would be even more complex for users than Pin.
  • There is interest in “languages after Rust” that keep Rust’s safety but redesign moves, async, and comptime.

Async Rust, Pin, and ergonomics

  • Many see Pin as tightly tied to async/await and futures; some feel Rust’s async story is “half‑baked” and comparatively painful versus other languages.
  • Others insist that with macros (pin!, pin‑project) and idioms, Pin isn’t that hard in everyday async code.
  • A common pattern is “I add Pin where the compiler complains until it compiles,” reflecting weak intuition about when it’s needed.

Why Pin feels confusing

  • Pin alone doesn’t define what is allowed; its meaning depends on whether the inner type is Unpin and on custom APIs built around it.
  • Documentation is criticized as technically accurate but opaque, especially for Unpin and its double‑negative feel.
  • Users struggle with action‑at‑a‑distance: changes far from the error site can suddenly introduce Unpin constraints.
  • Suggestions include more practical, “systems‑engineering” docs and better teaching analogies (Velcro/smooth, magnets/non‑magnetic, stapling vs hooks).

Unpin and typestate

  • Clarified view:
    • Pin is a state of a pointer, not a property of the data.
    • For most types (those that are Unpin), Pin<T> is effectively a no‑op.
    • Only types that rely on their address (e.g., self‑referential, some futures) truly care about pinning.
  • Pinning vs non‑transitive pinning of fields (via projection) is acknowledged as necessary but confusing accidental complexity.

Use cases beyond async

  • Reported non‑async uses:
    • FFI where a C API gives a raw pointer that must not move.
    • OS or system types (e.g., mutex/futex implementations) whose docs require stable addresses across their lifetime.

Async vs threads and broader concurrency debate

  • One camp argues all async is a workaround for inefficient OS threads; “fix threads” and much complexity (including Pin) disappears.
  • Others respond that:
    • OS‑level fixes are unrealistic or outside language designers’ control.
    • Async offers benefits such as cancellation, fine‑grained control, and embedded/no‑alloc scenarios.
    • Thread APIs and context‑switch costs still limit simple “just use threads” answers.
  • Go’s model is cited both positively (no explicit async) and negatively (composability, context management, hidden overhead).

HN‑specific meta: titles and moderation

  • Many dislike the bare title “Pin” as uninformative or clickbaity; some want language tags like “[Rust] Pin”.
  • Others note HN guidelines favor original titles but are applied with varying strictness; debate centers on balancing fidelity vs clarity.