clojure-rs / ClojureRS

Clojure, implemented atop Rust (unofficial)
Apache License 2.0
950 stars 27 forks source link

A little writeup on the GC #11

Open divs1210 opened 4 years ago

divs1210 commented 4 years ago

Hi! This is a neat project! I'd like to understand how it handles memory management. Thanks!

scrabsha commented 4 years ago

As far as I know, it uses reference counting (Rc) to handle memory management. You may read documentation about Rc here and here.

@Tko1, any comment?

Tko1 commented 4 years ago

Yes, right now its simple naive reference counting. I know this is a hot topic, since in the long run, garbage collection is a big question, as we've all heard how Clojure involves lots of short lived allocations and heavily relies on the JVM's status as a world class garbage collector,

Our naive reference counting implementation will likely not stay. Currently there is also lots of indiscriminate copying going on that will also not stay. You'll notice me say in several comments on the project that I'm taking a much more iterative approach to this than I normally do, getting just a MVP version of each feature up and slowly improving each part as time goes on. I have several more sophisticated designs in mind, but I think it will be easier to make these sorts of decisions when there's enough of a prototype to really see all the constraints on the problem in a much more up-close and intimate way.

divs1210 commented 4 years ago

Got it. Honestly, I think RC is a great starting point, and may even be Good Enough in the long term. After all, MacOS and iOS have been using it for a long time without major issues.

scrabsha commented 4 years ago

I think, on the other hand that reference counting is fine, as long as we don't use it too much. For instance, in my opinion, it does not make any sense to wrap an integer (represented as i32 in the code) into a Rc, because, thanks to its small size, it can be copied instead of being Rc-cloned.

This applies to any type which is smaller than a pointer, so integers, characters, booleans (maybe floats but not sure).

A place where Rc may become important is when manipulating lists. In this case, it is totally ok to me to use it.

Also, we can guarantee that we won't have cycle referencing since that would require mutability. Clojure being functional, mutability does not exist.

On the other hand, even if we use them only at the right place, Rc may still slow down the program a bit. As such, I agree that we may have to implement a garbage collector in the future.

divs1210 commented 4 years ago

I found Clojit, a Clojure VM written in C. It uses MPS as its GC.

xorgy commented 2 months ago

There is https://www.mmtk.io/ which is written in Rust and has LXR. LXR is, as far as I can tell, basically the state of the art in general purpose garbage collectors. It seems to be especially well behaved on small heaps, which is something other low latency collectors (ZGC and Shenandoah) struggle with.