mirror of https://github.com/poanetwork/gecko.git
343 lines
7.6 KiB
Go
343 lines
7.6 KiB
Go
package spchainvm
|
|
|
|
import (
|
|
"testing"
|
|
|
|
"github.com/ava-labs/gecko/database/memdb"
|
|
"github.com/ava-labs/gecko/ids"
|
|
"github.com/ava-labs/gecko/snow"
|
|
"github.com/ava-labs/gecko/snow/consensus/snowman"
|
|
"github.com/ava-labs/gecko/snow/engine/common"
|
|
)
|
|
|
|
func genGenesisState(numBlocks, numTxsPerBlock int, b *testing.B) ([]byte, []*Block) {
|
|
ctx := snow.DefaultContextTest()
|
|
builder := Builder{
|
|
NetworkID: ctx.NetworkID,
|
|
ChainID: ctx.ChainID,
|
|
}
|
|
|
|
genesisBlock, err := builder.NewBlock(ids.Empty, nil)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
|
|
blocks := genBlocks(
|
|
/*numBlocks=*/ numBlocks,
|
|
/*numTxsPerBlock=*/ numTxsPerBlock,
|
|
/*initialParent=*/ genesisBlock.ID(),
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
genesisAccounts := []Account{}
|
|
for _, block := range blocks {
|
|
for _, tx := range block.txs {
|
|
genesisAccounts = append(
|
|
genesisAccounts,
|
|
Account{
|
|
id: tx.Key(ctx).Address(),
|
|
nonce: tx.nonce - 1,
|
|
balance: tx.amount,
|
|
},
|
|
)
|
|
}
|
|
}
|
|
|
|
codec := Codec{}
|
|
genesisData, err := codec.MarshalGenesis(genesisAccounts)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
|
|
return genesisData, blocks
|
|
}
|
|
|
|
func genGenesisStateBytes(numBlocks, numTxsPerBlock int, b *testing.B) ([]byte, [][]byte) {
|
|
genesisData, blocks := genGenesisState(numBlocks, numTxsPerBlock, b)
|
|
blockBytes := make([][]byte, numBlocks)
|
|
for i, block := range blocks {
|
|
blockBytes[i] = block.Bytes()
|
|
}
|
|
return genesisData, blockBytes
|
|
}
|
|
|
|
// BenchmarkParseBlock runs the benchmark of parsing blocks
|
|
func BenchmarkParseBlock(b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
ctx := snow.DefaultContextTest()
|
|
genesisBytes, blocks := genGenesisStateBytes(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ ctx,
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
for n := 0; n < b.N; n++ {
|
|
for _, blockBytes := range blocks {
|
|
vm.state.block.Flush()
|
|
|
|
b.StartTimer()
|
|
if _, err := vm.ParseBlock(blockBytes); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
}
|
|
|
|
// BenchmarkParseAndVerify runs the benchmark of parsing blocks and verifying them
|
|
func BenchmarkParseAndVerify(b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
genesisBytes, blocks := genGenesisStateBytes(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
for n := 0; n < b.N; n++ {
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ snow.DefaultContextTest(),
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
|
|
b.StartTimer()
|
|
for _, blockBytes := range blocks {
|
|
blk, err := vm.ParseBlock(blockBytes)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
if err := blk.Verify(); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
}
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
|
|
// BenchmarkAccept runs the benchmark of accepting blocks
|
|
func BenchmarkAccept(b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
genesisBytes, blocks := genGenesisStateBytes(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
for n := 0; n < b.N; n++ {
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ snow.DefaultContextTest(),
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
|
|
for _, blockBytes := range blocks {
|
|
blk, err := vm.ParseBlock(blockBytes)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
if err := blk.Verify(); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
|
|
b.StartTimer()
|
|
blk.Accept()
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
}
|
|
|
|
// ParseAndVerifyAndAccept runs the benchmark of parsing, verifying, and accepting blocks
|
|
func ParseAndVerifyAndAccept(numBlocks, numTxsPerBlock int, b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
genesisBytes, blocks := genGenesisStateBytes(
|
|
/*numBlocks=*/ numBlocks,
|
|
/*numTxsPerBlock=*/ numTxsPerBlock,
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
for n := 0; n < b.N; n++ {
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ snow.DefaultContextTest(),
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
|
|
b.StartTimer()
|
|
for _, blockBytes := range blocks {
|
|
blk, err := vm.ParseBlock(blockBytes)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
if err := blk.Verify(); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
blk.Accept()
|
|
}
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
|
|
// BenchmarkParseAndVerifyAndAccept1 runs the benchmark of parsing, verifying, and accepting 1 block
|
|
func BenchmarkParseAndVerifyAndAccept1(b *testing.B) {
|
|
ParseAndVerifyAndAccept(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|
|
|
|
// BenchmarkParseAndVerifyAndAccept10 runs the benchmark of parsing, verifying, and accepting 10 blocks
|
|
func BenchmarkParseAndVerifyAndAccept10(b *testing.B) {
|
|
ParseAndVerifyAndAccept(
|
|
/*numBlocks=*/ 10,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|
|
|
|
// ParseThenVerifyThenAccept runs the benchmark of parsing then verifying and then accepting blocks
|
|
func ParseThenVerifyThenAccept(numBlocks, numTxsPerBlock int, b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
genesisBytes, blocks := genGenesisStateBytes(
|
|
/*numBlocks=*/ numBlocks,
|
|
/*numTxsPerBlock=*/ numTxsPerBlock,
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
for n := 0; n < b.N; n++ {
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ snow.DefaultContextTest(),
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
|
|
b.StartTimer()
|
|
parsedBlocks := make([]snowman.Block, len(blocks))
|
|
for i, blockBytes := range blocks {
|
|
blk, err := vm.ParseBlock(blockBytes)
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
parsedBlocks[i] = blk
|
|
}
|
|
for _, blk := range parsedBlocks {
|
|
if err := blk.Verify(); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
}
|
|
for _, blk := range parsedBlocks {
|
|
blk.Accept()
|
|
}
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
|
|
// BenchmarkParseThenVerifyThenAccept1 runs the benchmark of parsing then verifying and then accepting 1 block
|
|
func BenchmarkParseThenVerifyThenAccept1(b *testing.B) {
|
|
ParseThenVerifyThenAccept(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|
|
|
|
// BenchmarkParseThenVerifyThenAccept10 runs the benchmark of parsing then verifying and then accepting 10 blocks
|
|
func BenchmarkParseThenVerifyThenAccept10(b *testing.B) {
|
|
ParseThenVerifyThenAccept(
|
|
/*numBlocks=*/ 10,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|
|
|
|
// IssueAndVerifyAndAccept runs the benchmark of issuing, verifying, and accepting blocks
|
|
func IssueAndVerifyAndAccept(numBlocks, numTxsPerBlock int, b *testing.B) {
|
|
b.StopTimer()
|
|
b.ResetTimer()
|
|
|
|
genesisBytes, blocks := genGenesisState(
|
|
/*numBlocks=*/ numBlocks,
|
|
/*numTxsPerBlock=*/ numTxsPerBlock,
|
|
/*testing=*/ b,
|
|
)
|
|
|
|
for n := 0; n < b.N; n++ {
|
|
vm := &VM{}
|
|
vm.Initialize(
|
|
/*ctx=*/ snow.DefaultContextTest(),
|
|
/*db=*/ memdb.New(),
|
|
/*genesis=*/ genesisBytes,
|
|
/*engineChan=*/ make(chan common.Message, 1),
|
|
/*fxs=*/ nil,
|
|
)
|
|
vm.SetPreference(vm.LastAccepted())
|
|
|
|
b.StartTimer()
|
|
for _, block := range blocks {
|
|
for _, tx := range block.txs {
|
|
if _, err := vm.IssueTx(tx.Bytes(), nil); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
}
|
|
|
|
blk, err := vm.BuildBlock()
|
|
if err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
if err := blk.Verify(); err != nil {
|
|
b.Fatal(err)
|
|
}
|
|
vm.SetPreference(blk.ID())
|
|
blk.Accept()
|
|
}
|
|
b.StopTimer()
|
|
}
|
|
}
|
|
|
|
// BenchmarkIssueAndVerifyAndAccept1 runs the benchmark of issuing, verifying, and accepting 1 block
|
|
func BenchmarkIssueAndVerifyAndAccept1(b *testing.B) {
|
|
IssueAndVerifyAndAccept(
|
|
/*numBlocks=*/ 1,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|
|
|
|
// BenchmarkIssueAndVerifyAndAccept10 runs the benchmark of issuing, verifying, and accepting 10 blocks
|
|
func BenchmarkIssueAndVerifyAndAccept10(b *testing.B) {
|
|
IssueAndVerifyAndAccept(
|
|
/*numBlocks=*/ 10,
|
|
/*numTxsPerBlock=*/ 1,
|
|
/*testing=*/ b,
|
|
)
|
|
}
|