core/types: don't use Address zero value for invalid addresses

pull/532/head
Felix Lange 10 years ago
parent d5de6489d7
commit e91ab84dbe
  1. 59
      core/types/transaction.go
  2. 3
      core/types/transaction_test.go

@ -2,6 +2,7 @@ package types
import ( import (
"bytes" "bytes"
"errors"
"fmt" "fmt"
"io" "io"
"math/big" "math/big"
@ -21,19 +22,19 @@ type Transaction struct {
AccountNonce uint64 AccountNonce uint64
Price *big.Int Price *big.Int
GasLimit *big.Int GasLimit *big.Int
Recipient common.Address Recipient *common.Address // nil means contract creation
Amount *big.Int Amount *big.Int
Payload []byte Payload []byte
V byte V byte
R, S []byte R, S []byte
} }
func NewContractCreationTx(amount, gasAmount, price *big.Int, data []byte) *Transaction { func NewContractCreationTx(amount, gasLimit, gasPrice *big.Int, data []byte) *Transaction {
return NewTransactionMessage(common.Address{}, amount, gasAmount, price, data) return &Transaction{Recipient: nil, Amount: amount, GasLimit: gasLimit, Price: gasPrice, Payload: data}
} }
func NewTransactionMessage(to common.Address, amount, gasAmount, price *big.Int, data []byte) *Transaction { func NewTransactionMessage(to common.Address, amount, gasAmount, gasPrice *big.Int, data []byte) *Transaction {
return &Transaction{Recipient: to, Amount: amount, Price: price, GasLimit: gasAmount, Payload: data} return &Transaction{Recipient: &to, Amount: amount, GasLimit: gasAmount, Price: gasPrice, Payload: data}
} }
func NewTransactionFromBytes(data []byte) *Transaction { func NewTransactionFromBytes(data []byte) *Transaction {
@ -73,12 +74,21 @@ func (self *Transaction) SetNonce(AccountNonce uint64) {
self.AccountNonce = AccountNonce self.AccountNonce = AccountNonce
} }
func (self *Transaction) From() common.Address { func (self *Transaction) From() (common.Address, error) {
return self.sender() pubkey := self.PublicKey()
if len(pubkey) == 0 || pubkey[0] != 4 {
return common.Address{}, errors.New("invalid public key")
}
var addr common.Address
copy(addr[:], crypto.Sha3(pubkey[1:]))
return addr, nil
} }
func (self *Transaction) To() common.Address { // To returns the recipient of the transaction.
return self.Recipient // If transaction is a contract creation (with no recipient address)
// To returns nil.
func (tx *Transaction) To() *common.Address {
return tx.Recipient
} }
func (tx *Transaction) Curve() (v byte, r []byte, s []byte) { func (tx *Transaction) Curve() (v byte, r []byte, s []byte) {
@ -105,18 +115,6 @@ func (tx *Transaction) PublicKey() []byte {
return pubkey return pubkey
} }
func (tx *Transaction) sender() (a common.Address) {
pubkey := tx.PublicKey()
// Validate the returned key.
// Return nil if public key isn't in full format
if len(pubkey) == 0 || pubkey[0] != 4 {
return a
}
copy(a[:], crypto.Sha3(pubkey[1:]))
return a
}
func (tx *Transaction) SetSignatureValues(sig []byte) error { func (tx *Transaction) SetSignatureValues(sig []byte) error {
tx.R = sig[:32] tx.R = sig[:32]
tx.S = sig[32:64] tx.S = sig[32:64]
@ -149,11 +147,22 @@ func (tx *Transaction) RlpEncode() []byte {
} }
func (tx *Transaction) String() string { func (tx *Transaction) String() string {
var from, to string
if f, err := tx.From(); err != nil {
from = "[invalid sender]"
} else {
from = fmt.Sprintf("%x", f[:])
}
if t := tx.To(); t == nil {
to = "[contract creation]"
} else {
to = fmt.Sprintf("%x", t[:])
}
return fmt.Sprintf(` return fmt.Sprintf(`
TX(%x) TX(%x)
Contract: %v Contract: %v
From: %x From: %s
To: %x To: %s
Nonce: %v Nonce: %v
GasPrice: %v GasPrice: %v
GasLimit %v GasLimit %v
@ -166,8 +175,8 @@ func (tx *Transaction) String() string {
`, `,
tx.Hash(), tx.Hash(),
len(tx.Recipient) == 0, len(tx.Recipient) == 0,
tx.From(), from,
tx.To(), to,
tx.AccountNonce, tx.AccountNonce,
tx.Price, tx.Price,
tx.GasLimit, tx.GasLimit,

@ -19,8 +19,9 @@ var (
nil, nil,
) )
rightvrsRecipient = common.HexToAddress("b94f5374fce5edbc8e2a8697c15331677e6ebf0b")
rightvrsTx = &Transaction{ rightvrsTx = &Transaction{
Recipient: common.HexToAddress("b94f5374fce5edbc8e2a8697c15331677e6ebf0b"), Recipient: &rightvrsRecipient,
AccountNonce: 3, AccountNonce: 3,
Price: big.NewInt(1), Price: big.NewInt(1),
GasLimit: big.NewInt(2000), GasLimit: big.NewInt(2000),

Loading…
Cancel
Save