bastion 0.63.1
ci / personal-data (push) Successful in 4s
ci / test (push) Successful in 4m58s
ci / fuzz (push) Successful in 3m33s

This commit is contained in:
Privatae
2026-11-03 22:56:18 +00:00
parent 2043fa5e9e
commit 48899b41a9
78 changed files with 10366 additions and 307 deletions
+29
View File
@@ -441,6 +441,18 @@ func pipeServerIsService(h windows.Handle) error {
return fmt.Errorf("cannot tell which process serves the pipe: %w", err)
}
svcPID, err := bastionServicePID()
if errors.Is(err, windows.ERROR_ACCESS_DENIED) {
// The service's default permissions let an INTERACTIVE logon query it,
// not a network one (ssh, a remote PowerShell): the owner's own
// `status` over ssh was refused as "Access is denied". The pipe's
// owner says what the process id would: servePipe sets no owner, so
// the pipe's is the creating token's default owner, which for
// LocalSystem is BUILTIN\Administrators (seen on Windows Server 2022)
// or SYSTEM, and no program of an ordinary account can make an object
// either owns. An administrator's own program could; an administrator
// already holds the service itself.
return pipeOwnedBySystem(h)
}
if err != nil {
return err
}
@@ -450,6 +462,23 @@ func pipeServerIsService(h windows.Handle) error {
return nil
}
// pipeOwnedBySystem refuses a pipe whose owner is not LocalSystem or the
// Administrators group, the two owners LocalSystem's objects get.
func pipeOwnedBySystem(h windows.Handle) error {
sd, err := windows.GetSecurityInfo(h, windows.SE_FILE_OBJECT, windows.OWNER_SECURITY_INFORMATION)
if err != nil {
return fmt.Errorf("cannot tell who made the pipe: %w", err)
}
owner, _, err := sd.Owner()
if err != nil || owner == nil {
return fmt.Errorf("cannot tell who made the pipe: %v", err)
}
if !owner.IsWellKnown(windows.WinLocalSystemSid) && !owner.IsWellKnown(windows.WinBuiltinAdministratorsSid) {
return fmt.Errorf("the pipe was made by %s, not by the %s service; nothing was sent", owner.String(), winServiceName)
}
return nil
}
// bastionServicePID is the service's process id from the Service Control
// Manager, asked with the query right every signed-in user holds. 0 when it is
// not running.