sandbox - make lazyEnv fit for sandbox use

This commit is contained in:
Benjamin Pasero
2020-08-24 11:09:22 +02:00
parent 890d7c61af
commit 653e7e26df
6 changed files with 69 additions and 58 deletions

View File

@@ -33,8 +33,8 @@ const bootstrapWindow = (() => {
return window.MonacoBootstrapWindow;
})();
// Setup shell environment
process['lazyEnv'] = getLazyEnv();
// Load environment in parallel to workbench loading to avoid waterfall
const whenEnvResolved = bootstrapWindow.globals().process.whenEnvResolved;
// Load workbench main JS, CSS and NLS all in parallel. This is an
// optimization to prevent a waterfall of loading to happen, because
@@ -45,23 +45,26 @@ bootstrapWindow.load([
'vs/nls!vs/workbench/workbench.desktop.main',
'vs/css!vs/workbench/workbench.desktop.main'
],
function (workbench, configuration) {
async function (workbench, configuration) {
// Mark start of workbench
perf.mark('didLoadWorkbenchMain');
performance.mark('workbench-start');
return process['lazyEnv'].then(function () {
perf.mark('main/startup');
// Wait for process environment being fully resolved
await whenEnvResolved;
// @ts-ignore
return require('vs/workbench/electron-browser/desktop.main').main(configuration);
});
perf.mark('main/startup');
// @ts-ignore
return require('vs/workbench/electron-browser/desktop.main').main(configuration);
},
{
removeDeveloperKeybindingsAfterLoad: true,
canModifyDOM: function (windowConfig) {
showPartsSplash(windowConfig);
if (!bootstrapWindow.globals().context.sandbox) {
showPartsSplash(windowConfig); // TODO@sandbox non-sandboxed only
}
},
beforeLoaderConfig: function (windowConfig, loaderConfig) {
loaderConfig.recordStats = true;
@@ -171,26 +174,3 @@ function showPartsSplash(configuration) {
perf.mark('didShowPartsSplash');
}
/**
* @returns {Promise<void>}
*/
function getLazyEnv() {
const ipcRenderer = bootstrapWindow.globals().ipcRenderer;
return new Promise(function (resolve) {
const handle = setTimeout(function () {
resolve();
console.warn('renderer did not receive lazyEnv in time');
}, 10000);
ipcRenderer.once('vscode:acceptShellEnv', function (event, shellEnv) {
clearTimeout(handle);
Object.assign(process.env, shellEnv);
// @ts-ignore
resolve(process.env);
});
ipcRenderer.send('vscode:fetchShellEnv');
});
}

View File

@@ -364,17 +364,17 @@ export class CodeApplication extends Disposable {
const sharedProcess = this.instantiationService.createInstance(SharedProcess, machineId, this.userEnv);
const sharedProcessClient = sharedProcess.whenIpcReady().then(() => {
this.logService.trace('Shared process: IPC ready');
return connect(this.environmentService.sharedIPCHandle, 'main');
});
const sharedProcessReady = sharedProcess.whenReady().then(() => {
this.logService.trace('Shared process: init ready');
return sharedProcessClient;
});
this.lifecycleMainService.when(LifecycleMainPhase.AfterWindowOpen).then(() => {
this._register(new RunOnceScheduler(async () => {
const userEnv = await getShellEnvironment(this.logService, this.environmentService);
sharedProcess.spawn(userEnv);
sharedProcess.spawn(await getShellEnvironment(this.logService, this.environmentService));
}, 3000)).schedule();
});
@@ -847,6 +847,9 @@ export class CodeApplication extends Disposable {
} catch (error) {
this.logService.error(error);
}
// Start to fetch shell environment after window has opened
getShellEnvironment(this.logService, this.environmentService);
}
private handleRemoteAuthorities(): void {

View File

@@ -3,7 +3,7 @@
* Licensed under the MIT License. See License.txt in the project root for license information.
*--------------------------------------------------------------------------------------------*/
import * as cp from 'child_process';
import { spawn } from 'child_process';
import { generateUuid } from 'vs/base/common/uuid';
import { isWindows } from 'vs/base/common/platform';
import { ILogService } from 'vs/platform/log/common/log';
@@ -30,7 +30,7 @@ function getUnixShellEnvironment(logService: ILogService): Promise<typeof proces
logService.trace('getUnixShellEnvironment#env', env);
logService.trace('getUnixShellEnvironment#spawn', command);
const child = cp.spawn(process.env.SHELL!, ['-ilc', command], {
const child = spawn(process.env.SHELL!, ['-ilc', command], {
detached: true,
stdio: ['ignore', 'pipe', process.stderr],
env
@@ -82,8 +82,7 @@ function getUnixShellEnvironment(logService: ILogService): Promise<typeof proces
return promise.catch(() => ({}));
}
let _shellEnv: Promise<typeof process.env>;
let shellEnvPromise: Promise<typeof process.env> | undefined = undefined;
/**
* We need to get the environment from a user's shell.
@@ -91,21 +90,21 @@ let _shellEnv: Promise<typeof process.env>;
* from within a shell.
*/
export function getShellEnvironment(logService: ILogService, environmentService: INativeEnvironmentService): Promise<typeof process.env> {
if (_shellEnv === undefined) {
if (!shellEnvPromise) {
if (environmentService.args['disable-user-env-probe']) {
logService.trace('getShellEnvironment: disable-user-env-probe set, skipping');
_shellEnv = Promise.resolve({});
shellEnvPromise = Promise.resolve({});
} else if (isWindows) {
logService.trace('getShellEnvironment: running on Windows, skipping');
_shellEnv = Promise.resolve({});
shellEnvPromise = Promise.resolve({});
} else if (process.env['VSCODE_CLI'] === '1' && process.env['VSCODE_FORCE_USER_ENV'] !== '1') {
logService.trace('getShellEnvironment: running on CLI, skipping');
_shellEnv = Promise.resolve({});
shellEnvPromise = Promise.resolve({});
} else {
logService.trace('getShellEnvironment: running on Unix');
_shellEnv = getUnixShellEnvironment(logService);
shellEnvPromise = getUnixShellEnvironment(logService);
}
}
return _shellEnv;
return shellEnvPromise;
}