mirror of
https://github.com/denoland/rusty_v8.git
synced 2024-11-21 15:04:33 -05:00
Refactored OwnedIsolate construction code in prep for lockers (#1442)
Pulled the isolate construction changes from the locker API to a separate PR. Co-authored-by: Matt Mastracci <matthew@mastracci.com>
This commit is contained in:
parent
f42a8e41e0
commit
cdeba6ac57
2 changed files with 91 additions and 70 deletions
155
src/isolate.rs
155
src/isolate.rs
|
@ -608,6 +608,20 @@ impl Isolate {
|
|||
);
|
||||
}
|
||||
|
||||
fn new_impl(params: CreateParams) -> *mut Isolate {
|
||||
crate::V8::assert_initialized();
|
||||
let (raw_create_params, create_param_allocations) = params.finalize();
|
||||
let cxx_isolate = unsafe { v8__Isolate__New(&raw_create_params) };
|
||||
let isolate = unsafe { &mut *cxx_isolate };
|
||||
isolate.initialize(create_param_allocations);
|
||||
cxx_isolate
|
||||
}
|
||||
|
||||
pub(crate) fn initialize(&mut self, create_param_allocations: Box<dyn Any>) {
|
||||
self.assert_embedder_data_slot_count_and_offset_correct();
|
||||
self.create_annex(create_param_allocations);
|
||||
}
|
||||
|
||||
/// Creates a new isolate. Does not change the currently entered
|
||||
/// isolate.
|
||||
///
|
||||
|
@ -617,17 +631,7 @@ impl Isolate {
|
|||
/// V8::initialize() must have run prior to this.
|
||||
#[allow(clippy::new_ret_no_self)]
|
||||
pub fn new(params: CreateParams) -> OwnedIsolate {
|
||||
crate::V8::assert_initialized();
|
||||
let (raw_create_params, create_param_allocations) = params.finalize();
|
||||
let cxx_isolate = unsafe { v8__Isolate__New(&raw_create_params) };
|
||||
let mut owned_isolate = OwnedIsolate::new(cxx_isolate);
|
||||
owned_isolate.assert_embedder_data_slot_count_and_offset_correct();
|
||||
ScopeData::new_root(&mut owned_isolate);
|
||||
owned_isolate.create_annex(create_param_allocations);
|
||||
unsafe {
|
||||
owned_isolate.enter();
|
||||
}
|
||||
owned_isolate
|
||||
OwnedIsolate::new(Self::new_impl(params))
|
||||
}
|
||||
|
||||
#[allow(clippy::new_ret_no_self)]
|
||||
|
@ -687,6 +691,32 @@ impl Isolate {
|
|||
self.set_data_internal(Self::ANNEX_SLOT, annex_ptr as *mut _);
|
||||
}
|
||||
|
||||
unsafe fn dispose_annex(&mut self) {
|
||||
// Set the `isolate` pointer inside the annex struct to null, so any
|
||||
// IsolateHandle that outlives the isolate will know that it can't call
|
||||
// methods on the isolate.
|
||||
let annex = self.get_annex_mut();
|
||||
{
|
||||
let _lock = annex.isolate_mutex.lock().unwrap();
|
||||
annex.isolate = null_mut();
|
||||
}
|
||||
|
||||
// Clear slots and drop owned objects that were taken out of `CreateParams`.
|
||||
annex.create_param_allocations = Box::new(());
|
||||
annex.slots.clear();
|
||||
|
||||
// Run through any remaining guaranteed finalizers.
|
||||
for finalizer in annex.finalizer_map.drain() {
|
||||
if let FinalizerCallback::Guaranteed(callback) = finalizer {
|
||||
callback();
|
||||
}
|
||||
}
|
||||
|
||||
// Subtract one from the Arc<IsolateAnnex> reference count.
|
||||
unsafe { Arc::from_raw(annex) };
|
||||
self.set_data(0, null_mut());
|
||||
}
|
||||
|
||||
#[inline(always)]
|
||||
fn get_annex(&self) -> &IsolateAnnex {
|
||||
let annex_ptr =
|
||||
|
@ -770,6 +800,14 @@ impl Isolate {
|
|||
slots[slot as usize] = data;
|
||||
}
|
||||
|
||||
pub(crate) fn init_scope_root(&mut self) {
|
||||
ScopeData::new_root(self);
|
||||
}
|
||||
|
||||
pub(crate) fn dispose_scope_root(&mut self) {
|
||||
ScopeData::drop_root(self);
|
||||
}
|
||||
|
||||
/// Returns a pointer to the `ScopeData` struct for the current scope.
|
||||
#[inline(always)]
|
||||
pub(crate) fn get_current_scope_data(&self) -> Option<NonNull<ScopeData>> {
|
||||
|
@ -1276,41 +1314,12 @@ impl Isolate {
|
|||
}
|
||||
}
|
||||
|
||||
unsafe fn clear_scope_and_annex(&mut self) {
|
||||
// Drop the scope stack.
|
||||
ScopeData::drop_root(self);
|
||||
|
||||
// Set the `isolate` pointer inside the annex struct to null, so any
|
||||
// IsolateHandle that outlives the isolate will know that it can't call
|
||||
// methods on the isolate.
|
||||
let annex = self.get_annex_mut();
|
||||
{
|
||||
let _lock = annex.isolate_mutex.lock().unwrap();
|
||||
annex.isolate = null_mut();
|
||||
}
|
||||
|
||||
// Clear slots and drop owned objects that were taken out of `CreateParams`.
|
||||
annex.create_param_allocations = Box::new(());
|
||||
annex.slots.clear();
|
||||
|
||||
// Run through any remaining guaranteed finalizers.
|
||||
for finalizer in annex.finalizer_map.drain() {
|
||||
if let FinalizerCallback::Guaranteed(callback) = finalizer {
|
||||
callback();
|
||||
}
|
||||
}
|
||||
|
||||
// Subtract one from the Arc<IsolateAnnex> reference count.
|
||||
Arc::from_raw(annex);
|
||||
self.set_data(0, null_mut());
|
||||
}
|
||||
|
||||
/// Disposes the isolate. The isolate must not be entered by any
|
||||
/// thread to be disposable.
|
||||
unsafe fn dispose(&mut self) {
|
||||
// No test case in rusty_v8 show this, but there have been situations in
|
||||
// deno where dropping Annex before the states causes a segfault.
|
||||
v8__Isolate__Dispose(self)
|
||||
v8__Isolate__Dispose(self);
|
||||
}
|
||||
|
||||
/// Take a heap snapshot. The callback is invoked one or more times
|
||||
|
@ -1589,8 +1598,18 @@ pub struct OwnedIsolate {
|
|||
|
||||
impl OwnedIsolate {
|
||||
pub(crate) fn new(cxx_isolate: *mut Isolate) -> Self {
|
||||
let mut isolate = Self::new_already_entered(cxx_isolate);
|
||||
unsafe {
|
||||
isolate.enter();
|
||||
}
|
||||
isolate
|
||||
}
|
||||
|
||||
pub(crate) fn new_already_entered(cxx_isolate: *mut Isolate) -> Self {
|
||||
let cxx_isolate = NonNull::new(cxx_isolate).unwrap();
|
||||
Self { cxx_isolate }
|
||||
let mut owned_isolate = Self { cxx_isolate };
|
||||
owned_isolate.init_scope_root();
|
||||
owned_isolate
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1608,12 +1627,38 @@ impl Drop for OwnedIsolate {
|
|||
"v8::OwnedIsolate instances must be dropped in the reverse order of creation. They are entered upon creation and exited upon being dropped."
|
||||
);
|
||||
self.exit();
|
||||
self.cxx_isolate.as_mut().clear_scope_and_annex();
|
||||
self.cxx_isolate.as_mut().dispose();
|
||||
self.dispose_scope_root();
|
||||
self.dispose_annex();
|
||||
self.dispose();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
impl OwnedIsolate {
|
||||
/// Creates a snapshot data blob.
|
||||
/// This must not be called from within a handle scope.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// Panics if the isolate was not created using [`Isolate::snapshot_creator`]
|
||||
#[inline(always)]
|
||||
pub fn create_blob(
|
||||
mut self,
|
||||
function_code_handling: FunctionCodeHandling,
|
||||
) -> Option<StartupData> {
|
||||
let mut snapshot_creator =
|
||||
self.get_annex_mut().maybe_snapshot_creator.take().unwrap();
|
||||
unsafe {
|
||||
self.dispose_scope_root();
|
||||
self.dispose_annex();
|
||||
}
|
||||
// The isolate is owned by the snapshot creator; we need to forget it
|
||||
// here as the snapshot creator will drop it when running the destructor.
|
||||
std::mem::forget(self);
|
||||
snapshot_creator.create_blob(function_code_handling)
|
||||
}
|
||||
}
|
||||
|
||||
impl Deref for OwnedIsolate {
|
||||
type Target = Isolate;
|
||||
fn deref(&self) -> &Self::Target {
|
||||
|
@ -1639,28 +1684,6 @@ impl AsMut<Isolate> for Isolate {
|
|||
}
|
||||
}
|
||||
|
||||
impl OwnedIsolate {
|
||||
/// Creates a snapshot data blob.
|
||||
/// This must not be called from within a handle scope.
|
||||
///
|
||||
/// # Panics
|
||||
///
|
||||
/// Panics if the isolate was not created using [`Isolate::snapshot_creator`]
|
||||
#[inline(always)]
|
||||
pub fn create_blob(
|
||||
mut self,
|
||||
function_code_handling: FunctionCodeHandling,
|
||||
) -> Option<StartupData> {
|
||||
let mut snapshot_creator =
|
||||
self.get_annex_mut().maybe_snapshot_creator.take().unwrap();
|
||||
unsafe { self.cxx_isolate.as_mut().clear_scope_and_annex() };
|
||||
// The isolate is owned by the snapshot creator; we need to forget it
|
||||
// here as the snapshot creator will drop it when running the destructor.
|
||||
std::mem::forget(self);
|
||||
snapshot_creator.create_blob(function_code_handling)
|
||||
}
|
||||
}
|
||||
|
||||
impl HeapStatistics {
|
||||
#[inline(always)]
|
||||
pub fn total_heap_size(&self) -> usize {
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
use crate::external_references::ExternalReferences;
|
||||
use crate::isolate_create_params::raw;
|
||||
use crate::scope::data::ScopeData;
|
||||
use crate::support::char;
|
||||
use crate::support::int;
|
||||
use crate::support::Allocated;
|
||||
|
@ -144,9 +143,8 @@ impl SnapshotCreator {
|
|||
|
||||
let isolate_ptr =
|
||||
unsafe { v8__SnapshotCreator__GetIsolate(&snapshot_creator) };
|
||||
let mut owned_isolate = OwnedIsolate::new(isolate_ptr);
|
||||
ScopeData::new_root(&mut owned_isolate);
|
||||
owned_isolate.create_annex(create_param_allocations);
|
||||
let mut owned_isolate = OwnedIsolate::new_already_entered(isolate_ptr);
|
||||
owned_isolate.initialize(create_param_allocations);
|
||||
owned_isolate.set_snapshot_creator(snapshot_creator);
|
||||
owned_isolate
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue