Browse Source

fix: ensure app load is limited to real asar files when appropriate (#39807)

* fix: ensure app load is limited to real asar files when appropriate

Co-authored-by: Samuel Attard <[email protected]>

* chore: update line numbers in node test

* chore: update patches

---------

Co-authored-by: trop[bot] <37223003+trop[bot]@users.noreply.github.com>
Co-authored-by: Samuel Attard <[email protected]>
Co-authored-by: PatchUp <73610968+patchup[bot]@users.noreply.github.com>
trop[bot] 1 year ago
parent
commit
b9e0f097bd

+ 3 - 1
lib/asar/fs-wrapper.ts

@@ -27,7 +27,7 @@ const cachedArchives = new Map<string, NodeJS.AsarArchive>();
 const getOrCreateArchive = (archivePath: string) => {
   const isCached = cachedArchives.has(archivePath);
   if (isCached) {
-    return cachedArchives.get(archivePath);
+    return cachedArchives.get(archivePath)!;
   }
 
   try {
@@ -39,6 +39,8 @@ const getOrCreateArchive = (archivePath: string) => {
   }
 };
 
+process._getOrCreateArchive = getOrCreateArchive;
+
 const asarRe = /\.asar/i;
 
 // Separate asar package's path from full path.

+ 9 - 0
lib/browser/init.ts

@@ -84,11 +84,20 @@ const v8Util = process._linkedBinding('electron_common_v8_util');
 let packagePath = null;
 let packageJson = null;
 const searchPaths: string[] = v8Util.getHiddenValue(global, 'appSearchPaths');
+const searchPathsOnlyLoadASAR: boolean = v8Util.getHiddenValue(global, 'appSearchPathsOnlyLoadASAR');
+// Borrow the _getOrCreateArchive asar helper
+const getOrCreateArchive = process._getOrCreateArchive;
+delete process._getOrCreateArchive;
 
 if (process.resourcesPath) {
   for (packagePath of searchPaths) {
     try {
       packagePath = path.join(process.resourcesPath, packagePath);
+      if (searchPathsOnlyLoadASAR) {
+        if (!getOrCreateArchive?.(packagePath)) {
+          continue;
+        }
+      }
       packageJson = Module._load(path.join(packagePath, 'package.json'));
       break;
     } catch {

+ 2 - 2
patches/node/chore_update_fixtures_errors_force_colors_snapshot.patch

@@ -11,7 +11,7 @@ trying to see whether or not the lines are greyed out. One possibility
 would be to upstream a changed test that doesn't hardcode line numbers.
 
 diff --git a/test/fixtures/errors/force_colors.snapshot b/test/fixtures/errors/force_colors.snapshot
-index 0334a0b4faa3633aa8617b9538873e7f3540513b..28ba4d18fe5e3caf4d904a055550110fd4faa609 100644
+index 0334a0b4faa3633aa8617b9538873e7f3540513b..7f85ddc507c9c38ce85ed2a48f8152eef168717b 100644
 --- a/test/fixtures/errors/force_colors.snapshot
 +++ b/test/fixtures/errors/force_colors.snapshot
 @@ -4,11 +4,12 @@ throw new Error('Should include grayed stack trace')
@@ -27,7 +27,7 @@ index 0334a0b4faa3633aa8617b9538873e7f3540513b..28ba4d18fe5e3caf4d904a055550110f
 +    at Object..js (node:internal*modules*cjs*loader:1326:10)
 +    at Module.load (node:internal*modules*cjs*loader:1126:32)
 +    at node:internal*modules*cjs*loader:967:12
-+    at Function._load (node:electron*js2c*asar_bundle:756:32)
++    at Function._load (node:electron*js2c*asar_bundle:757:32)
 +    at Function.executeUserEntryPoint [as runMain] (node:internal*modules*run_main:96:12)
      at node:internal*main*run_main_module:23:47
  

+ 7 - 0
shell/common/node_bindings.cc

@@ -523,6 +523,13 @@ std::shared_ptr<node::Environment> NodeBindings::CreateEnvironment(
                          electron::fuses::IsOnlyLoadAppFromAsarEnabled()
                              ? app_asar_search_paths
                              : search_paths));
+    context->Global()->SetPrivate(
+        context,
+        v8::Private::ForApi(
+            isolate, gin::ConvertToV8(isolate, "appSearchPathsOnlyLoadASAR")
+                         .As<v8::String>()),
+        gin::ConvertToV8(isolate,
+                         electron::fuses::IsOnlyLoadAppFromAsarEnabled()));
   }
 
   base::FilePath resources_path = GetResourcesPath();

+ 1 - 0
typings/internal-ambient.d.ts

@@ -244,6 +244,7 @@ declare namespace NodeJS {
     // Additional properties
     _firstFileName?: string;
     _serviceStartupScript: string;
+    _getOrCreateArchive?: (path: string) => NodeJS.AsarArchive | null;
 
     helperExecPath: string;
     mainModule?: NodeJS.Module | undefined;