You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

215 lines
5.1 KiB

9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
9 years ago
  1. package crypto
  2. import (
  3. "bytes"
  4. secp256k1 "github.com/btcsuite/btcd/btcec"
  5. "github.com/tendermint/ed25519"
  6. "github.com/tendermint/ed25519/extra25519"
  7. . "github.com/tendermint/go-common"
  8. data "github.com/tendermint/go-data"
  9. "github.com/tendermint/go-wire"
  10. "golang.org/x/crypto/ripemd160"
  11. )
  12. // PubKey is part of Account and Validator.
  13. type PubKey interface {
  14. Address() []byte
  15. Bytes() []byte
  16. KeyString() string
  17. VerifyBytes(msg []byte, sig Signature) bool
  18. Equals(PubKey) bool
  19. }
  20. // Types of PubKey implementations
  21. const (
  22. PubKeyTypeEd25519 = byte(0x01)
  23. PubKeyTypeSecp256k1 = byte(0x02)
  24. PubKeyNameEd25519 = "ed25519"
  25. PubKeyNameSecp256k1 = "secp256k1"
  26. )
  27. var pubKeyMapper data.Mapper
  28. // register both public key types with go-data (and thus go-wire)
  29. func init() {
  30. pubKeyMapper = data.NewMapper(PubKeyS{}).
  31. RegisterInterface(PubKeyEd25519{}, PubKeyNameEd25519, PubKeyTypeEd25519).
  32. RegisterInterface(PubKeySecp256k1{}, PubKeyNameSecp256k1, PubKeyTypeSecp256k1)
  33. }
  34. // PubKeyS add json serialization to PubKey
  35. type PubKeyS struct {
  36. PubKey
  37. }
  38. func (p PubKeyS) MarshalJSON() ([]byte, error) {
  39. return pubKeyMapper.ToJSON(p.PubKey)
  40. }
  41. func (p *PubKeyS) UnmarshalJSON(data []byte) (err error) {
  42. parsed, err := pubKeyMapper.FromJSON(data)
  43. if err == nil {
  44. p.PubKey = parsed.(PubKey)
  45. }
  46. return
  47. }
  48. func (p PubKeyS) Empty() bool {
  49. return p.PubKey == nil
  50. }
  51. func PubKeyFromBytes(pubKeyBytes []byte) (pubKey PubKey, err error) {
  52. err = wire.ReadBinaryBytes(pubKeyBytes, &pubKey)
  53. return
  54. }
  55. //-------------------------------------
  56. // Implements PubKey
  57. type PubKeyEd25519 [32]byte
  58. func (pubKey PubKeyEd25519) Address() []byte {
  59. w, n, err := new(bytes.Buffer), new(int), new(error)
  60. wire.WriteBinary(pubKey[:], w, n, err)
  61. if *err != nil {
  62. PanicCrisis(*err)
  63. }
  64. // append type byte
  65. encodedPubkey := append([]byte{PubKeyTypeEd25519}, w.Bytes()...)
  66. hasher := ripemd160.New()
  67. hasher.Write(encodedPubkey) // does not error
  68. return hasher.Sum(nil)
  69. }
  70. func (pubKey PubKeyEd25519) Bytes() []byte {
  71. return wire.BinaryBytes(struct{ PubKey }{pubKey})
  72. }
  73. func (pubKey PubKeyEd25519) VerifyBytes(msg []byte, sig_ Signature) bool {
  74. // unwrap if needed
  75. if wrap, ok := sig_.(SignatureS); ok {
  76. sig_ = wrap.Signature
  77. }
  78. // make sure we use the same algorithm to sign
  79. sig, ok := sig_.(SignatureEd25519)
  80. if !ok {
  81. return false
  82. }
  83. pubKeyBytes := [32]byte(pubKey)
  84. sigBytes := [64]byte(sig)
  85. return ed25519.Verify(&pubKeyBytes, msg, &sigBytes)
  86. }
  87. func (p PubKeyEd25519) MarshalJSON() ([]byte, error) {
  88. return data.Encoder.Marshal(p[:])
  89. }
  90. func (p *PubKeyEd25519) UnmarshalJSON(enc []byte) error {
  91. var ref []byte
  92. err := data.Encoder.Unmarshal(&ref, enc)
  93. copy(p[:], ref)
  94. return err
  95. }
  96. // For use with golang/crypto/nacl/box
  97. // If error, returns nil.
  98. func (pubKey PubKeyEd25519) ToCurve25519() *[32]byte {
  99. keyCurve25519, pubKeyBytes := new([32]byte), [32]byte(pubKey)
  100. ok := extra25519.PublicKeyToCurve25519(keyCurve25519, &pubKeyBytes)
  101. if !ok {
  102. return nil
  103. }
  104. return keyCurve25519
  105. }
  106. func (pubKey PubKeyEd25519) String() string {
  107. return Fmt("PubKeyEd25519{%X}", pubKey[:])
  108. }
  109. // Must return the full bytes in hex.
  110. // Used for map keying, etc.
  111. func (pubKey PubKeyEd25519) KeyString() string {
  112. return Fmt("%X", pubKey[:])
  113. }
  114. func (pubKey PubKeyEd25519) Equals(other PubKey) bool {
  115. if otherEd, ok := other.(PubKeyEd25519); ok {
  116. return bytes.Equal(pubKey[:], otherEd[:])
  117. } else {
  118. return false
  119. }
  120. }
  121. //-------------------------------------
  122. // Implements PubKey
  123. type PubKeySecp256k1 [64]byte
  124. func (pubKey PubKeySecp256k1) Address() []byte {
  125. w, n, err := new(bytes.Buffer), new(int), new(error)
  126. wire.WriteBinary(pubKey[:], w, n, err)
  127. if *err != nil {
  128. PanicCrisis(*err)
  129. }
  130. // append type byte
  131. encodedPubkey := append([]byte{PubKeyTypeSecp256k1}, w.Bytes()...)
  132. hasher := ripemd160.New()
  133. hasher.Write(encodedPubkey) // does not error
  134. return hasher.Sum(nil)
  135. }
  136. func (pubKey PubKeySecp256k1) Bytes() []byte {
  137. return wire.BinaryBytes(struct{ PubKey }{pubKey})
  138. }
  139. func (pubKey PubKeySecp256k1) VerifyBytes(msg []byte, sig_ Signature) bool {
  140. // unwrap if needed
  141. if wrap, ok := sig_.(SignatureS); ok {
  142. sig_ = wrap.Signature
  143. }
  144. // and assert same algorithm to sign and verify
  145. sig, ok := sig_.(SignatureSecp256k1)
  146. if !ok {
  147. return false
  148. }
  149. pub__, err := secp256k1.ParsePubKey(append([]byte{0x04}, pubKey[:]...), secp256k1.S256())
  150. if err != nil {
  151. return false
  152. }
  153. sig__, err := secp256k1.ParseDERSignature(sig[:], secp256k1.S256())
  154. if err != nil {
  155. return false
  156. }
  157. return sig__.Verify(Sha256(msg), pub__)
  158. }
  159. func (p PubKeySecp256k1) MarshalJSON() ([]byte, error) {
  160. return data.Encoder.Marshal(p[:])
  161. }
  162. func (p *PubKeySecp256k1) UnmarshalJSON(enc []byte) error {
  163. var ref []byte
  164. err := data.Encoder.Unmarshal(&ref, enc)
  165. copy(p[:], ref)
  166. return err
  167. }
  168. func (pubKey PubKeySecp256k1) String() string {
  169. return Fmt("PubKeySecp256k1{%X}", pubKey[:])
  170. }
  171. // Must return the full bytes in hex.
  172. // Used for map keying, etc.
  173. func (pubKey PubKeySecp256k1) KeyString() string {
  174. return Fmt("%X", pubKey[:])
  175. }
  176. func (pubKey PubKeySecp256k1) Equals(other PubKey) bool {
  177. if otherSecp, ok := other.(PubKeySecp256k1); ok {
  178. return bytes.Equal(pubKey[:], otherSecp[:])
  179. } else {
  180. return false
  181. }
  182. }