-
Notifications
You must be signed in to change notification settings - Fork 118
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Auto merge of #352 - Redfire75369:gc/root-infrastructure, r=jdm
Added GC Tracing Infrastructure Fixes #346 Moved `mozjs::rust::Trace` to `mozjs::gc::trace::Traceable`, and added more implementations for smart pointers, wrappers, and collections. Added `mozjs::gc::trace::RootedTraceableSet`, `mozjs::gc::collections::RootableVec` and `mozjs::gc::collections::RootedVec`. Added `rooted_vec!` macro. Reorganised GC-related code in `mozjs`. I'm not too sure about the file structure change, but I think it's fine. If there's any more high-level rooted structures I can add, please do inform me.
- Loading branch information
Showing
16 changed files
with
1,005 additions
and
549 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,116 @@ | ||
use gc::{RootedTraceableSet, Traceable}; | ||
use jsapi::{Heap, JSTracer}; | ||
use mozjs_sys::jsgc::GCMethods; | ||
use rust::Handle; | ||
use std::ops::{Deref, DerefMut}; | ||
|
||
/// A vector of items to be rooted with `RootedVec`. | ||
/// Guaranteed to be empty when not rooted. | ||
pub struct RootableVec<T: Traceable> { | ||
v: Vec<T>, | ||
} | ||
|
||
impl<T: Traceable> RootableVec<T> { | ||
/// Create a vector of items of type T that can be rooted later. | ||
pub fn new_unrooted() -> RootableVec<T> { | ||
RootableVec { v: Vec::new() } | ||
} | ||
} | ||
|
||
unsafe impl<T: Traceable> Traceable for RootableVec<T> { | ||
unsafe fn trace(&self, trc: *mut JSTracer) { | ||
self.v.trace(trc); | ||
} | ||
} | ||
|
||
/// A vector of items rooted for the lifetime 'a. | ||
pub struct RootedVec<'a, T: Traceable + 'static> { | ||
root: &'a mut RootableVec<T>, | ||
} | ||
|
||
impl<'a, T: Traceable + 'static> RootedVec<'a, T> { | ||
pub fn new(root: &'a mut RootableVec<T>) -> RootedVec<'a, T> { | ||
unsafe { | ||
RootedTraceableSet::add(root); | ||
} | ||
RootedVec { root } | ||
} | ||
} | ||
|
||
impl<'a, T: Traceable + 'static> Drop for RootedVec<'a, T> { | ||
fn drop(&mut self) { | ||
self.clear(); | ||
unsafe { | ||
RootedTraceableSet::remove(self.root); | ||
} | ||
} | ||
} | ||
|
||
impl<'a, T: Traceable> Deref for RootedVec<'a, T> { | ||
type Target = Vec<T>; | ||
fn deref(&self) -> &Vec<T> { | ||
&self.root.v | ||
} | ||
} | ||
|
||
impl<'a, T: Traceable> DerefMut for RootedVec<'a, T> { | ||
fn deref_mut(&mut self) -> &mut Vec<T> { | ||
&mut self.root.v | ||
} | ||
} | ||
|
||
pub struct RootedTraceableBox<T: Traceable + 'static> { | ||
ptr: *mut T, | ||
} | ||
|
||
impl<T: Traceable + 'static> RootedTraceableBox<T> { | ||
pub fn new(traceable: T) -> RootedTraceableBox<T> { | ||
Self::from_box(Box::new(traceable)) | ||
} | ||
|
||
pub fn from_box(boxed_traceable: Box<T>) -> RootedTraceableBox<T> { | ||
let traceable = Box::into_raw(boxed_traceable); | ||
unsafe { | ||
RootedTraceableSet::add(traceable); | ||
} | ||
RootedTraceableBox { ptr: traceable } | ||
} | ||
} | ||
|
||
impl<T> RootedTraceableBox<Heap<T>> | ||
where | ||
Heap<T>: Traceable + 'static, | ||
T: GCMethods + Copy, | ||
{ | ||
pub fn handle(&self) -> Handle<T> { | ||
unsafe { Handle::from_raw((*self.ptr).handle()) } | ||
} | ||
} | ||
|
||
unsafe impl<T: Traceable + 'static> Traceable for RootedTraceableBox<T> { | ||
unsafe fn trace(&self, trc: *mut JSTracer) { | ||
(*self.ptr).trace(trc) | ||
} | ||
} | ||
|
||
impl<T: Traceable> Deref for RootedTraceableBox<T> { | ||
type Target = T; | ||
fn deref(&self) -> &T { | ||
unsafe { &*self.ptr } | ||
} | ||
} | ||
|
||
impl<T: Traceable> DerefMut for RootedTraceableBox<T> { | ||
fn deref_mut(&mut self) -> &mut T { | ||
unsafe { &mut *self.ptr } | ||
} | ||
} | ||
|
||
impl<T: Traceable + 'static> Drop for RootedTraceableBox<T> { | ||
fn drop(&mut self) { | ||
unsafe { | ||
RootedTraceableSet::remove(self.ptr); | ||
let _ = Box::from_raw(self.ptr); | ||
} | ||
} | ||
} |
Oops, something went wrong.