Browse Source

fix: do not allocate when comparing keys

pull/1683/head
dignifiedquire 5 years ago
committed by Steven Allen
parent
commit
5915b53974
  1. 8
      core/crypto/key.go
  2. 30
      core/crypto/key_test.go
  3. 47
      core/crypto/rsa_go.go

8
core/crypto/key.go

@ -363,7 +363,9 @@ func KeyEqual(k1, k2 Key) bool {
return true
}
b1, err1 := k1.Bytes()
b2, err2 := k2.Bytes()
return subtle.ConstantTimeCompare(b1, b2) == 1 && err1 == err2
if k1.Type() != k2.Type() {
return false
}
return k1.Equals(k2)
}

30
core/crypto/key_test.go

@ -101,18 +101,19 @@ func testKeyEncoding(t *testing.T, sk PrivKey) {
}
func testKeyEquals(t *testing.T, k Key) {
kb, err := k.Bytes()
if err != nil {
t.Fatal(err)
}
// kb, err := k.Raw()
// if err != nil {
// t.Fatal(err)
// }
if !KeyEqual(k, k) {
t.Fatal("Key not equal to itself.")
}
if !KeyEqual(k, testkey(kb)) {
t.Fatal("Key not equal to key with same bytes.")
}
// bad test, relies on deep internals..
// if !KeyEqual(k, testkey(kb)) {
// t.Fatal("Key not equal to key with same bytes.")
// }
sk, pk, err := test.RandTestKeyPair(RSA, 512)
if err != nil {
@ -143,7 +144,20 @@ func (pk testkey) Raw() ([]byte, error) {
}
func (pk testkey) Equals(k Key) bool {
return KeyEqual(pk, k)
if pk.Type() != k.Type() {
return false
}
a, err := pk.Raw()
if err != nil {
return false
}
b, err := k.Raw()
if err != nil {
return false
}
return bytes.Equal(a, b)
}
func TestUnknownCurveErrors(t *testing.T) {

47
core/crypto/rsa_go.go

@ -3,6 +3,7 @@
package crypto
import (
"bytes"
"crypto"
"crypto/rand"
"crypto/rsa"
@ -63,7 +64,21 @@ func (pk *RsaPublicKey) Raw() ([]byte, error) {
// Equals checks whether this key is equal to another
func (pk *RsaPublicKey) Equals(k Key) bool {
return KeyEqual(pk, k)
// make sure this is an rsa public key
other, ok := (k).(*RsaPublicKey)
if !ok {
a, err := pk.Raw()
if err != nil {
return false
}
b, err := k.Raw()
if err != nil {
return false
}
return bytes.Equal(a, b)
}
return pk.k.N.Cmp(other.k.N) == 0 && pk.k.E == other.k.E
}
// Sign returns a signature of the input data
@ -93,7 +108,35 @@ func (sk *RsaPrivateKey) Raw() ([]byte, error) {
// Equals checks whether this key is equal to another
func (sk *RsaPrivateKey) Equals(k Key) bool {
return KeyEqual(sk, k)
// make sure this is an rsa public key
other, ok := (k).(*RsaPrivateKey)
if !ok {
a, err := sk.Raw()
if err != nil {
return false
}
b, err := k.Raw()
if err != nil {
return false
}
return bytes.Equal(a, b)
}
a := sk.sk
b := other.sk
if a.PublicKey.N.Cmp(b.PublicKey.N) != 0 {
return false
}
if a.PublicKey.E != b.PublicKey.E {
return false
}
if a.D.Cmp(b.D) != 0 {
return false
}
return true
}
// UnmarshalRsaPrivateKey returns a private key from the input x509 bytes

Loading…
Cancel
Save