Skip to content

Replace type_name with TypeId using typeid crate - #100

Merged
nekevss merged 2 commits into
boa-dev:mainfrom
shruti2522:branded-collector/TypeId
Aug 13, 2026
Merged

Replace type_name with TypeId using typeid crate#100
nekevss merged 2 commits into
boa-dev:mainfrom
shruti2522:branded-collector/TypeId

Conversation

@shruti2522

Copy link
Copy Markdown
Contributor

Related to #98 (comment)

Replaced the string based type_name method with the standard core::any::TypeId. This makes downcasting safer and fully supports #![no_std] environments without cross thread memory bugs.

Because TypeId requires a 'static lifetime (and our GC pointers use a temporary 'gc lifetime), added a StaticId proxy type to safely bridge the gap

  • added type StaticId to the Trace trait. Every GC type now links to a safe 'static version of itself (for example, Gc<'gc, T> links to Gc<'static, T::StaticId>)
  • GcBox uses TypeId instead of strings. When Gc::is<U>() is called, it safely checks the type using TypeId::of::<U::StaticId>()
  • To satisfy the compiler's size requirements without causing infinite type resolution loops, used Vec as the static proxy for slices ([T]) and String as the proxy for str
  • Removed the thread_local! requirement in the null collector to prevent cross thread uaf bugs and brings back full #![no_std] support.

actual_type_name == core::any::type_name::<U>()
pub fn is<U: Trace + ?Sized>(&self) -> bool {
let actual_type_id = unsafe { (*self.ptr.as_ptr().as_ptr()).0.type_id };
actual_type_id == core::any::TypeId::of::<U::StaticId>()

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Huh, why can't we use TypeId::of::<U>() here?

@shruti2522 shruti2522 Aug 13, 2026

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Replced StaticId with dtonlay's typeid crate, everything compiles, certainly an improvement on the earlier approach.
It gives us a TypeId equivalent that works without requiring 'static, so U no longer needs the StaticId proxy at all

Copilot AI lite review requested due to automatic review settings August 13, 2026 03:25
@shruti2522
shruti2522 force-pushed the branded-collector/TypeId branch 2 times, most recently from 788e873 to f579642 Compare August 13, 2026 03:31
@shruti2522
shruti2522 force-pushed the branded-collector/TypeId branch from f579642 to 40363d4 Compare August 13, 2026 03:33

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR replaces string-based runtime type checks (type_name) with TypeId-based checks (via the typeid crate) in the branded collectors, aiming to make Gc::is/downcasting safer and more compatible with #![no_std].

Changes:

  • Store a runtime type identifier in GcBox and switch Gc::is to compare TypeIds instead of type_name strings.
  • Update branded Trace blanket impls and add/adjust safety documentation in the null collector’s global mutation context.
  • Introduce the typeid dependency and update lockfile accordingly.

Reviewed changes

Copilot reviewed 11 out of 12 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
oscars/src/collectors/null_collector_branded/weak.rs Adds comment about static proxy mapping for weak pointers.
oscars/src/collectors/null_collector_branded/trace.rs Updates several Trace blanket impl bounds and comments; adds Trace for str.
oscars/src/collectors/null_collector_branded/mutation_ctx.rs Expands safety documentation around MutationContext::global() TLS usage.
oscars/src/collectors/null_collector_branded/gc.rs Switches Gc::is from string comparison to typeid::of.
oscars/src/collectors/null_collector_branded/gc_box.rs Stores TypeId in GcBox and updates constructor bounds.
oscars/src/collectors/null_collector_branded/ephemeron.rs Adds comment describing intended static proxy mapping.
oscars/src/collectors/null_collector_branded/cell.rs Uses Clone trait for GcRef; adds comment about static mapping.
oscars/src/collectors/mark_sweep_branded/weak.rs Minor simplification in is_upgradable; adds comment about static proxy mapping.
oscars/src/collectors/mark_sweep_branded/trace.rs Updates several Trace blanket impl bounds/comments; adds Trace for str.
oscars/src/collectors/mark_sweep_branded/tests/uaf.rs Adds comment describing intended static proxy mapping for test type.
oscars/src/collectors/mark_sweep_branded/tests/mod.rs Adds comment on Trace impl for JsObject.
oscars/src/collectors/mark_sweep_branded/mod.rs Adds Default impl for Collector.
oscars/src/collectors/mark_sweep_branded/gc.rs Switches Gc::is to typeid::of; updates Trace impl signature.
oscars/src/collectors/mark_sweep_branded/gc_box.rs Stores TypeId in GcBox and updates constructor bounds.
oscars/src/collectors/mark_sweep_branded/ephemeron.rs Adds comment describing intended static proxy mapping.
oscars/src/collectors/mark_sweep_branded/cell.rs Adds comment about branding/static mapping for GcRefCell.
oscars/Cargo.toml Adds the typeid dependency.
Cargo.lock Records the new typeid package in the lockfile.
Suppressed comments (3)

oscars/src/collectors/mark_sweep_branded/trace.rs:272

  • PhantomData<T> is a marker and has no runtime data to trace, so requiring T: 'static here is an unnecessary restriction. It also conflicts with the unbranded collector’s Trace for PhantomData<T> blanket impl (collectors/mark_sweep/trace.rs:398-401). Unless there is a concrete reason to restrict this, consider restoring the unrestricted impl.

unsafe impl Trace for core::any::TypeId {
    #[inline]
    unsafe fn trace(&self, _tracer: &mut Tracer) {}
}

oscars/src/collectors/null_collector_branded/trace.rs:194

  • PhantomData<T> is a marker and has no runtime data to trace, so requiring T: 'static here is an unnecessary restriction (and inconsistent with the unbranded collector’s blanket impl in collectors/mark_sweep/trace.rs:398-401). Unless there is a concrete reason to restrict this, consider restoring the unrestricted impl.

unsafe impl<T: Trace + Default> Trace for Cell<T> {
    unsafe fn trace(&self, tracer: &mut Tracer) {
        let v = self.take();
        v.trace(tracer);

oscars/src/collectors/mark_sweep_branded/trace.rs:426

  • This comment says “Gc requires &mut self to trace”, but Trace::trace takes &self and Gc itself is traced via a shared reference. If the intent is to forbid branded GC pointers in BTreeSet by using the T: 'static bound, the comment should state that instead to avoid spreading incorrect guidance.
    use crate::collectors::mark_sweep_branded::{Trace, Tracer};
    use icu_locale_core::{LanguageIdentifier, Locale};


💡 Add a code-review agent skill or configure MCP servers for context-aware, tailored reviews. Learn more in the docs.

Comment thread oscars/src/collectors/mark_sweep_branded/gc_box.rs Outdated
Comment thread oscars/src/collectors/null_collector_branded/gc_box.rs Outdated
Comment thread oscars/src/collectors/mark_sweep_branded/trace.rs Outdated
Comment thread oscars/src/collectors/null_collector_branded/trace.rs Outdated
Comment thread oscars/src/collectors/null_collector_branded/mutation_ctx.rs
Comment thread oscars/src/collectors/mark_sweep_branded/gc.rs
Comment thread oscars/src/collectors/mark_sweep_branded/trace.rs
@nekevss
nekevss merged commit ed5f692 into boa-dev:main Aug 13, 2026
4 checks passed
@shruti2522 shruti2522 changed the title Replace type_name with TypeId using StaticId proxies Replace type_name with TypeId using typeid crate Aug 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants