kyren / gc-arena

Incremental garbage collection from safe Rust
Creative Commons Zero v1.0 Universal
436 stars 36 forks source link

Add GcWeak::trace_strong #91

Closed kyren closed 6 months ago

kyren commented 6 months ago

Allows someone to more easily decide at runtime whether a GcWeak should be treated as a strong pointer or a weak pointer during tracing.

This is not strictly required for piccolo to implement weak tables but it makes it a lot less obnoxious.

Includes a couple of drive by changes adding extra debug asserts, and a very small perf increase for GcWeak::resurrect.

kyren commented 6 months ago

As per discussion, also now includes another drive by change, requiring a Collection context for GcWeak::is_dropped. Mutation already has GcWeak::upgrade which is just strictly better, and it makes explaining what GcWeak::is_dropped does simpler (it can no longer be in conflict with GcWeak::upgrade).

kyren commented 6 months ago

After discussing this on Discord, we felt that it was too much of a footgun, and allowed you to do some confusing (if memory safe) things without understanding the consequences. Since using this method always requires implementing Collect::trace, which is unsafe, you can accomplish the same thing by carefully using GcWeak::from_ptr / Gc::from_ptr to swap between logically holding a GcWeak or a Gc. It is always safe to go from Gc to GcWeak, but going the other way requires a successful upgrade and a write barrier on the containing pointer to ensure that the object is re-traced, since it is (morally speaking) a mutation causing new values to be owned. Requiring the user to do this does not require (much) more unsafety, and is conceptually more consistent.