github.com/gochain-io/gochain@v2.2.26+incompatible/core/types/transaction.go (about)

     1  // Copyright 2014 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  
    17  package types
    18  
    19  import (
    20  	"container/heap"
    21  	"context"
    22  	"errors"
    23  	"io"
    24  	"math/big"
    25  	"sync/atomic"
    26  
    27  	"github.com/gochain-io/gochain/common"
    28  	"github.com/gochain-io/gochain/common/hexutil"
    29  	"github.com/gochain-io/gochain/crypto"
    30  	"github.com/gochain-io/gochain/rlp"
    31  )
    32  
    33  //go:generate gencodec -type txdata -field-override txdataMarshaling -out gen_tx_json.go
    34  
    35  var (
    36  	ErrInvalidSig = errors.New("invalid transaction v, r, s values")
    37  	errNoSigner   = errors.New("missing signing methods")
    38  )
    39  
    40  type Transaction struct {
    41  	data txdata
    42  	// caches
    43  	hash atomic.Value
    44  	size atomic.Value
    45  	from atomic.Value
    46  }
    47  
    48  type txdata struct {
    49  	AccountNonce uint64          `json:"nonce"    gencodec:"required"`
    50  	Price        *big.Int        `json:"gasPrice" gencodec:"required"`
    51  	GasLimit     uint64          `json:"gas"      gencodec:"required"`
    52  	Recipient    *common.Address `json:"to"       rlp:"nil"` // nil means contract creation
    53  	Amount       *big.Int        `json:"value"    gencodec:"required"`
    54  	Payload      []byte          `json:"input"    gencodec:"required"`
    55  
    56  	// Signature values
    57  	V *big.Int `json:"v" gencodec:"required"`
    58  	R *big.Int `json:"r" gencodec:"required"`
    59  	S *big.Int `json:"s" gencodec:"required"`
    60  
    61  	// This is only used when marshaling to JSON.
    62  	Hash *common.Hash `json:"hash" rlp:"-"`
    63  }
    64  
    65  type txdataMarshaling struct {
    66  	AccountNonce hexutil.Uint64
    67  	Price        *hexutil.Big
    68  	GasLimit     hexutil.Uint64
    69  	Amount       *hexutil.Big
    70  	Payload      hexutil.Bytes
    71  	V            *hexutil.Big
    72  	R            *hexutil.Big
    73  	S            *hexutil.Big
    74  }
    75  
    76  func NewTransaction(nonce uint64, to common.Address, amount *big.Int, gasLimit uint64, gasPrice *big.Int, data []byte) *Transaction {
    77  	return newTransaction(nonce, &to, amount, gasLimit, gasPrice, data)
    78  }
    79  
    80  func NewContractCreation(nonce uint64, amount *big.Int, gasLimit uint64, gasPrice *big.Int, data []byte) *Transaction {
    81  	return newTransaction(nonce, nil, amount, gasLimit, gasPrice, data)
    82  }
    83  
    84  func newTransaction(nonce uint64, to *common.Address, amount *big.Int, gasLimit uint64, gasPrice *big.Int, data []byte) *Transaction {
    85  	if len(data) > 0 {
    86  		data = common.CopyBytes(data)
    87  	}
    88  	d := txdata{
    89  		AccountNonce: nonce,
    90  		Recipient:    to,
    91  		Payload:      data,
    92  		Amount:       new(big.Int),
    93  		GasLimit:     gasLimit,
    94  		Price:        new(big.Int),
    95  		V:            new(big.Int),
    96  		R:            new(big.Int),
    97  		S:            new(big.Int),
    98  	}
    99  	if amount != nil {
   100  		d.Amount.Set(amount)
   101  	}
   102  	if gasPrice != nil {
   103  		d.Price.Set(gasPrice)
   104  	}
   105  
   106  	return &Transaction{data: d}
   107  }
   108  
   109  // ChainId returns which chain id this transaction was signed for (if at all)
   110  func (tx *Transaction) ChainId() *big.Int {
   111  	return deriveChainId(tx.data.V)
   112  }
   113  
   114  // Protected returns whether the transaction is protected from replay protection.
   115  func (tx *Transaction) Protected() bool {
   116  	return isProtectedV(tx.data.V)
   117  }
   118  
   119  func isProtectedV(V *big.Int) bool {
   120  	if V.BitLen() <= 8 {
   121  		v := V.Uint64()
   122  		return v != 27 && v != 28
   123  	}
   124  	// anything not 27 or 28 is considered protected
   125  	return true
   126  }
   127  
   128  // EncodeRLP implements rlp.Encoder
   129  func (tx *Transaction) EncodeRLP(w io.Writer) error {
   130  	return rlp.Encode(w, &tx.data)
   131  }
   132  
   133  // DecodeRLP implements rlp.Decoder
   134  func (tx *Transaction) DecodeRLP(s *rlp.Stream) error {
   135  	_, size, _ := s.Kind()
   136  	err := s.Decode(&tx.data)
   137  	if err == nil {
   138  		tx.size.Store(common.StorageSize(rlp.ListSize(size)))
   139  	}
   140  
   141  	return err
   142  }
   143  
   144  // MarshalJSON encodes the web3 RPC transaction format.
   145  func (tx *Transaction) MarshalJSON() ([]byte, error) {
   146  	hash := tx.Hash()
   147  	data := tx.data
   148  	data.Hash = &hash
   149  	return data.MarshalJSON()
   150  }
   151  
   152  // UnmarshalJSON decodes the web3 RPC transaction format.
   153  func (tx *Transaction) UnmarshalJSON(input []byte) error {
   154  	var dec txdata
   155  	if err := dec.UnmarshalJSON(input); err != nil {
   156  		return err
   157  	}
   158  
   159  	withSignature := dec.V.Sign() != 0 || dec.R.Sign() != 0 || dec.S.Sign() != 0
   160  	if withSignature {
   161  		var V byte
   162  		if isProtectedV(dec.V) {
   163  			chainID := deriveChainId(dec.V).Uint64()
   164  			V = byte(dec.V.Uint64() - 35 - 2*chainID)
   165  		} else {
   166  			V = byte(dec.V.Uint64() - 27)
   167  		}
   168  		if !crypto.ValidateSignatureValues(V, dec.R, dec.S, false) {
   169  			return ErrInvalidSig
   170  		}
   171  	}
   172  
   173  	*tx = Transaction{data: dec}
   174  	return nil
   175  }
   176  
   177  func (tx *Transaction) Data() []byte                       { return common.CopyBytes(tx.data.Payload) }
   178  func (tx *Transaction) Gas() uint64                        { return tx.data.GasLimit }
   179  func (tx *Transaction) GasPrice() *big.Int                 { return new(big.Int).Set(tx.data.Price) }
   180  func (tx *Transaction) CmpGasPriceTx(tx2 *Transaction) int { return tx.data.Price.Cmp(tx2.data.Price) }
   181  func (tx *Transaction) CmpGasPrice(i *big.Int) int         { return tx.data.Price.Cmp(i) }
   182  func (tx *Transaction) Value() *big.Int                    { return new(big.Int).Set(tx.data.Amount) }
   183  func (tx *Transaction) Nonce() uint64                      { return tx.data.AccountNonce }
   184  func (tx *Transaction) CheckNonce() bool                   { return true }
   185  
   186  // To returns the recipient address of the transaction.
   187  // It returns nil if the transaction is a contract creation.
   188  func (tx *Transaction) To() *common.Address {
   189  	if tx.data.Recipient == nil {
   190  		return nil
   191  	}
   192  	to := *tx.data.Recipient
   193  	return &to
   194  }
   195  
   196  // Hash hashes the RLP encoding of tx.
   197  // It uniquely identifies the transaction.
   198  func (tx *Transaction) Hash() common.Hash {
   199  	if hash := tx.hash.Load(); hash != nil {
   200  		return hash.(common.Hash)
   201  	}
   202  	v := rlpHash(tx)
   203  	tx.hash.Store(v)
   204  	return v
   205  }
   206  
   207  // Size returns the true RLP encoded storage size of the transaction, either by
   208  // encoding and returning it, or returning a previsouly cached value.
   209  func (tx *Transaction) Size() common.StorageSize {
   210  	if size := tx.size.Load(); size != nil {
   211  		return size.(common.StorageSize)
   212  	}
   213  	c := writeCounter(0)
   214  	rlp.Encode(&c, &tx.data)
   215  	tx.size.Store(common.StorageSize(c))
   216  	return common.StorageSize(c)
   217  }
   218  
   219  // AsMessage returns the transaction as a core.Message.
   220  //
   221  // AsMessage requires a signer to derive the sender.
   222  //
   223  // XXX Rename message to something less arbitrary?
   224  func (tx *Transaction) AsMessage(ctx context.Context, s Signer) (*Message, error) {
   225  	from, err := Sender(s, tx)
   226  	if err != nil {
   227  		return nil, err
   228  	}
   229  	msg := &Message{
   230  		nonce:      tx.data.AccountNonce,
   231  		gasLimit:   tx.data.GasLimit,
   232  		gasPrice:   tx.data.Price,
   233  		to:         tx.data.Recipient,
   234  		amount:     tx.data.Amount,
   235  		data:       tx.data.Payload,
   236  		checkNonce: true,
   237  		from:       from,
   238  	}
   239  	return msg, nil
   240  }
   241  
   242  // WithSignature returns a new transaction with the given signature.
   243  // This signature needs to be formatted as described in the yellow paper (v+27).
   244  func (tx *Transaction) WithSignature(signer Signer, sig []byte) (*Transaction, error) {
   245  	r, s, v, err := signer.SignatureValues(tx, sig)
   246  	if err != nil {
   247  		return nil, err
   248  	}
   249  	cpy := &Transaction{data: tx.data}
   250  	cpy.data.R, cpy.data.S, cpy.data.V = r, s, v
   251  	return cpy, nil
   252  }
   253  
   254  // Cost returns amount + gasprice * gaslimit.
   255  func (tx *Transaction) Cost() *big.Int {
   256  	total := new(big.Int).Mul(tx.data.Price, new(big.Int).SetUint64(tx.data.GasLimit))
   257  	total.Add(total, tx.data.Amount)
   258  	return total
   259  }
   260  
   261  func (tx *Transaction) RawSignatureValues() (*big.Int, *big.Int, *big.Int) {
   262  	return tx.data.V, tx.data.R, tx.data.S
   263  }
   264  
   265  // Transactions is a Transaction slice type for basic sorting.
   266  type Transactions []*Transaction
   267  
   268  // Len returns the length of s.
   269  func (s Transactions) Len() int { return len(s) }
   270  
   271  // Swap swaps the i'th and the j'th element in s.
   272  func (s Transactions) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
   273  
   274  // GetRlp implements Rlpable and returns the i'th element of s in rlp.
   275  func (s Transactions) GetRlp(i int) []byte {
   276  	enc, _ := rlp.EncodeToBytes(s[i])
   277  	return enc
   278  }
   279  
   280  // TxByNonce implements the sort interface to allow sorting a list of transactions
   281  // by their nonces. This is usually only useful for sorting transactions from a
   282  // single account, otherwise a nonce comparison doesn't make much sense.
   283  type TxByNonce Transactions
   284  
   285  func (s TxByNonce) Len() int           { return len(s) }
   286  func (s TxByNonce) Less(i, j int) bool { return s[i].data.AccountNonce < s[j].data.AccountNonce }
   287  func (s TxByNonce) Swap(i, j int)      { s[i], s[j] = s[j], s[i] }
   288  
   289  // TxByPrice implements both the sort and the heap interface, making it useful
   290  // for all at once sorting as well as individually adding and removing elements.
   291  type TxByPrice Transactions
   292  
   293  func (s TxByPrice) Len() int           { return len(s) }
   294  func (s TxByPrice) Less(i, j int) bool { return s[i].data.Price.Cmp(s[j].data.Price) > 0 }
   295  func (s TxByPrice) Swap(i, j int)      { s[i], s[j] = s[j], s[i] }
   296  
   297  func (s *TxByPrice) Push(x interface{}) {
   298  	*s = append(*s, x.(*Transaction))
   299  }
   300  
   301  func (s *TxByPrice) Pop() interface{} {
   302  	old := *s
   303  	n := len(old)
   304  	x := old[n-1]
   305  	*s = old[0 : n-1]
   306  	return x
   307  }
   308  
   309  // TransactionsByPriceAndNonce represents a set of transactions that can return
   310  // transactions in a profit-maximizing sorted order, while supporting removing
   311  // entire batches of transactions for non-executable accounts.
   312  type TransactionsByPriceAndNonce struct {
   313  	txs    map[common.Address]Transactions // Per account nonce-sorted list of transactions
   314  	heads  TxByPrice                       // Next transaction for each unique account (price heap)
   315  	signer Signer                          // Signer for the set of transactions
   316  }
   317  
   318  // NewTransactionsByPriceAndNonce creates a transaction set that can retrieve
   319  // price sorted transactions in a nonce-honouring way.
   320  //
   321  // Note, the input map is reowned so the caller should not interact any more with
   322  // if after providing it to the constructor.
   323  func NewTransactionsByPriceAndNonce(signer Signer, txs map[common.Address]Transactions) *TransactionsByPriceAndNonce {
   324  	// Initialize a price based heap with the head transactions
   325  	heads := make(TxByPrice, 0, len(txs))
   326  	for from, accTxs := range txs {
   327  		if len(accTxs) > 0 {
   328  			heads = append(heads, accTxs[0])
   329  			// Ensure the sender address is from the signer
   330  			acc, _ := Sender(signer, accTxs[0])
   331  			txs[acc] = accTxs[1:]
   332  			if from != acc {
   333  				delete(txs, from)
   334  			}
   335  		}
   336  	}
   337  	heap.Init(&heads)
   338  
   339  	// Assemble and return the transaction set
   340  	return &TransactionsByPriceAndNonce{
   341  		txs:    txs,
   342  		heads:  heads,
   343  		signer: signer,
   344  	}
   345  }
   346  
   347  // Peek returns the next transaction by price.
   348  func (t *TransactionsByPriceAndNonce) Peek() *Transaction {
   349  	if len(t.heads) == 0 {
   350  		return nil
   351  	}
   352  	return t.heads[0]
   353  }
   354  
   355  // Shift replaces the current best head with the next one from the same account.
   356  func (t *TransactionsByPriceAndNonce) Shift() {
   357  	acc, _ := Sender(t.signer, t.heads[0])
   358  	if txs, ok := t.txs[acc]; ok && len(txs) > 0 {
   359  		t.heads[0], t.txs[acc] = txs[0], txs[1:]
   360  		heap.Fix(&t.heads, 0)
   361  	} else {
   362  		heap.Pop(&t.heads)
   363  	}
   364  }
   365  
   366  // Pop removes the best transaction, *not* replacing it with the next one from
   367  // the same account. This should be used when a transaction cannot be executed
   368  // and hence all subsequent ones should be discarded from the same account.
   369  func (t *TransactionsByPriceAndNonce) Pop() {
   370  	heap.Pop(&t.heads)
   371  }
   372  
   373  // Message is a fully derived transaction and implements core.Message
   374  //
   375  // NOTE: In a future PR this will be removed.
   376  type Message struct {
   377  	to         *common.Address
   378  	from       common.Address
   379  	nonce      uint64
   380  	amount     *big.Int
   381  	gasLimit   uint64
   382  	gasPrice   *big.Int
   383  	data       []byte
   384  	checkNonce bool
   385  }
   386  
   387  func NewMessage(from common.Address, to *common.Address, nonce uint64, amount *big.Int, gasLimit uint64, gasPrice *big.Int, data []byte, checkNonce bool) *Message {
   388  	return &Message{
   389  		from:       from,
   390  		to:         to,
   391  		nonce:      nonce,
   392  		amount:     amount,
   393  		gasLimit:   gasLimit,
   394  		gasPrice:   gasPrice,
   395  		data:       data,
   396  		checkNonce: checkNonce,
   397  	}
   398  }
   399  
   400  func (m *Message) From() common.Address { return m.from }
   401  func (m *Message) To() *common.Address  { return m.to }
   402  func (m *Message) GasPrice() *big.Int   { return m.gasPrice }
   403  func (m *Message) Value() *big.Int      { return m.amount }
   404  func (m *Message) Gas() uint64          { return m.gasLimit }
   405  func (m *Message) Nonce() uint64        { return m.nonce }
   406  func (m *Message) Data() []byte         { return m.data }
   407  func (m *Message) CheckNonce() bool     { return m.checkNonce }