Hacker News new | ask | show | jobs
by lolinder 1301 days ago
This is the kind of attitude that will send Rust the way of C++.

Features cost, even optional features. No programming language can or should try to be everything to everyone: to attempt it is to serve no one very well at all, because you split the focus of the language development between too many use cases and you complicate the language so thoroughly that onboarding a new programmer becomes an exercise in re-education about which subsets are acceptable in the given organization.

Rust's niche is safely managing memory without a GC. If Rust adds a GC, even an optional one, it will have lost its soul.

3 comments

Not only that, but the borrow checker also handles safety concerns. Rust's concurrency safety story ("fearless concurrency") is literally built on the back of ownership and borrowing.
Oh, wow, yes. I confess I skimmed the part about green threads.

I think OP doesn't understand that runtime features like GC and green threads have a cost, and Rust is designed around a making it safe to avoid that cost. Most of Rust's features don't make sense in the context of a managed runtime—what you would be left with is basically a subset of OCaml with C-style syntax and optional mutability.

> Most of Rust's features don't make sense in the context of a managed runtime

I don’t think that’s entirely true actually (which is why linearity is explored in languages like haskell).

For instance Go makes it easier to trigger data races, which undermine memory safety. This is a managed langage “built for concurrency” where using concurrency means memory safety is at risk.

And that’s not recent news, Russ Cox himself wrote about it back in 2010: https://research.swtch.com/gorace

True, but linearity/affine types applied carefully in the context of a managed runtime would look quite different from Rust's borrow checker. The reason why Rust's borrow checker is so infamous is because Rust has to prove everything at compile time. Bringing affine types to a GC language would most likely involve making them opt-in (or only triggered in concurrent situations), while making linearity optional in Rust would undermine its foundations.
You can opt into runtime checking in Rust via interior mutability. Cell<>, RefCell<>, Rc<>, Arc<>, Mutex<>, Rwlock<> are constructs that involve varying levels of runtime checking - most of these will be way more efficient than GC. It's even simpler to use .clone() in order to effectively do away with any requirement for linearity.
(Cell<T> doesn’t actually do runtime checking)
Green threads have been totally superseded by current async support in Rust. That's why they're no longer part of the language itself.
Technically green threads were removed when rust was moved “down the stack” back before 1.0: green threads would mean requiring a runtime (scheduler & al) which is problematic when targeting foundational libraries and embedded programming, it makes integrating with other systems a lot harder.

Async being opt-in means the people who don’t need it can avoid it, though it’s not always great when e.g. the premier HTTP client of the ecosystem provides a “blocking” interface which iirc just starts a runtime and delegates to the async interface.

Ironically very early prerelease versions of Rust had a GC (and also Go-style fibers).

I think, however, a lot of people would love to see other GC languages take up the safety promises that Rust provides (especially concurrency).

A framework for "pluggable" and optional GC could be very helpful for dealing with the rare case of general graph-like data, where there really is no feasible alternative in terms of more explicit memory management. This will probably be done as a natural outcome of stable support for "local" allocators, which is already planned in Rust itself.