* Add retesteth command * Remove label and insert full version * mineBlock - break the inner loop when the block is full * Fixes for touched non-reward accounts, gas limit issues * Not fail when SendTx has transaction with incorrect RLP * Fix linter (unnecessary conversion) * retesteth: add usage string to flag
		
			
				
	
	
		
			149 lines
		
	
	
		
			5.2 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			149 lines
		
	
	
		
			5.2 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
// Copyright 2019 The go-ethereum Authors
 | 
						|
// This file is part of go-ethereum.
 | 
						|
//
 | 
						|
// go-ethereum is free software: you can redistribute it and/or modify
 | 
						|
// it under the terms of the GNU General Public License as published by
 | 
						|
// the Free Software Foundation, either version 3 of the License, or
 | 
						|
// (at your option) any later version.
 | 
						|
//
 | 
						|
// go-ethereum is distributed in the hope that it will be useful,
 | 
						|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
 | 
						|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
 | 
						|
// GNU General Public License for more details.
 | 
						|
//
 | 
						|
// You should have received a copy of the GNU General Public License
 | 
						|
// along with go-ethereum. If not, see <http://www.gnu.org/licenses/>.
 | 
						|
 | 
						|
package main
 | 
						|
 | 
						|
import (
 | 
						|
	"math/big"
 | 
						|
 | 
						|
	"github.com/ethereum/go-ethereum/common"
 | 
						|
	"github.com/ethereum/go-ethereum/common/hexutil"
 | 
						|
	"github.com/ethereum/go-ethereum/core/types"
 | 
						|
)
 | 
						|
 | 
						|
// RPCTransaction represents a transaction that will serialize to the RPC representation of a transaction
 | 
						|
type RPCTransaction struct {
 | 
						|
	BlockHash        common.Hash     `json:"blockHash"`
 | 
						|
	BlockNumber      *hexutil.Big    `json:"blockNumber"`
 | 
						|
	From             common.Address  `json:"from"`
 | 
						|
	Gas              hexutil.Uint64  `json:"gas"`
 | 
						|
	GasPrice         *hexutil.Big    `json:"gasPrice"`
 | 
						|
	Hash             common.Hash     `json:"hash"`
 | 
						|
	Input            hexutil.Bytes   `json:"input"`
 | 
						|
	Nonce            hexutil.Uint64  `json:"nonce"`
 | 
						|
	To               *common.Address `json:"to"`
 | 
						|
	TransactionIndex hexutil.Uint    `json:"transactionIndex"`
 | 
						|
	Value            *hexutil.Big    `json:"value"`
 | 
						|
	V                *hexutil.Big    `json:"v"`
 | 
						|
	R                *hexutil.Big    `json:"r"`
 | 
						|
	S                *hexutil.Big    `json:"s"`
 | 
						|
}
 | 
						|
 | 
						|
// newRPCTransaction returns a transaction that will serialize to the RPC
 | 
						|
// representation, with the given location metadata set (if available).
 | 
						|
func newRPCTransaction(tx *types.Transaction, blockHash common.Hash, blockNumber uint64, index uint64) *RPCTransaction {
 | 
						|
	var signer types.Signer = types.FrontierSigner{}
 | 
						|
	if tx.Protected() {
 | 
						|
		signer = types.NewEIP155Signer(tx.ChainId())
 | 
						|
	}
 | 
						|
	from, _ := types.Sender(signer, tx)
 | 
						|
	v, r, s := tx.RawSignatureValues()
 | 
						|
 | 
						|
	result := &RPCTransaction{
 | 
						|
		From:     from,
 | 
						|
		Gas:      hexutil.Uint64(tx.Gas()),
 | 
						|
		GasPrice: (*hexutil.Big)(tx.GasPrice()),
 | 
						|
		Hash:     tx.Hash(),
 | 
						|
		Input:    hexutil.Bytes(tx.Data()),
 | 
						|
		Nonce:    hexutil.Uint64(tx.Nonce()),
 | 
						|
		To:       tx.To(),
 | 
						|
		Value:    (*hexutil.Big)(tx.Value()),
 | 
						|
		V:        (*hexutil.Big)(v),
 | 
						|
		R:        (*hexutil.Big)(r),
 | 
						|
		S:        (*hexutil.Big)(s),
 | 
						|
	}
 | 
						|
	if blockHash != (common.Hash{}) {
 | 
						|
		result.BlockHash = blockHash
 | 
						|
		result.BlockNumber = (*hexutil.Big)(new(big.Int).SetUint64(blockNumber))
 | 
						|
		result.TransactionIndex = hexutil.Uint(index)
 | 
						|
	}
 | 
						|
	return result
 | 
						|
}
 | 
						|
 | 
						|
// newRPCTransactionFromBlockIndex returns a transaction that will serialize to the RPC representation.
 | 
						|
func newRPCTransactionFromBlockIndex(b *types.Block, index uint64) *RPCTransaction {
 | 
						|
	txs := b.Transactions()
 | 
						|
	if index >= uint64(len(txs)) {
 | 
						|
		return nil
 | 
						|
	}
 | 
						|
	return newRPCTransaction(txs[index], b.Hash(), b.NumberU64(), index)
 | 
						|
}
 | 
						|
 | 
						|
// newRPCTransactionFromBlockHash returns a transaction that will serialize to the RPC representation.
 | 
						|
func newRPCTransactionFromBlockHash(b *types.Block, hash common.Hash) *RPCTransaction {
 | 
						|
	for idx, tx := range b.Transactions() {
 | 
						|
		if tx.Hash() == hash {
 | 
						|
			return newRPCTransactionFromBlockIndex(b, uint64(idx))
 | 
						|
		}
 | 
						|
	}
 | 
						|
	return nil
 | 
						|
}
 | 
						|
 | 
						|
// RPCMarshalBlock converts the given block to the RPC output which depends on fullTx. If inclTx is true transactions are
 | 
						|
// returned. When fullTx is true the returned block contains full transaction details, otherwise it will only contain
 | 
						|
// transaction hashes.
 | 
						|
func RPCMarshalBlock(b *types.Block, inclTx bool, fullTx bool) (map[string]interface{}, error) {
 | 
						|
	head := b.Header() // copies the header once
 | 
						|
	fields := map[string]interface{}{
 | 
						|
		"number":           (*hexutil.Big)(head.Number),
 | 
						|
		"hash":             b.Hash(),
 | 
						|
		"parentHash":       head.ParentHash,
 | 
						|
		"nonce":            head.Nonce,
 | 
						|
		"mixHash":          head.MixDigest,
 | 
						|
		"sha3Uncles":       head.UncleHash,
 | 
						|
		"logsBloom":        head.Bloom,
 | 
						|
		"stateRoot":        head.Root,
 | 
						|
		"miner":            head.Coinbase,
 | 
						|
		"difficulty":       (*hexutil.Big)(head.Difficulty),
 | 
						|
		"extraData":        hexutil.Bytes(head.Extra),
 | 
						|
		"size":             hexutil.Uint64(b.Size()),
 | 
						|
		"gasLimit":         hexutil.Uint64(head.GasLimit),
 | 
						|
		"gasUsed":          hexutil.Uint64(head.GasUsed),
 | 
						|
		"timestamp":        hexutil.Uint64(head.Time),
 | 
						|
		"transactionsRoot": head.TxHash,
 | 
						|
		"receiptsRoot":     head.ReceiptHash,
 | 
						|
	}
 | 
						|
 | 
						|
	if inclTx {
 | 
						|
		formatTx := func(tx *types.Transaction) (interface{}, error) {
 | 
						|
			return tx.Hash(), nil
 | 
						|
		}
 | 
						|
		if fullTx {
 | 
						|
			formatTx = func(tx *types.Transaction) (interface{}, error) {
 | 
						|
				return newRPCTransactionFromBlockHash(b, tx.Hash()), nil
 | 
						|
			}
 | 
						|
		}
 | 
						|
		txs := b.Transactions()
 | 
						|
		transactions := make([]interface{}, len(txs))
 | 
						|
		var err error
 | 
						|
		for i, tx := range txs {
 | 
						|
			if transactions[i], err = formatTx(tx); err != nil {
 | 
						|
				return nil, err
 | 
						|
			}
 | 
						|
		}
 | 
						|
		fields["transactions"] = transactions
 | 
						|
	}
 | 
						|
 | 
						|
	uncles := b.Uncles()
 | 
						|
	uncleHashes := make([]common.Hash, len(uncles))
 | 
						|
	for i, uncle := range uncles {
 | 
						|
		uncleHashes[i] = uncle.Hash()
 | 
						|
	}
 | 
						|
	fields["uncles"] = uncleHashes
 | 
						|
 | 
						|
	return fields, nil
 | 
						|
}
 |