Fugrip is a Rust implementation of FUGC (Fil's Unbelievable Garbage Collector), a sophisticated parallel concurrent on-the-fly grey-stack Dijkstra accurate non-moving garbage collector originally designed for the Verse programming language.
🚧 Active Development: The project is undergoing a strategic refactoring to push all MMTk types behind an impermeable "blackwall" of opaque handles with zero-cost abstractions.
- Zero-Cost Opaque Abstraction: All MMTk types hidden behind opaque handles
- Swappable Backends: jemalloc, MMTk, or custom allocators via compile-time dispatch
- Perfect Type Safety: MMTk types never escape to external code
- Deadlock-Free Handshakes: Lock-free coordination protocol
- FUGC 8-Step Protocol: Complete concurrent collection implementation
Legacy code mixed MMTk types (Address, ObjectReference) with opaque handles, creating:
- ❌ Type leakage defeating abstraction benefits
- ❌ Build failures from incompatible type systems
- ❌ Impossible backend swapping (MMTk types everywhere)
- ❌ Complex migration path for external users
Strategy: Migrate modules from foundation upward, creating a forcing function where external code must use opaque handles.
Layer 1: Foundation (Start Here)
- ✅
alloc_facade.rs- Core opaque API ⭐ FIRST TARGET - 🔄
types.rs- Custom types for non-MMTk backend - 🔄
core.rs- Object headers and basic types
Layer 2: Core Services
4. ⏳ test_utils.rs - Testing infrastructure
5. ⏳ debug_test.rs - Debugging utilities
Layer 3: Allocation & Memory
6. ⏳ allocator.rs - Main allocation interface
7. ⏳ facade_allocator.rs - Facade-based allocator
8. ⏳ modern_allocator.rs - Modern allocation interface
Layer 4: GC Coordination
9. ⏳ concurrent/ modules - Marking, barriers, tricolor
10. ⏳ fugc_coordinator/ - FUGC protocol coordination
11. ⏳ memory_management/ - Finalizers, weak refs, free objects
Layer 5: High-Level Features
12. ⏳ safepoint/ - Safepoint management
13. ⏳ plan.rs - Plan management
14. ⏳ binding/ - MMTk binding layer
✅ Completed:
- Opaque handle types (
MutatorHandle,PlanHandle) - Feature flag infrastructure (
use_mmtkvsuse_jemalloc) - Basic allocation facade with handle registry
- Zero-cost dispatch architecture
- Public API cleanup (no MMTk re-exports in
lib.rs)
🔄 In Progress:
alloc_facade.rscore functionality completion- Pure opaque example demonstration
compat.rselimination planning
📋 Next Steps:
- Complete
alloc_facade.rs- remove allcompatimports - Create working
examples/pure_opaque_demo.rs - Verify zero-cost:
assert_eq!(size_of::<MutatorHandle>(), size_of::<usize>()) - Begin Layer 2 migration (
test_utils.rs)
# Build with jemalloc backend (opaque handles only)
cargo build --no-default-features --features use_jemalloc
# Build with MMTk backend (legacy + opaque)
cargo build --features use_mmtk
# Test opaque abstraction
cargo run --example pure_opaque_demo --features use_jemalloc
# Run tests
cargo nextest run --features smokeThe opaque handle system guarantees zero runtime overhead:
// Handles are just numbers - perfect zero-cost abstraction
assert_eq!(size_of::<MutatorHandle>(), size_of::<usize>());
assert_eq!(size_of::<PlanHandle>(), size_of::<usize>());
// All dispatch happens at compile-time via feature flags
#[cfg(feature = "use_mmtk")]
fn allocate_impl(handle: MutatorHandle) -> *mut u8 { /* MMTk path */ }
#[cfg(not(feature = "use_mmtk"))]
fn allocate_impl(handle: MutatorHandle) -> *mut u8 { /* jemalloc path */ }// ❌ MMTk types exposed everywhere
use mmtk::util::{Address, ObjectReference};
use crate::compat::{Address, ObjectReference};
fn allocate(mutator: &Mutator<RustVM>) -> ObjectReference {
// Direct MMTk usage - not swappable
}// ✅ Only opaque handles exposed
use crate::alloc_facade::{MutatorHandle, allocate};
fn allocate_object(mutator: MutatorHandle) -> *mut u8 {
// Handle-based allocation - swappable backends
}- Zero Runtime Overhead: All dispatch at compile-time
- Perfect Abstraction: MMTk completely hidden behind blackwall
- Swappable Backends: Easy to switch allocators without code changes
- Type Safety: Invalid states unrepresentable
- Clean APIs: Simple handle-based interface
- Future-Proof: Easy to extend without breaking changes
When working on migration:
- Never import
compattypes in new code - Use opaque handles exclusively (
MutatorHandle,PlanHandle) - Test both backends (
use_mmtkanduse_jemalloc) - Verify zero-cost with size assertions
- Follow bottom-up migration order
See MMTK_BLACKWALL_ROADMAP.md for detailed migration instructions.
- Architecture: See
CLAUDE.mdfor detailed technical documentation - Migration: See
MMTK_BLACKWALL_ROADMAP.mdfor step-by-step migration guide - FUGC Protocol: 8-step concurrent collection algorithm documentation
- Testing: Feature flag organization and protocol validation