blob: 9ada182bf28c5562ee2d9e6ac7346ef879854dad [file] [log] [blame]
/*---------------------------------------------------------
* Copyright 2021 The Go Authors. All rights reserved.
* Licensed under the MIT License. See LICENSE in the project root for license information.
*--------------------------------------------------------*/
import { ChildProcess } from 'child_process';
import getPort = require('get-port');
import { DebugConfiguration } from 'vscode';
import vscode = require('vscode');
import { spawnDapServerProcess as spawnDlvDapServerProcess } from './debugAdapter2/goDlvDebug';
import { logError, logInfo } from './goLogging';
import { killProcessTree } from './utils/processUtils';
export class GoDebugAdapterDescriptorFactory implements vscode.DebugAdapterDescriptorFactory {
private dlvDapServer?: ChildProcess;
public async createDebugAdapterDescriptor(
session: vscode.DebugSession,
executable: vscode.DebugAdapterExecutable | undefined
): Promise<vscode.ProviderResult<vscode.DebugAdapterDescriptor>> {
// The dlv-dap server currently receives certain flags and arguments on startup
// and must be started in an appropriate folder for the program to be debugged.
// In order to support this, we kill the current dlv-dap server, and start a
// new one.
await this.terminateDlvDapServerProcess();
const {port, host} = await this.startDapServer(session.configuration);
return new vscode.DebugAdapterServer(port, host);
}
public async dispose() {
await this.terminateDlvDapServerProcess();
}
private async terminateDlvDapServerProcess() {
if (this.dlvDapServer) {
await killProcessTree(this.dlvDapServer);
this.dlvDapServer = null;
}
}
private async startDapServer(configuration: DebugConfiguration): Promise<{ port: number; host: string; }> {
if (!configuration.host) {
configuration.host = '127.0.0.1';
}
if (configuration.port) {
// If a port has been specified, assume there is an already
// running dap server to connect to.
return {port: configuration.port, host: configuration.host};
} else {
configuration.port = await getPort();
}
this.dlvDapServer = spawnDlvDapServerProcess(configuration, logInfo, logError);
// Wait to give dlv-dap a chance to start before returning.
return await
new Promise<{ port: number; host: string; }>((resolve) => setTimeout(() => {
resolve({port: configuration.port, host: configuration.host});
}, 500));
}
}