summaryrefslogtreecommitdiff
path: root/core/runtime/snapshot_util.rs
diff options
context:
space:
mode:
Diffstat (limited to 'core/runtime/snapshot_util.rs')
-rw-r--r--core/runtime/snapshot_util.rs259
1 files changed, 0 insertions, 259 deletions
diff --git a/core/runtime/snapshot_util.rs b/core/runtime/snapshot_util.rs
deleted file mode 100644
index e664856c6..000000000
--- a/core/runtime/snapshot_util.rs
+++ /dev/null
@@ -1,259 +0,0 @@
-// Copyright 2018-2023 the Deno authors. All rights reserved. MIT license.
-
-use std::path::Path;
-use std::path::PathBuf;
-use std::time::Instant;
-
-use crate::runtime::jsruntime::BUILTIN_SOURCES;
-use crate::runtime::RuntimeSnapshotOptions;
-use crate::ExtModuleLoaderCb;
-use crate::Extension;
-use crate::ExtensionFileSourceCode;
-use crate::JsRuntimeForSnapshot;
-use crate::RuntimeOptions;
-use crate::Snapshot;
-
-pub type CompressionCb = dyn Fn(&mut Vec<u8>, &[u8]);
-
-pub struct CreateSnapshotOptions {
- pub cargo_manifest_dir: &'static str,
- pub snapshot_path: PathBuf,
- pub startup_snapshot: Option<Snapshot>,
- pub extensions: Vec<Extension>,
- pub compression_cb: Option<Box<CompressionCb>>,
- pub snapshot_module_load_cb: Option<ExtModuleLoaderCb>,
-}
-
-pub struct CreateSnapshotOutput {
- /// Any files marked as LoadedFromFsDuringSnapshot are collected here and should be
- /// printed as 'cargo:rerun-if-changed' lines from your build script.
- pub files_loaded_during_snapshot: Vec<PathBuf>,
-}
-
-#[must_use = "The files listed by create_snapshot should be printed as 'cargo:rerun-if-changed' lines"]
-pub fn create_snapshot(
- create_snapshot_options: CreateSnapshotOptions,
-) -> CreateSnapshotOutput {
- let mut mark = Instant::now();
-
- let js_runtime = JsRuntimeForSnapshot::new(
- RuntimeOptions {
- startup_snapshot: create_snapshot_options.startup_snapshot,
- extensions: create_snapshot_options.extensions,
- ..Default::default()
- },
- RuntimeSnapshotOptions {
- snapshot_module_load_cb: create_snapshot_options.snapshot_module_load_cb,
- },
- );
- println!(
- "JsRuntime for snapshot prepared, took {:#?} ({})",
- Instant::now().saturating_duration_since(mark),
- create_snapshot_options.snapshot_path.display()
- );
- mark = Instant::now();
-
- let mut files_loaded_during_snapshot = vec![];
- for source in &*BUILTIN_SOURCES {
- if let ExtensionFileSourceCode::LoadedFromFsDuringSnapshot(path) =
- &source.code
- {
- files_loaded_during_snapshot.push(path.clone());
- }
- }
- for source in js_runtime
- .extensions()
- .iter()
- .flat_map(|e| vec![e.get_esm_sources(), e.get_js_sources()])
- .flatten()
- {
- if let ExtensionFileSourceCode::LoadedFromFsDuringSnapshot(path) =
- &source.code
- {
- files_loaded_during_snapshot.push(path.clone());
- }
- }
-
- let snapshot = js_runtime.snapshot();
- let snapshot_slice: &[u8] = &snapshot;
- println!(
- "Snapshot size: {}, took {:#?} ({})",
- snapshot_slice.len(),
- Instant::now().saturating_duration_since(mark),
- create_snapshot_options.snapshot_path.display()
- );
- mark = Instant::now();
-
- let maybe_compressed_snapshot: Box<dyn AsRef<[u8]>> =
- if let Some(compression_cb) = create_snapshot_options.compression_cb {
- let mut vec = vec![];
-
- vec.extend_from_slice(
- &u32::try_from(snapshot.len())
- .expect("snapshot larger than 4gb")
- .to_le_bytes(),
- );
-
- (compression_cb)(&mut vec, snapshot_slice);
-
- println!(
- "Snapshot compressed size: {}, took {:#?} ({})",
- vec.len(),
- Instant::now().saturating_duration_since(mark),
- create_snapshot_options.snapshot_path.display()
- );
- mark = std::time::Instant::now();
-
- Box::new(vec)
- } else {
- Box::new(snapshot_slice)
- };
-
- std::fs::write(
- &create_snapshot_options.snapshot_path,
- &*maybe_compressed_snapshot,
- )
- .unwrap();
- println!(
- "Snapshot written, took: {:#?} ({})",
- Instant::now().saturating_duration_since(mark),
- create_snapshot_options.snapshot_path.display(),
- );
- CreateSnapshotOutput {
- files_loaded_during_snapshot,
- }
-}
-
-pub type FilterFn = Box<dyn Fn(&PathBuf) -> bool>;
-
-pub fn get_js_files(
- cargo_manifest_dir: &'static str,
- directory: &str,
- filter: Option<FilterFn>,
-) -> Vec<PathBuf> {
- let manifest_dir = Path::new(cargo_manifest_dir);
- let mut js_files = std::fs::read_dir(directory)
- .unwrap()
- .map(|dir_entry| {
- let file = dir_entry.unwrap();
- manifest_dir.join(file.path())
- })
- .filter(|path| {
- path.extension().unwrap_or_default() == "js"
- && filter.as_ref().map(|filter| filter(path)).unwrap_or(true)
- })
- .collect::<Vec<PathBuf>>();
- js_files.sort();
- js_files
-}
-
-fn data_error_to_panic(err: v8::DataError) -> ! {
- match err {
- v8::DataError::BadType { actual, expected } => {
- panic!(
- "Invalid type for snapshot data: expected {expected}, got {actual}"
- );
- }
- v8::DataError::NoData { expected } => {
- panic!("No data for snapshot data: expected {expected}");
- }
- }
-}
-
-pub(crate) struct SnapshottedData {
- pub module_map_data: v8::Global<v8::Array>,
- pub module_handles: Vec<v8::Global<v8::Module>>,
-}
-
-static MODULE_MAP_CONTEXT_DATA_INDEX: usize = 0;
-
-pub(crate) fn get_snapshotted_data(
- scope: &mut v8::HandleScope<()>,
- context: v8::Local<v8::Context>,
-) -> SnapshottedData {
- let mut scope = v8::ContextScope::new(scope, context);
-
- // The 0th element is the module map itself, followed by X number of module
- // handles. We need to deserialize the "next_module_id" field from the
- // map to see how many module handles we expect.
- let result = scope.get_context_data_from_snapshot_once::<v8::Array>(
- MODULE_MAP_CONTEXT_DATA_INDEX,
- );
-
- let val = match result {
- Ok(v) => v,
- Err(err) => data_error_to_panic(err),
- };
-
- let next_module_id = {
- let info_data: v8::Local<v8::Array> =
- val.get_index(&mut scope, 1).unwrap().try_into().unwrap();
- info_data.length()
- };
-
- // Over allocate so executing a few scripts doesn't have to resize this vec.
- let mut module_handles = Vec::with_capacity(next_module_id as usize + 16);
- for i in 1..=next_module_id {
- match scope.get_context_data_from_snapshot_once::<v8::Module>(i as usize) {
- Ok(val) => {
- let module_global = v8::Global::new(&mut scope, val);
- module_handles.push(module_global);
- }
- Err(err) => data_error_to_panic(err),
- }
- }
-
- SnapshottedData {
- module_map_data: v8::Global::new(&mut scope, val),
- module_handles,
- }
-}
-
-pub(crate) fn set_snapshotted_data(
- scope: &mut v8::HandleScope<()>,
- context: v8::Global<v8::Context>,
- snapshotted_data: SnapshottedData,
-) {
- let local_context = v8::Local::new(scope, context);
- let local_data = v8::Local::new(scope, snapshotted_data.module_map_data);
- let offset = scope.add_context_data(local_context, local_data);
- assert_eq!(offset, MODULE_MAP_CONTEXT_DATA_INDEX);
-
- for (index, handle) in snapshotted_data.module_handles.into_iter().enumerate()
- {
- let module_handle = v8::Local::new(scope, handle);
- let offset = scope.add_context_data(local_context, module_handle);
- assert_eq!(offset, index + 1);
- }
-}
-
-/// Returns an isolate set up for snapshotting.
-pub(crate) fn create_snapshot_creator(
- external_refs: &'static v8::ExternalReferences,
- maybe_startup_snapshot: Option<Snapshot>,
-) -> v8::OwnedIsolate {
- if let Some(snapshot) = maybe_startup_snapshot {
- match snapshot {
- Snapshot::Static(data) => {
- v8::Isolate::snapshot_creator_from_existing_snapshot(
- data,
- Some(external_refs),
- )
- }
- Snapshot::JustCreated(data) => {
- v8::Isolate::snapshot_creator_from_existing_snapshot(
- data,
- Some(external_refs),
- )
- }
- Snapshot::Boxed(data) => {
- v8::Isolate::snapshot_creator_from_existing_snapshot(
- data,
- Some(external_refs),
- )
- }
- }
- } else {
- v8::Isolate::snapshot_creator(Some(external_refs))
- }
-}