Skip to content

Commit 52b52b7

Browse files
Support -CustomPipeName
1 parent 1a86d4b commit 52b52b7

File tree

2 files changed

+44
-22
lines changed

2 files changed

+44
-22
lines changed

src/PowerShellEditorServices.Protocol/DebugAdapter/AttachRequest.cs

+2
Original file line numberDiff line numberDiff line change
@@ -21,5 +21,7 @@ public class AttachRequestArguments
2121
public string ProcessId { get; set; }
2222

2323
public int RunspaceId { get; set; }
24+
25+
public string CustomPipeName { get; set; }
2426
}
2527
}

src/PowerShellEditorServices.Protocol/Server/DebugAdapter.cs

+42-22
Original file line numberDiff line numberDiff line change
@@ -350,11 +350,17 @@ protected async Task HandleAttachRequestAsync(
350350

351351
RegisterEventHandlers();
352352

353+
bool processIdIsSet = !string.IsNullOrEmpty(attachParams.ProcessId) && attachParams.ProcessId != "undefined";
354+
bool customPipeNameIsSet = !string.IsNullOrEmpty(attachParams.CustomPipeName) && attachParams.CustomPipeName != "undefined";
355+
356+
PowerShellVersionDetails runspaceVersion =
357+
_editorSession.PowerShellContext.CurrentRunspace.PowerShellVersion;
358+
353359
// If there are no host processes to attach to or the user cancels selection, we get a null for the process id.
354360
// This is not an error, just a request to stop the original "attach to" request.
355361
// Testing against "undefined" is a HACK because I don't know how to make "Cancel" on quick pick loading
356362
// to cancel on the VSCode side without sending an attachRequest with processId set to "undefined".
357-
if (string.IsNullOrEmpty(attachParams.ProcessId) || (attachParams.ProcessId == "undefined"))
363+
if (!processIdIsSet && !customPipeNameIsSet)
358364
{
359365
Logger.Write(
360366
LogLevel.Normal,
@@ -370,9 +376,6 @@ await requestContext.SendErrorAsync(
370376

371377
if (attachParams.ComputerName != null)
372378
{
373-
PowerShellVersionDetails runspaceVersion =
374-
_editorSession.PowerShellContext.CurrentRunspace.PowerShellVersion;
375-
376379
if (runspaceVersion.Version.Major < 4)
377380
{
378381
await requestContext.SendErrorAsync(
@@ -403,16 +406,12 @@ await requestContext.SendErrorAsync(
403406
_isRemoteAttach = true;
404407
}
405408

406-
if (int.TryParse(attachParams.ProcessId, out int processId) && (processId > 0))
409+
if (processIdIsSet && int.TryParse(attachParams.ProcessId, out int processId) && (processId > 0))
407410
{
408-
PowerShellVersionDetails runspaceVersion =
409-
_editorSession.PowerShellContext.CurrentRunspace.PowerShellVersion;
410-
411411
if (runspaceVersion.Version.Major < 5)
412412
{
413413
await requestContext.SendErrorAsync(
414414
$"Attaching to a process is only available with PowerShell 5 and higher (current session is {runspaceVersion.Version}).");
415-
416415
return;
417416
}
418417

@@ -427,20 +426,27 @@ await requestContext.SendErrorAsync(
427426

428427
return;
429428
}
429+
}
430+
else if (customPipeNameIsSet)
431+
{
432+
if (runspaceVersion.Version.Major < 6 && runspaceVersion.Version.Minor < 2)
433+
{
434+
await requestContext.SendErrorAsync(
435+
$"Attaching to a process with CustomPipeName is only available with PowerShell 6.2 and higher (current session is {runspaceVersion.Version}).");
436+
return;
437+
}
438+
439+
await _editorSession.PowerShellContext.ExecuteScriptStringAsync(
440+
$"Enter-PSHostProcess -CustomPipeName {attachParams.CustomPipeName}",
441+
errorMessages);
442+
443+
if (errorMessages.Length > 0)
444+
{
445+
await requestContext.SendErrorAsync(
446+
$"Could not attach to process with CustomPipeName: '{attachParams.CustomPipeName}'");
430447

431-
// Clear any existing breakpoints before proceeding
432-
await ClearSessionBreakpointsAsync();
433-
434-
// Execute the Debug-Runspace command but don't await it because it
435-
// will block the debug adapter initialization process. The
436-
// InitializedEvent will be sent as soon as the RunspaceChanged
437-
// event gets fired with the attached runspace.
438-
int runspaceId = attachParams.RunspaceId > 0 ? attachParams.RunspaceId : 1;
439-
_waitingForAttach = true;
440-
Task nonAwaitedTask =
441-
_editorSession.PowerShellContext
442-
.ExecuteScriptStringAsync($"\nDebug-Runspace -Id {runspaceId}")
443-
.ContinueWith(OnExecutionCompletedAsync);
448+
return;
449+
}
444450
}
445451
else
446452
{
@@ -454,6 +460,20 @@ await requestContext.SendErrorAsync(
454460
return;
455461
}
456462

463+
// Clear any existing breakpoints before proceeding
464+
await ClearSessionBreakpointsAsync();
465+
466+
// Execute the Debug-Runspace command but don't await it because it
467+
// will block the debug adapter initialization process. The
468+
// InitializedEvent will be sent as soon as the RunspaceChanged
469+
// event gets fired with the attached runspace.
470+
int runspaceId = attachParams.RunspaceId > 0 ? attachParams.RunspaceId : 1;
471+
_waitingForAttach = true;
472+
Task nonAwaitedTask =
473+
_editorSession.PowerShellContext
474+
.ExecuteScriptStringAsync($"\nDebug-Runspace -Id {runspaceId}")
475+
.ContinueWith(OnExecutionCompletedAsync);
476+
457477
await requestContext.SendResultAsync(null);
458478
}
459479

0 commit comments

Comments
 (0)