keychain: add single key wrapper implementations
This commit is contained in:
parent
6cf1844b0e
commit
cf0380ac81
82
keychain/ecdh.go
Normal file
82
keychain/ecdh.go
Normal file
@ -0,0 +1,82 @@
|
|||||||
|
package keychain
|
||||||
|
|
||||||
|
import (
|
||||||
|
"crypto/sha256"
|
||||||
|
|
||||||
|
"github.com/btcsuite/btcd/btcec"
|
||||||
|
)
|
||||||
|
|
||||||
|
// NewPubKeyECDH wraps the given key of the key ring so it adheres to the
|
||||||
|
// SingleKeyECDH interface.
|
||||||
|
func NewPubKeyECDH(keyDesc KeyDescriptor, ecdh ECDHRing) *PubKeyECDH {
|
||||||
|
return &PubKeyECDH{
|
||||||
|
keyDesc: keyDesc,
|
||||||
|
ecdh: ecdh,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// PubKeyECDH is an implementation of the SingleKeyECDH interface. It wraps an
|
||||||
|
// ECDH key ring so it can perform ECDH shared key generation against a single
|
||||||
|
// abstracted away private key.
|
||||||
|
type PubKeyECDH struct {
|
||||||
|
keyDesc KeyDescriptor
|
||||||
|
ecdh ECDHRing
|
||||||
|
}
|
||||||
|
|
||||||
|
// PubKey returns the public key of the private key that is abstracted away by
|
||||||
|
// the interface.
|
||||||
|
//
|
||||||
|
// NOTE: This is part of the SingleKeyECDH interface.
|
||||||
|
func (p *PubKeyECDH) PubKey() *btcec.PublicKey {
|
||||||
|
return p.keyDesc.PubKey
|
||||||
|
}
|
||||||
|
|
||||||
|
// ECDH performs a scalar multiplication (ECDH-like operation) between the
|
||||||
|
// abstracted private key and a remote public key. The output returned will be
|
||||||
|
// the sha256 of the resulting shared point serialized in compressed format. If
|
||||||
|
// k is our private key, and P is the public key, we perform the following
|
||||||
|
// operation:
|
||||||
|
//
|
||||||
|
// sx := k*P
|
||||||
|
// s := sha256(sx.SerializeCompressed())
|
||||||
|
//
|
||||||
|
// NOTE: This is part of the SingleKeyECDH interface.
|
||||||
|
func (p *PubKeyECDH) ECDH(pubKey *btcec.PublicKey) ([32]byte, error) {
|
||||||
|
return p.ecdh.ECDH(p.keyDesc, pubKey)
|
||||||
|
}
|
||||||
|
|
||||||
|
// PrivKeyECDH is an implementation of the SingleKeyECDH in which we do have the
|
||||||
|
// full private key. This can be used to wrap a temporary key to conform to the
|
||||||
|
// SingleKeyECDH interface.
|
||||||
|
type PrivKeyECDH struct {
|
||||||
|
// PrivKey is the private key that is used for the ECDH operation.
|
||||||
|
PrivKey *btcec.PrivateKey
|
||||||
|
}
|
||||||
|
|
||||||
|
// PubKey returns the public key of the private key that is abstracted away by
|
||||||
|
// the interface.
|
||||||
|
//
|
||||||
|
// NOTE: This is part of the SingleKeyECDH interface.
|
||||||
|
func (p *PrivKeyECDH) PubKey() *btcec.PublicKey {
|
||||||
|
return p.PrivKey.PubKey()
|
||||||
|
}
|
||||||
|
|
||||||
|
// ECDH performs a scalar multiplication (ECDH-like operation) between the
|
||||||
|
// abstracted private key and a remote public key. The output returned will be
|
||||||
|
// the sha256 of the resulting shared point serialized in compressed format. If
|
||||||
|
// k is our private key, and P is the public key, we perform the following
|
||||||
|
// operation:
|
||||||
|
//
|
||||||
|
// sx := k*P
|
||||||
|
// s := sha256(sx.SerializeCompressed())
|
||||||
|
//
|
||||||
|
// NOTE: This is part of the SingleKeyECDH interface.
|
||||||
|
func (p *PrivKeyECDH) ECDH(pub *btcec.PublicKey) ([32]byte, error) {
|
||||||
|
s := &btcec.PublicKey{}
|
||||||
|
s.X, s.Y = btcec.S256().ScalarMult(pub.X, pub.Y, p.PrivKey.D.Bytes())
|
||||||
|
|
||||||
|
return sha256.Sum256(s.SerializeCompressed()), nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var _ SingleKeyECDH = (*PubKeyECDH)(nil)
|
||||||
|
var _ SingleKeyECDH = (*PrivKeyECDH)(nil)
|
56
keychain/signer.go
Normal file
56
keychain/signer.go
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
package keychain
|
||||||
|
|
||||||
|
import "github.com/btcsuite/btcd/btcec"
|
||||||
|
|
||||||
|
func NewPubKeyDigestSigner(keyDesc KeyDescriptor,
|
||||||
|
signer DigestSignerRing) *PubKeyDigestSigner {
|
||||||
|
|
||||||
|
return &PubKeyDigestSigner{
|
||||||
|
keyDesc: keyDesc,
|
||||||
|
digestSigner: signer,
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
type PubKeyDigestSigner struct {
|
||||||
|
keyDesc KeyDescriptor
|
||||||
|
digestSigner DigestSignerRing
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PubKeyDigestSigner) PubKey() *btcec.PublicKey {
|
||||||
|
return p.keyDesc.PubKey
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PubKeyDigestSigner) SignDigest(digest [32]byte) (*btcec.Signature,
|
||||||
|
error) {
|
||||||
|
|
||||||
|
return p.digestSigner.SignDigest(p.keyDesc, digest)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PubKeyDigestSigner) SignDigestCompact(digest [32]byte) ([]byte,
|
||||||
|
error) {
|
||||||
|
|
||||||
|
return p.digestSigner.SignDigestCompact(p.keyDesc, digest)
|
||||||
|
}
|
||||||
|
|
||||||
|
type PrivKeyDigestSigner struct {
|
||||||
|
PrivKey *btcec.PrivateKey
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PrivKeyDigestSigner) PubKey() *btcec.PublicKey {
|
||||||
|
return p.PrivKey.PubKey()
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PrivKeyDigestSigner) SignDigest(digest [32]byte) (*btcec.Signature,
|
||||||
|
error) {
|
||||||
|
|
||||||
|
return p.PrivKey.Sign(digest[:])
|
||||||
|
}
|
||||||
|
|
||||||
|
func (p *PrivKeyDigestSigner) SignDigestCompact(digest [32]byte) ([]byte,
|
||||||
|
error) {
|
||||||
|
|
||||||
|
return btcec.SignCompact(btcec.S256(), p.PrivKey, digest[:], true)
|
||||||
|
}
|
||||||
|
|
||||||
|
var _ SingleKeyDigestSigner = (*PubKeyDigestSigner)(nil)
|
||||||
|
var _ SingleKeyDigestSigner = (*PrivKeyDigestSigner)(nil)
|
Loading…
Reference in New Issue
Block a user