package crypto import ( "crypto/dsa" //nolint:staticcheck "crypto/ecdsa" "crypto/ed25519" "crypto/rsa" "errors" "math/big" "github.com/ProtonMail/go-crypto/openpgp/ecdh" "github.com/ProtonMail/go-crypto/openpgp/elgamal" ) func (sk *SessionKey) Clear() (ok bool) { clearMem(sk.Key) return true } func (key *Key) ClearPrivateParams() (ok bool) { num := key.clearPrivateWithSubkeys() key.entity.PrivateKey = nil for k := range key.entity.Subkeys { key.entity.Subkeys[k].PrivateKey = nil } return num > 0 } func (key *Key) clearPrivateWithSubkeys() (num int) { num = 0 if key.entity.PrivateKey != nil { err := clearPrivateKey(key.entity.PrivateKey.PrivateKey) if err == nil { num++ } } for k := range key.entity.Subkeys { if key.entity.Subkeys[k].PrivateKey != nil { err := clearPrivateKey(key.entity.Subkeys[k].PrivateKey.PrivateKey) if err == nil { num++ } } } return num } func clearPrivateKey(privateKey interface{}) error { switch priv := privateKey.(type) { case *rsa.PrivateKey: return clearRSAPrivateKey(priv) case *dsa.PrivateKey: return clearDSAPrivateKey(priv) case *elgamal.PrivateKey: return clearElGamalPrivateKey(priv) case *ecdsa.PrivateKey: return clearECDSAPrivateKey(priv) case *ed25519.PrivateKey: return clearEdDSAPrivateKey(priv) case *ecdh.PrivateKey: return clearECDHPrivateKey(priv) default: return errors.New("gopenpgp: unknown private key") } } func clearBigInt(n *big.Int) { w := n.Bits() for k := range w { w[k] = 0x00 } } func clearMem(w []byte) { for k := range w { w[k] = 0x00 } } func clearRSAPrivateKey(rsaPriv *rsa.PrivateKey) error { clearBigInt(rsaPriv.D) for idx := range rsaPriv.Primes { clearBigInt(rsaPriv.Primes[idx]) } clearBigInt(rsaPriv.Precomputed.Qinv) clearBigInt(rsaPriv.Precomputed.Dp) clearBigInt(rsaPriv.Precomputed.Dq) for idx := range rsaPriv.Precomputed.CRTValues { clearBigInt(rsaPriv.Precomputed.CRTValues[idx].Exp) clearBigInt(rsaPriv.Precomputed.CRTValues[idx].Coeff) clearBigInt(rsaPriv.Precomputed.CRTValues[idx].R) } return nil } func clearDSAPrivateKey(priv *dsa.PrivateKey) error { clearBigInt(priv.X) return nil } func clearElGamalPrivateKey(priv *elgamal.PrivateKey) error { clearBigInt(priv.X) return nil } func clearECDSAPrivateKey(priv *ecdsa.PrivateKey) error { clearBigInt(priv.D) return nil } func clearEdDSAPrivateKey(priv *ed25519.PrivateKey) error { clearMem(*priv) return nil } func clearECDHPrivateKey(priv *ecdh.PrivateKey) error { clearMem(priv.D) return nil }