Some checks failed
CD Pipeline / select-latest-carrier (push) Successful in 2m2s
CD Pipeline / workflow-shape (push) Successful in 0s
CD Pipeline / cancel-stale-cd (push) Has been skipped
CD Pipeline / tests (push) Successful in 6m29s
CD Pipeline / revalidate-deploy-carrier (push) Successful in 29s
CD Pipeline / build-and-deploy (push) Failing after 42s
CD Pipeline / revalidate-post-deploy-carrier (push) Has been skipped
CD Pipeline / post-deploy-checks (push) Has been skipped
346 lines
20 KiB
PowerShell
346 lines
20 KiB
PowerShell
[CmdletBinding()]
|
|
param(
|
|
[Parameter(Mandatory = $true)]
|
|
[string]$ControlPlaneSource
|
|
)
|
|
|
|
$ErrorActionPreference = "Stop"
|
|
$ProgressPreference = "SilentlyContinue"
|
|
|
|
function Get-ExactFunctionSource {
|
|
param([object]$Ast, [string]$Name)
|
|
$matches = @($Ast.FindAll({
|
|
param($node)
|
|
$node -is [Management.Automation.Language.FunctionDefinitionAst] -and $node.Name -eq $Name
|
|
}, $true))
|
|
if ($matches.Count -ne 1) { throw "function_identity_mismatch:$Name" }
|
|
[string]$matches[0].Extent.Text
|
|
}
|
|
|
|
function Assert-Replay {
|
|
param([bool]$Condition, [string]$Reason)
|
|
if (-not $Condition) { throw $Reason }
|
|
}
|
|
|
|
$tokens = $null
|
|
$errors = $null
|
|
$ast = [Management.Automation.Language.Parser]::ParseInput(
|
|
$ControlPlaneSource,
|
|
[ref]$tokens,
|
|
[ref]$errors
|
|
)
|
|
if ($errors.Count -ne 0) { throw "control_plane_parse_failed" }
|
|
foreach ($name in @(
|
|
"Get-AgentProcessDescendants",
|
|
"ConvertTo-AgentNativeProcessArgument",
|
|
"ConvertTo-AgentProcessIdentitySnapshot",
|
|
"Get-AgentCreationBoundedDescendants",
|
|
"Test-AgentProcessSnapshotMatch",
|
|
"Select-AgentProcessTreeIdentitySnapshot",
|
|
"Get-AgentProcessTreeIdentitySnapshot",
|
|
"Get-AgentProcessIdentityReadback",
|
|
"Test-AgentProcessIdentityActive",
|
|
"Wait-AgentProcessTreeIdentityAbsent",
|
|
"Stop-AgentBoundedProcessSnapshot",
|
|
"Read-AgentBoundedTextFile",
|
|
"Invoke-AgentBoundedProcess"
|
|
)) {
|
|
. ([ScriptBlock]::Create((Get-ExactFunctionSource $ast $name)))
|
|
}
|
|
|
|
$root = Join-Path $env:TEMP ("agent99-bounded-process-replay-" + [guid]::NewGuid().ToString("N"))
|
|
$normal = $null
|
|
$timeout = $null
|
|
$flood = $null
|
|
$rootOnly = $null
|
|
$rootOnlyChildIdentity = $null
|
|
$orphanRace = $null
|
|
$orphanRaceChildIdentity = $null
|
|
$pidReuseSelection = $null
|
|
$creationBoundSelection = $null
|
|
$stopReadbackFailure = $null
|
|
$stopReadbackFailureChildIdentity = $null
|
|
$cimFailure = $null
|
|
$cimFailureChildIdentity = $null
|
|
$cleanupVerified = $false
|
|
try {
|
|
New-Item -ItemType Directory -Path $root -Force | Out-Null
|
|
$powershell = Join-Path $env:SystemRoot "System32\WindowsPowerShell\v1.0\powershell.exe"
|
|
$cmd = Join-Path $env:SystemRoot "System32\cmd.exe"
|
|
|
|
$normal = Invoke-AgentBoundedProcess `
|
|
-FilePath $cmd `
|
|
-Arguments @("/d", "/c", "echo", "AG99_BOUNDED_OK") `
|
|
-TimeoutSeconds 5 `
|
|
-MaximumOutputBytes 4096
|
|
Assert-Replay ($normal.ok -and $normal.completed -and $normal.stdout -match "AG99_BOUNDED_OK") "normal_process_failed"
|
|
|
|
$childPath = Join-Path $root "child.ps1"
|
|
$parentPath = Join-Path $root "parent.ps1"
|
|
[IO.File]::WriteAllText($childPath, 'Start-Sleep -Seconds 30', (New-Object Text.UTF8Encoding($false)))
|
|
[IO.File]::WriteAllText($parentPath, @'
|
|
param([string]$ChildPath)
|
|
$powershell = Join-Path $env:SystemRoot "System32\WindowsPowerShell\v1.0\powershell.exe"
|
|
$arguments = "-NoProfile -NonInteractive -File `"$ChildPath`""
|
|
Start-Process -FilePath $powershell -ArgumentList $arguments -WindowStyle Hidden | Out-Null
|
|
Start-Sleep -Seconds 30
|
|
'@, (New-Object Text.UTF8Encoding($false)))
|
|
$timeout = Invoke-AgentBoundedProcess `
|
|
-FilePath $powershell `
|
|
-Arguments @("-NoProfile", "-NonInteractive", "-File", $parentPath, "-ChildPath", $childPath) `
|
|
-TimeoutSeconds 2 `
|
|
-MaximumOutputBytes 4096
|
|
Assert-Replay ($timeout.timedOut -and -not $timeout.completed) "timeout_not_detected"
|
|
Assert-Replay ($timeout.processTreeStopped -and -not $timeout.treeReadbackFailed) "timeout_tree_not_stopped"
|
|
Assert-Replay ([int]$timeout.killedIdentityCount -ge 2) "timeout_descendant_not_observed"
|
|
|
|
$floodPath = Join-Path $root "flood.ps1"
|
|
[IO.File]::WriteAllText($floodPath, @'
|
|
for ($index = 0; $index -lt 1000; $index++) {
|
|
[Console]::Out.Write(('X' * 1024))
|
|
}
|
|
Start-Sleep -Seconds 5
|
|
'@, (New-Object Text.UTF8Encoding($false)))
|
|
$flood = Invoke-AgentBoundedProcess `
|
|
-FilePath $powershell `
|
|
-Arguments @("-NoProfile", "-NonInteractive", "-File", $floodPath) `
|
|
-TimeoutSeconds 10 `
|
|
-MaximumOutputBytes 4096
|
|
Assert-Replay ($flood.outputLimitExceeded -and -not $flood.completed) "streaming_output_limit_not_detected"
|
|
Assert-Replay ([long]$flood.capturedBytes -le [long]$flood.maximumOutputBytes) "captured_output_exceeded_contract"
|
|
Assert-Replay ($flood.processTreeStopped -and -not $flood.treeReadbackFailed) "flood_tree_not_stopped"
|
|
|
|
$rootOnlyChildPidPath = Join-Path $root "root-only-child.pid"
|
|
$rootOnlyChildPath = Join-Path $root "root-only-child.ps1"
|
|
$rootOnlyParentPath = Join-Path $root "root-only-parent.ps1"
|
|
[IO.File]::WriteAllText($rootOnlyChildPath, @'
|
|
param([string]$PidPath)
|
|
[IO.File]::WriteAllText($PidPath, [string]$PID, (New-Object Text.UTF8Encoding($false)))
|
|
Start-Sleep -Seconds 30
|
|
'@, (New-Object Text.UTF8Encoding($false)))
|
|
[IO.File]::WriteAllText($rootOnlyParentPath, @'
|
|
param([string]$ChildPath, [string]$ChildPidPath)
|
|
$powershell = Join-Path $env:SystemRoot "System32\WindowsPowerShell\v1.0\powershell.exe"
|
|
$arguments = "-NoProfile -NonInteractive -File `"$ChildPath`" -PidPath `"$ChildPidPath`""
|
|
Start-Process -FilePath $powershell -ArgumentList $arguments -WindowStyle Hidden | Out-Null
|
|
Start-Sleep -Seconds 30
|
|
'@, (New-Object Text.UTF8Encoding($false)))
|
|
$rootOnly = Invoke-AgentBoundedProcess `
|
|
-FilePath $powershell `
|
|
-Arguments @("-NoProfile", "-NonInteractive", "-File", $rootOnlyParentPath, "-ChildPath", $rootOnlyChildPath, "-ChildPidPath", $rootOnlyChildPidPath) `
|
|
-TimeoutSeconds 2 `
|
|
-MaximumOutputBytes 4096 `
|
|
-TerminationScope Root
|
|
Assert-Replay ($rootOnly.timedOut -and $rootOnly.forcedTerminationPerformed) "root_only_timeout_not_detected"
|
|
Assert-Replay ($rootOnly.processScopeStopped -and -not $rootOnly.processTreeStopped) "root_only_scope_not_preserved"
|
|
Assert-Replay ([int]$rootOnly.preservedDescendantCount -ge 1) "root_only_descendant_not_preserved"
|
|
Assert-Replay (Test-Path -LiteralPath $rootOnlyChildPidPath -PathType Leaf) "root_only_child_pid_missing"
|
|
$rootOnlyChildPid = [int]([IO.File]::ReadAllText($rootOnlyChildPidPath))
|
|
$rootOnlyChildProcess = Get-CimInstance Win32_Process -Filter "ProcessId = $rootOnlyChildPid" -ErrorAction Stop
|
|
$rootOnlyChildIdentity = [pscustomobject]@{
|
|
processId = [int]$rootOnlyChildProcess.ProcessId
|
|
parentProcessId = [int]$rootOnlyChildProcess.ParentProcessId
|
|
creationUtc = ([datetime]$rootOnlyChildProcess.CreationDate).ToUniversalTime().ToString("o")
|
|
name = [string]$rootOnlyChildProcess.Name
|
|
}
|
|
Assert-Replay (Test-AgentProcessIdentityActive $rootOnlyChildIdentity) "root_only_child_not_active_after_parent_stop"
|
|
|
|
$orphanRaceChildPidPath = Join-Path $root "orphan-race-child.pid"
|
|
$orphanRaceParentPath = Join-Path $root "orphan-race-parent.ps1"
|
|
[IO.File]::WriteAllText($orphanRaceParentPath, @'
|
|
param([string]$ChildPath, [string]$ChildPidPath)
|
|
$powershell = Join-Path $env:SystemRoot "System32\WindowsPowerShell\v1.0\powershell.exe"
|
|
$arguments = "-NoProfile -NonInteractive -File `"$ChildPath`" -PidPath `"$ChildPidPath`""
|
|
Start-Process -FilePath $powershell -ArgumentList $arguments -WindowStyle Hidden | Out-Null
|
|
$stopwatch = [Diagnostics.Stopwatch]::StartNew()
|
|
while (-not (Test-Path -LiteralPath $ChildPidPath) -and $stopwatch.Elapsed.TotalSeconds -lt 5) {
|
|
Start-Sleep -Milliseconds 50
|
|
}
|
|
Start-Sleep -Seconds 1
|
|
'@, (New-Object Text.UTF8Encoding($false)))
|
|
$orphanStartInfo = New-Object Diagnostics.ProcessStartInfo
|
|
$orphanStartInfo.FileName = $powershell
|
|
$orphanStartInfo.Arguments = "-NoProfile -NonInteractive -File `"$orphanRaceParentPath`" -ChildPath `"$rootOnlyChildPath`" -ChildPidPath `"$orphanRaceChildPidPath`""
|
|
$orphanStartInfo.UseShellExecute = $false
|
|
$orphanStartInfo.CreateNoWindow = $true
|
|
$orphanRoot = New-Object Diagnostics.Process
|
|
$orphanRoot.StartInfo = $orphanStartInfo
|
|
Assert-Replay $orphanRoot.Start() "orphan_race_parent_start_failed"
|
|
$orphanRootInfo = Get-CimInstance Win32_Process -Filter "ProcessId = $([int]$orphanRoot.Id)" -ErrorAction Stop | Select-Object -First 1
|
|
$orphanRootIdentity = ConvertTo-AgentProcessIdentitySnapshot $orphanRootInfo
|
|
Assert-Replay ([bool]$orphanRootIdentity) "orphan_race_root_identity_capture_failed"
|
|
Assert-Replay $orphanRoot.WaitForExit(8000) "orphan_race_parent_did_not_exit"
|
|
Assert-Replay (Test-Path -LiteralPath $orphanRaceChildPidPath -PathType Leaf) "orphan_race_child_pid_missing"
|
|
$orphanIdentities = @(Get-AgentProcessTreeIdentitySnapshot $orphanRootIdentity $orphanRoot.ExitTime.ToUniversalTime())
|
|
Assert-Replay ($orphanIdentities.Count -ge 1) "orphan_race_descendant_snapshot_missing"
|
|
Assert-Replay (@($orphanIdentities | Where-Object { [int]$_.processId -eq [int]$orphanRoot.Id }).Count -eq 0) "orphan_race_root_unexpectedly_present"
|
|
$orphanRaceChildIdentity = @($orphanIdentities | Select-Object -First 1)[0]
|
|
$orphanRace = Stop-AgentBoundedProcessSnapshot $orphanRoot $orphanIdentities "Tree"
|
|
Assert-Replay ($orphanRace.processTreeStopped -and $orphanRace.processScopeStopped) "orphan_race_tree_false_green"
|
|
Assert-Replay (-not (Test-AgentProcessIdentityActive $orphanRaceChildIdentity)) "orphan_race_child_still_active"
|
|
|
|
$pidReuseRootCreated = [datetime]::UtcNow.AddMinutes(-5)
|
|
$pidReuseRootExited = $pidReuseRootCreated.AddSeconds(2)
|
|
$pidReuseExpectedRoot = [pscustomobject]@{
|
|
processId = 9001
|
|
parentProcessId = 7000
|
|
creationUtc = $pidReuseRootCreated.ToString("o")
|
|
name = "powershell.exe"
|
|
}
|
|
$pidReuseProcesses = @(
|
|
[pscustomobject]@{ ProcessId = 9001; ParentProcessId = 8000; CreationDate = $pidReuseRootExited.AddSeconds(1); Name = "powershell.exe" },
|
|
[pscustomobject]@{ ProcessId = 9002; ParentProcessId = 9001; CreationDate = $pidReuseRootCreated.AddSeconds(1); Name = "cmd.exe" },
|
|
[pscustomobject]@{ ProcessId = 9003; ParentProcessId = 9002; CreationDate = $pidReuseRootExited.AddSeconds(1); Name = "conhost.exe" },
|
|
[pscustomobject]@{ ProcessId = 9004; ParentProcessId = 9001; CreationDate = $pidReuseRootExited.AddSeconds(2); Name = "not-agent99.exe" },
|
|
[pscustomobject]@{ ProcessId = 9005; ParentProcessId = 9002; CreationDate = $pidReuseRootCreated.AddMilliseconds(500); Name = "older-than-parent.exe" }
|
|
)
|
|
$pidReuseSelection = @(Select-AgentProcessTreeIdentitySnapshot $pidReuseProcesses $pidReuseExpectedRoot $pidReuseRootExited)
|
|
$pidReuseSelectedIds = @($pidReuseSelection | ForEach-Object { [int]$_.processId } | Sort-Object)
|
|
Assert-Replay (($pidReuseSelectedIds -join ",") -eq "9002,9003") "pid_reuse_selection_not_identity_bounded"
|
|
|
|
$liveRootCreated = [datetime]::UtcNow.AddMinutes(-1)
|
|
$liveRootIdentity = [pscustomobject]@{ processId = 9101; parentProcessId = 7000; creationUtc = $liveRootCreated.ToString("o"); name = "powershell.exe" }
|
|
$liveRootProcesses = @(
|
|
[pscustomobject]@{ ProcessId = 9101; ParentProcessId = 7000; CreationDate = $liveRootCreated; Name = "powershell.exe" },
|
|
[pscustomobject]@{ ProcessId = 9102; ParentProcessId = 9101; CreationDate = $liveRootCreated.AddSeconds(1); Name = "valid-child.exe" },
|
|
[pscustomobject]@{ ProcessId = 9103; ParentProcessId = 9101; CreationDate = $liveRootCreated.AddSeconds(-1); Name = "older-unrelated.exe" }
|
|
)
|
|
$creationBoundSelection = @(Select-AgentProcessTreeIdentitySnapshot $liveRootProcesses $liveRootIdentity ([datetime]::MinValue))
|
|
$creationBoundIds = @($creationBoundSelection | ForEach-Object { [int]$_.processId } | Sort-Object)
|
|
Assert-Replay (($creationBoundIds -join ",") -eq "9101,9102") "live_root_child_creation_bound_failed"
|
|
|
|
$stopReadbackChildPidPath = Join-Path $root "stop-readback-failure-child.pid"
|
|
function Get-AgentProcessIdentityReadback { [pscustomobject]@{ known = $false; active = $false; reason = "synthetic_stop_readback_failure" } }
|
|
$stopReadbackFailure = Invoke-AgentBoundedProcess `
|
|
-FilePath $powershell `
|
|
-Arguments @("-NoProfile", "-NonInteractive", "-File", $rootOnlyParentPath, "-ChildPath", $rootOnlyChildPath, "-ChildPidPath", $stopReadbackChildPidPath) `
|
|
-TimeoutSeconds 2 `
|
|
-MaximumOutputBytes 4096
|
|
. ([ScriptBlock]::Create((Get-ExactFunctionSource $ast "Get-AgentProcessIdentityReadback")))
|
|
Assert-Replay ($stopReadbackFailure.timedOut -and $stopReadbackFailure.identityReadbackFailed) "stop_readback_failure_not_detected"
|
|
Assert-Replay ($stopReadbackFailure.treeReadbackFailed -and $stopReadbackFailure.rootFallbackTerminationUsed) "stop_readback_failure_not_fail_closed"
|
|
Assert-Replay ($stopReadbackFailure.processScopeStopped -and -not $stopReadbackFailure.processTreeStopped) "stop_readback_failure_tree_false_green"
|
|
Assert-Replay (Test-Path -LiteralPath $stopReadbackChildPidPath -PathType Leaf) "stop_readback_failure_child_pid_missing"
|
|
$stopReadbackChildPid = [int]([IO.File]::ReadAllText($stopReadbackChildPidPath))
|
|
$stopReadbackChildProcess = Get-CimInstance Win32_Process -Filter "ProcessId = $stopReadbackChildPid" -ErrorAction Stop
|
|
$stopReadbackFailureChildIdentity = ConvertTo-AgentProcessIdentitySnapshot $stopReadbackChildProcess
|
|
Assert-Replay (Test-AgentProcessIdentityActive $stopReadbackFailureChildIdentity) "stop_readback_failure_child_unexpectedly_stopped"
|
|
|
|
$cimFailureChildPidPath = Join-Path $root "cim-failure-child.pid"
|
|
function Get-AgentProcessTreeIdentitySnapshot { throw "synthetic_cim_failure" }
|
|
$cimFailure = Invoke-AgentBoundedProcess `
|
|
-FilePath $powershell `
|
|
-Arguments @("-NoProfile", "-NonInteractive", "-File", $rootOnlyParentPath, "-ChildPath", $rootOnlyChildPath, "-ChildPidPath", $cimFailureChildPidPath) `
|
|
-TimeoutSeconds 2 `
|
|
-MaximumOutputBytes 4096
|
|
. ([ScriptBlock]::Create((Get-ExactFunctionSource $ast "Get-AgentProcessTreeIdentitySnapshot")))
|
|
. ([ScriptBlock]::Create((Get-ExactFunctionSource $ast "Get-AgentProcessIdentityReadback")))
|
|
Assert-Replay ($cimFailure.timedOut -and $cimFailure.treeReadbackFailed) "cim_failure_not_detected"
|
|
Assert-Replay ($cimFailure.rootFallbackTerminationUsed -and $cimFailure.processScopeStopped) "cim_failure_root_not_stopped"
|
|
Assert-Replay (-not $cimFailure.processTreeStopped) "cim_failure_tree_false_green"
|
|
Assert-Replay (Test-Path -LiteralPath $cimFailureChildPidPath -PathType Leaf) "cim_failure_child_pid_missing"
|
|
$cimFailureChildPid = [int]([IO.File]::ReadAllText($cimFailureChildPidPath))
|
|
$cimFailureChildProcess = Get-CimInstance Win32_Process -Filter "ProcessId = $cimFailureChildPid" -ErrorAction Stop
|
|
$cimFailureChildIdentity = [pscustomobject]@{
|
|
processId = [int]$cimFailureChildProcess.ProcessId
|
|
parentProcessId = [int]$cimFailureChildProcess.ParentProcessId
|
|
creationUtc = ([datetime]$cimFailureChildProcess.CreationDate).ToUniversalTime().ToString("o")
|
|
name = [string]$cimFailureChildProcess.Name
|
|
}
|
|
Assert-Replay (Test-AgentProcessIdentityActive $cimFailureChildIdentity) "cim_failure_child_unexpectedly_stopped"
|
|
} finally {
|
|
. ([ScriptBlock]::Create((Get-ExactFunctionSource $ast "Get-AgentProcessTreeIdentitySnapshot")))
|
|
if ($rootOnlyChildIdentity -and (Test-AgentProcessIdentityActive $rootOnlyChildIdentity)) {
|
|
& "$env:SystemRoot\System32\taskkill.exe" /PID ([int]$rootOnlyChildIdentity.processId) /T /F 2>&1 | Out-Null
|
|
[void](Wait-AgentProcessTreeIdentityAbsent @($rootOnlyChildIdentity) 8)
|
|
}
|
|
if ($cimFailureChildIdentity -and (Test-AgentProcessIdentityActive $cimFailureChildIdentity)) {
|
|
& "$env:SystemRoot\System32\taskkill.exe" /PID ([int]$cimFailureChildIdentity.processId) /T /F 2>&1 | Out-Null
|
|
[void](Wait-AgentProcessTreeIdentityAbsent @($cimFailureChildIdentity) 8)
|
|
}
|
|
if ($orphanRaceChildIdentity -and (Test-AgentProcessIdentityActive $orphanRaceChildIdentity)) {
|
|
& "$env:SystemRoot\System32\taskkill.exe" /PID ([int]$orphanRaceChildIdentity.processId) /T /F 2>&1 | Out-Null
|
|
[void](Wait-AgentProcessTreeIdentityAbsent @($orphanRaceChildIdentity) 8)
|
|
}
|
|
if ($stopReadbackFailureChildIdentity -and (Test-AgentProcessIdentityActive $stopReadbackFailureChildIdentity)) {
|
|
& "$env:SystemRoot\System32\taskkill.exe" /PID ([int]$stopReadbackFailureChildIdentity.processId) /T /F 2>&1 | Out-Null
|
|
[void](Wait-AgentProcessTreeIdentityAbsent @($stopReadbackFailureChildIdentity) 8)
|
|
}
|
|
Remove-Item -LiteralPath $root -Recurse -Force -ErrorAction SilentlyContinue
|
|
$cleanupVerified = [bool](
|
|
-not (Test-Path -LiteralPath $root) -and
|
|
(-not $rootOnlyChildIdentity -or -not (Test-AgentProcessIdentityActive $rootOnlyChildIdentity)) -and
|
|
(-not $orphanRaceChildIdentity -or -not (Test-AgentProcessIdentityActive $orphanRaceChildIdentity)) -and
|
|
(-not $stopReadbackFailureChildIdentity -or -not (Test-AgentProcessIdentityActive $stopReadbackFailureChildIdentity)) -and
|
|
(-not $cimFailureChildIdentity -or -not (Test-AgentProcessIdentityActive $cimFailureChildIdentity))
|
|
)
|
|
}
|
|
|
|
[pscustomobject]@{
|
|
schemaVersion = "agent99_bounded_process_replay_v2"
|
|
ok = [bool]($normal.ok -and $timeout.timedOut -and $timeout.processTreeStopped -and $flood.outputLimitExceeded -and $flood.processTreeStopped -and $rootOnly.timedOut -and $rootOnly.processScopeStopped -and -not $rootOnly.processTreeStopped -and $orphanRace.processTreeStopped -and $pidReuseSelection.Count -eq 2 -and $creationBoundSelection.Count -eq 2 -and $stopReadbackFailure.identityReadbackFailed -and -not $stopReadbackFailure.processTreeStopped -and $cimFailure.timedOut -and $cimFailure.treeReadbackFailed -and $cimFailure.rootFallbackTerminationUsed -and $cimFailure.processScopeStopped -and -not $cimFailure.processTreeStopped -and $cleanupVerified)
|
|
normal = [pscustomobject]@{
|
|
exitCode = [int]$normal.exitCode
|
|
completed = [bool]$normal.completed
|
|
}
|
|
timeout = [pscustomobject]@{
|
|
exitCode = [int]$timeout.exitCode
|
|
timedOut = [bool]$timeout.timedOut
|
|
processTreeStopped = [bool]$timeout.processTreeStopped
|
|
killedIdentityCount = [int]$timeout.killedIdentityCount
|
|
}
|
|
flood = [pscustomobject]@{
|
|
exitCode = [int]$flood.exitCode
|
|
outputLimitExceeded = [bool]$flood.outputLimitExceeded
|
|
capturedBytes = [long]$flood.capturedBytes
|
|
maximumOutputBytes = [long]$flood.maximumOutputBytes
|
|
processTreeStopped = [bool]$flood.processTreeStopped
|
|
}
|
|
rootOnly = [pscustomobject]@{
|
|
exitCode = [int]$rootOnly.exitCode
|
|
timedOut = [bool]$rootOnly.timedOut
|
|
terminationScope = [string]$rootOnly.terminationScope
|
|
processScopeStopped = [bool]$rootOnly.processScopeStopped
|
|
processTreeStopped = [bool]$rootOnly.processTreeStopped
|
|
preservedDescendantCount = [int]$rootOnly.preservedDescendantCount
|
|
}
|
|
orphanRace = [pscustomobject]@{
|
|
rootExitedBeforeSnapshot = $true
|
|
descendantSnapshotCount = [int]$orphanIdentities.Count
|
|
processScopeStopped = [bool]$orphanRace.processScopeStopped
|
|
processTreeStopped = [bool]$orphanRace.processTreeStopped
|
|
}
|
|
pidReuseSelection = [pscustomobject]@{
|
|
reusedRootExcluded = [bool](@($pidReuseSelection | Where-Object { [int]$_.processId -eq 9001 }).Count -eq 0)
|
|
originalChildIncluded = [bool](@($pidReuseSelection | Where-Object { [int]$_.processId -eq 9002 }).Count -eq 1)
|
|
originalGrandchildIncluded = [bool](@($pidReuseSelection | Where-Object { [int]$_.processId -eq 9003 }).Count -eq 1)
|
|
reusedRootChildExcluded = [bool](@($pidReuseSelection | Where-Object { [int]$_.processId -eq 9004 }).Count -eq 0)
|
|
intermediateOlderProcessExcluded = [bool](@($pidReuseSelection | Where-Object { [int]$_.processId -eq 9005 }).Count -eq 0)
|
|
}
|
|
creationBounds = [pscustomobject]@{
|
|
liveRootIncluded = [bool](@($creationBoundSelection | Where-Object { [int]$_.processId -eq 9101 }).Count -eq 1)
|
|
validChildIncluded = [bool](@($creationBoundSelection | Where-Object { [int]$_.processId -eq 9102 }).Count -eq 1)
|
|
olderUnrelatedChildExcluded = [bool](@($creationBoundSelection | Where-Object { [int]$_.processId -eq 9103 }).Count -eq 0)
|
|
}
|
|
stopReadbackFailure = [pscustomobject]@{
|
|
identityReadbackFailed = [bool]$stopReadbackFailure.identityReadbackFailed
|
|
treeReadbackFailed = [bool]$stopReadbackFailure.treeReadbackFailed
|
|
rootFallbackTerminationUsed = [bool]$stopReadbackFailure.rootFallbackTerminationUsed
|
|
processScopeStopped = [bool]$stopReadbackFailure.processScopeStopped
|
|
processTreeStopped = [bool]$stopReadbackFailure.processTreeStopped
|
|
}
|
|
cimFailure = [pscustomobject]@{
|
|
exitCode = [int]$cimFailure.exitCode
|
|
timedOut = [bool]$cimFailure.timedOut
|
|
treeReadbackFailed = [bool]$cimFailure.treeReadbackFailed
|
|
rootFallbackTerminationUsed = [bool]$cimFailure.rootFallbackTerminationUsed
|
|
processScopeStopped = [bool]$cimFailure.processScopeStopped
|
|
processTreeStopped = [bool]$cimFailure.processTreeStopped
|
|
}
|
|
cleanupVerified = $cleanupVerified
|
|
productionPathWritePerformed = $false
|
|
vmPowerChangePerformed = $false
|
|
hostRebootPerformed = $false
|
|
secretValuesRead = $false
|
|
} | ConvertTo-Json -Compress -Depth 5
|