Skip to content

Commit 775b238

Browse files
committed
[dev.boringcrypto.go1.8] crypto/ecdsa: use unsafe.Pointer instead of atomic.Value
Using atomic.Value causes vet errors in code copying PublicKey or PrivateKey structures. I don't think the errors are accurate, but it's easier to work around them than to change vet or change atomic.Value. See #21504. Change-Id: I3a3435c1fc664cc5166c81674f6f7c58dab35f21 Reviewed-on: https://go-review.googlesource.com/56671 Run-TryBot: Russ Cox <[email protected]> TryBot-Result: Gobot Gobot <[email protected]> Reviewed-by: Ian Lance Taylor <[email protected]> Reviewed-by: Adam Langley <[email protected]> Reviewed-on: https://go-review.googlesource.com/57941
1 parent fb11572 commit 775b238

File tree

2 files changed

+23
-32
lines changed

2 files changed

+23
-32
lines changed

src/crypto/ecdsa/boring.go

+20-29
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,10 @@
55
package ecdsa
66

77
import (
8-
"crypto/elliptic"
98
"crypto/internal/boring"
109
"math/big"
10+
"sync/atomic"
11+
"unsafe"
1112
)
1213

1314
// Cached conversions from Go PublicKey/PrivateKey to BoringCrypto.
@@ -29,81 +30,71 @@ import (
2930

3031
type boringPub struct {
3132
key *boring.PublicKeyECDSA
32-
orig publicKey
33-
}
34-
35-
// copy of PublicKey without the atomic.Value field, to placate vet.
36-
type publicKey struct {
37-
elliptic.Curve
38-
X, Y *big.Int
33+
orig PublicKey
3934
}
4035

4136
func boringPublicKey(pub *PublicKey) (*boring.PublicKeyECDSA, error) {
42-
b, _ := pub.boring.Load().(boringPub)
43-
if publicKeyEqual(&b.orig, pub) {
37+
b := (*boringPub)(atomic.LoadPointer(&pub.boring))
38+
if b != nil && publicKeyEqual(&b.orig, pub) {
4439
return b.key, nil
4540
}
4641

42+
b = new(boringPub)
4743
b.orig = copyPublicKey(pub)
4844
key, err := boring.NewPublicKeyECDSA(b.orig.Curve.Params().Name, b.orig.X, b.orig.Y)
4945
if err != nil {
5046
return nil, err
5147
}
5248
b.key = key
53-
pub.boring.Store(b)
49+
atomic.StorePointer(&pub.boring, unsafe.Pointer(b))
5450
return key, nil
5551
}
5652

5753
type boringPriv struct {
5854
key *boring.PrivateKeyECDSA
59-
orig privateKey
60-
}
61-
62-
// copy of PrivateKey without the atomic.Value field, to placate vet.
63-
type privateKey struct {
64-
publicKey
65-
D *big.Int
55+
orig PrivateKey
6656
}
6757

6858
func boringPrivateKey(priv *PrivateKey) (*boring.PrivateKeyECDSA, error) {
69-
b, _ := priv.boring.Load().(boringPriv)
70-
if privateKeyEqual(&b.orig, priv) {
59+
b := (*boringPriv)(atomic.LoadPointer(&priv.boring))
60+
if b != nil && privateKeyEqual(&b.orig, priv) {
7161
return b.key, nil
7262
}
7363

64+
b = new(boringPriv)
7465
b.orig = copyPrivateKey(priv)
7566
key, err := boring.NewPrivateKeyECDSA(b.orig.Curve.Params().Name, b.orig.X, b.orig.Y, b.orig.D)
7667
if err != nil {
7768
return nil, err
7869
}
7970
b.key = key
80-
priv.boring.Store(b)
71+
atomic.StorePointer(&priv.boring, unsafe.Pointer(b))
8172
return key, nil
8273
}
8374

84-
func publicKeyEqual(k1 *publicKey, k2 *PublicKey) bool {
75+
func publicKeyEqual(k1, k2 *PublicKey) bool {
8576
return k1.X != nil &&
8677
k1.Curve.Params() == k2.Curve.Params() &&
8778
k1.X.Cmp(k2.X) == 0 &&
8879
k1.Y.Cmp(k2.Y) == 0
8980
}
9081

91-
func privateKeyEqual(k1 *privateKey, k2 *PrivateKey) bool {
92-
return publicKeyEqual(&k1.publicKey, &k2.PublicKey) &&
82+
func privateKeyEqual(k1, k2 *PrivateKey) bool {
83+
return publicKeyEqual(&k1.PublicKey, &k2.PublicKey) &&
9384
k1.D.Cmp(k2.D) == 0
9485
}
9586

96-
func copyPublicKey(k *PublicKey) publicKey {
97-
return publicKey{
87+
func copyPublicKey(k *PublicKey) PublicKey {
88+
return PublicKey{
9889
Curve: k.Curve,
9990
X: new(big.Int).Set(k.X),
10091
Y: new(big.Int).Set(k.Y),
10192
}
10293
}
10394

104-
func copyPrivateKey(k *PrivateKey) privateKey {
105-
return privateKey{
106-
publicKey: copyPublicKey(&k.PublicKey),
95+
func copyPrivateKey(k *PrivateKey) PrivateKey {
96+
return PrivateKey{
97+
PublicKey: copyPublicKey(&k.PublicKey),
10798
D: new(big.Int).Set(k.D),
10899
}
109100
}

src/crypto/ecdsa/ecdsa.go

+3-3
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,7 @@ import (
2727
"errors"
2828
"io"
2929
"math/big"
30-
"sync/atomic"
30+
"unsafe"
3131
)
3232

3333
// A invertible implements fast inverse mod Curve.Params().N
@@ -50,15 +50,15 @@ type PublicKey struct {
5050
elliptic.Curve
5151
X, Y *big.Int
5252

53-
boring atomic.Value
53+
boring unsafe.Pointer
5454
}
5555

5656
// PrivateKey represents a ECDSA private key.
5757
type PrivateKey struct {
5858
PublicKey
5959
D *big.Int
6060

61-
boring atomic.Value
61+
boring unsafe.Pointer
6262
}
6363

6464
type ecdsaSignature struct {

0 commit comments

Comments
 (0)