Conversation
There was a problem hiding this comment.
Pull request overview
This PR aims to reduce lifetime of sensitive cryptographic material by adding explicit destruction/zeroization hooks across the SSH transport and crypto layers, and invoking them after key exchange / rekey operations.
Changes:
- Add
Destroyablesupport to packet crypto interfaces and implementdestroy()in several KEX/cipher/MAC classes. - Zeroize derived key material via a new
KeyDerivation.Keys.zeroize()and wipe KEX-related buffers after NEWKEYS. - Proactively destroy/replace active crypto instances when enabling new encryption modes.
Reviewed changes
Copilot reviewed 17 out of 17 changed files in this pull request and generated 13 comments.
Show a summary per file
| File | Description |
|---|---|
| sshlib/src/main/kotlin/org/connectbot/sshlib/transport/PacketIO.kt | Destroys previous cipher/MAC/AEAD instances when reconfiguring encryption. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketMac.kt | Makes PacketMac Destroyable with default methods. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketCipher.kt | Makes PacketCipher Destroyable with default methods. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketAead.kt | Makes PacketAead Destroyable with default methods. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/MlKemHybridKeyExchange.kt | Adds destroy() to wipe ML-KEM and X25519 private keys. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/KeyDerivation.kt | Adds Keys.zeroize() and wipes intermediate digest buffers in derivation. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/KexAlgorithm.kt | Makes KEX algorithms Destroyable. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha512.kt | Attempts to add destroy logic for MAC key material. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha256.kt | Attempts to add destroy logic for MAC key material. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha1.kt | Attempts to add destroy logic for MAC key material. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/EcdhKeyExchange.kt | Adds destroy() to destroy underlying private key if supported. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/DiffieHellmanGroupExchange.kt | Clears DH private parameters after shared secret computation and on destroy. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/DiffieHellman.kt | Clears DH private key after shared secret computation and on destroy. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/Curve25519KeyExchange.kt | Avoids !! and adds destroy() to zeroize X25519 private key bytes. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/ChaCha20Poly1305Cipher.kt | Attempts to add destroy logic for AEAD key material. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/AesGcmCipher.kt | Attempts to add destroy logic for AEAD key material. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/client/SshConnection.kt | Copies sessionId, wipes KEX buffers, destroys KEX object, and zeroizes derived keys. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Try to call .destroy() on items that can be destroyed. Implement Destroyable on classes where it makes sense. Add a .zeroize() function for the Keys class to aid in sensitive value wiping.
There was a problem hiding this comment.
Pull request overview
This PR strengthens in-memory hygiene across the SSH crypto/transport stack by explicitly destroying/zeroizing key material and crypto primitives after they’re no longer needed (especially across re-key), reducing the lifetime of sensitive data in RAM.
Changes:
- Add
Destroyablesupport and call.destroy()when swapping packet encryption/MAC/AEAD state. - Add key material wiping (
zeroize()/fill(0)) for derived keys, KEX ephemeral secrets, and connection transcript buffers. - Ensure session ID and KEX-related buffers are copied and later wiped without affecting shared references.
Reviewed changes
Copilot reviewed 17 out of 17 changed files in this pull request and generated 6 comments.
Show a summary per file
| File | Description |
|---|---|
| sshlib/src/main/kotlin/org/connectbot/sshlib/transport/PacketIO.kt | Destroys previous cipher/MAC/AEAD instances when enabling new encryption modes. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketMac.kt | Makes packet MACs Destroyable (with default implementations). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketCipher.kt | Makes packet ciphers Destroyable (with default implementations). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/PacketAead.kt | Makes AEAD ciphers Destroyable (with default implementations). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/MlKemHybridKeyExchange.kt | Adds destroy() to wipe ML-KEM + X25519 private key buffers. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/KeyDerivation.kt | Adds Keys.zeroize() and wipes intermediate digest material during derivation. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/KexAlgorithm.kt | Extends Destroyable so KEX implementations can be destroyed after NEWKEYS. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha512.kt | Adds destroy() calling SecretKeySpec.destroy(). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha256.kt | Adds destroy() calling SecretKeySpec.destroy(). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/HmacSha1.kt | Adds destroy() calling SecretKeySpec.destroy(). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/EcdhKeyExchange.kt | Adds destroy() to drop and destroy the client private key if supported. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/DiffieHellmanGroupExchange.kt | Drops DH-GEX private/group params after use; adds destroy(). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/DiffieHellman.kt | Drops DH private key after computing shared secret; adds destroy(). |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/Curve25519KeyExchange.kt | Avoids !! and adds destroy() to wipe the X25519 private key bytes. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/ChaCha20Poly1305Cipher.kt | Adds destroy() to destroy key specs. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/crypto/AesGcmCipher.kt | Adds destroy() to destroy key spec. |
| sshlib/src/main/kotlin/org/connectbot/sshlib/client/SshConnection.kt | Copies/wipes session/KEX buffers; destroys KEX and wipes shared secret/exchange hash; zeroizes derived keys after installing ciphers. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Co-authored-by: Copilot Autofix powered by AI <175728472+Copilot@users.noreply.github.com>
Try to call .destroy() on items that can be destroyed. Implement Destroyable on classes where it makes sense. Add a .zeroize() function for the Keys class to aid in sensitive value wiping.