Make session key authorization atomic, unblock the encoder on teardown, drop agent privileges unconditionally

This commit is contained in:
Viktor Liu
2026-08-29 09:12:33 +02:00
parent 8b719f0b4e
commit 42450dbfbe
7 changed files with 119 additions and 14 deletions
+46
View File
@@ -711,3 +711,49 @@ func bytesRepeat(b byte, n int) []byte {
}
return out
}
// AuthorizeSessionKey resolves the key and authorizes the identity it names
// under one lock. Splitting those steps let an Update that revoked the key land
// in between, after which the caller still held a hash that authorized fine.
func TestAuthorizer_AuthorizeSessionKey_RevocationIsAtomic(t *testing.T) {
pub := bytesRepeat(0x55, sessionPubKeyLen)
userHash, err := sshauth.HashUserID("alice")
require.NoError(t, err)
granted := &Config{
AuthorizedUsers: []sshauth.UserIDHash{userHash},
MachineUsers: map[string][]uint32{Wildcard: {0}},
SessionPubKeys: []SessionPubKey{{PubKey: pub, UserIDHash: userHash}},
}
// The user stays authorized; only the session key is withdrawn. That is the
// shape that used to slip through, because the second step never looked at
// the key again.
revoked := &Config{
AuthorizedUsers: []sshauth.UserIDHash{userHash},
MachineUsers: map[string][]uint32{Wildcard: {0}},
}
a := NewAuthorizer()
a.Update(granted)
gotHash, _, err := a.AuthorizeSessionKey(pub, "alice")
require.NoError(t, err)
assert.Equal(t, userHash, gotHash)
a.Update(revoked)
_, _, err = a.AuthorizeSessionKey(pub, "alice")
require.ErrorIs(t, err, ErrSessionKeyNotKnown, "a revoked key must not authorize, even for a still-authorized user")
}
// A key that resolves but whose user is not authorized is refused by the second
// half of the same call.
func TestAuthorizer_AuthorizeSessionKey_UnauthorizedUser(t *testing.T) {
pub := bytesRepeat(0x66, sessionPubKeyLen)
userHash, err := sshauth.HashUserID("alice")
require.NoError(t, err)
a := NewAuthorizer()
a.Update(&Config{SessionPubKeys: []SessionPubKey{{PubKey: pub, UserIDHash: userHash}}})
_, _, err = a.AuthorizeSessionKey(pub, "alice")
require.ErrorIs(t, err, ErrUserNotAuthorized)
}