node.go 2.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104
  1. // Copyright 2015 The go-ethereum Authors
  2. // This file is part of the go-ethereum library.
  3. //
  4. // The go-ethereum library is free software: you can redistribute it and/or modify
  5. // it under the terms of the GNU Lesser General Public License as published by
  6. // the Free Software Foundation, either version 3 of the License, or
  7. // (at your option) any later version.
  8. //
  9. // The go-ethereum library is distributed in the hope that it will be useful,
  10. // but WITHOUT ANY WARRANTY; without even the implied warranty of
  11. // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  12. // GNU Lesser General Public License for more details.
  13. //
  14. // You should have received a copy of the GNU Lesser General Public License
  15. // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>.
  16. package discover
  17. import (
  18. "crypto/ecdsa"
  19. "errors"
  20. "math/big"
  21. "net"
  22. "time"
  23. "github.com/ethereum/go-ethereum/common/math"
  24. "github.com/ethereum/go-ethereum/crypto"
  25. "github.com/ethereum/go-ethereum/p2p/enode"
  26. )
  27. // node represents a host on the network.
  28. // The fields of Node may not be modified.
  29. type node struct {
  30. enode.Node
  31. addedAt time.Time // time when the node was added to the table
  32. livenessChecks uint // how often liveness was checked
  33. }
  34. type encPubkey [64]byte
  35. func encodePubkey(key *ecdsa.PublicKey) encPubkey {
  36. var e encPubkey
  37. math.ReadBits(key.X, e[:len(e)/2])
  38. math.ReadBits(key.Y, e[len(e)/2:])
  39. return e
  40. }
  41. func decodePubkey(e encPubkey) (*ecdsa.PublicKey, error) {
  42. p := &ecdsa.PublicKey{Curve: crypto.S256(), X: new(big.Int), Y: new(big.Int)}
  43. half := len(e) / 2
  44. p.X.SetBytes(e[:half])
  45. p.Y.SetBytes(e[half:])
  46. if !p.Curve.IsOnCurve(p.X, p.Y) {
  47. return nil, errors.New("invalid secp256k1 curve point")
  48. }
  49. return p, nil
  50. }
  51. func (e encPubkey) id() enode.ID {
  52. return enode.ID(crypto.Keccak256Hash(e[:]))
  53. }
  54. // recoverNodeKey computes the public key used to sign the
  55. // given hash from the signature.
  56. func recoverNodeKey(hash, sig []byte) (key encPubkey, err error) {
  57. pubkey, err := crypto.Ecrecover(hash, sig)
  58. if err != nil {
  59. return key, err
  60. }
  61. copy(key[:], pubkey[1:])
  62. return key, nil
  63. }
  64. func wrapNode(n *enode.Node) *node {
  65. return &node{Node: *n}
  66. }
  67. func wrapNodes(ns []*enode.Node) []*node {
  68. result := make([]*node, len(ns))
  69. for i, n := range ns {
  70. result[i] = wrapNode(n)
  71. }
  72. return result
  73. }
  74. func unwrapNode(n *node) *enode.Node {
  75. return &n.Node
  76. }
  77. func unwrapNodes(ns []*node) []*enode.Node {
  78. result := make([]*enode.Node, len(ns))
  79. for i, n := range ns {
  80. result[i] = unwrapNode(n)
  81. }
  82. return result
  83. }
  84. func (n *node) addr() *net.UDPAddr {
  85. return &net.UDPAddr{IP: n.IP(), Port: n.UDP()}
  86. }
  87. func (n *node) String() string {
  88. return n.Node.String()
  89. }