Skip to content
This repository has been archived by the owner on May 11, 2024. It is now read-only.

Commit

Permalink
feat(prover): wait random durations before submit dummy proofs (#79)
Browse files Browse the repository at this point in the history
  • Loading branch information
davidtaikocha authored Dec 15, 2022
1 parent 96d00fc commit b5e5179
Show file tree
Hide file tree
Showing 8 changed files with 137 additions and 24 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
# taiko-client

[![CI](https://github.com/taikoxyz/taiko-client/actions/workflows/test.yml/badge.svg)](https://github.com/taikoxyz/taiko-client/actions/workflows/test.yml)
[![codecov](https://codecov.io/gh/taikoxyz/taiko-client/branch/main/graph/badge.svg?token=OH6BJMVP6O)](https://codecov.io/gh/taikoxyz/taiko-client)
[![Codecov](https://img.shields.io/codecov/c/github/taikoxyz/taiko-client?logo=codecov&token=OH6BJMVP6O)](https://codecov.io/gh/taikoxyz/taiko-client)

Taiko protocol's client software implementation in Go.

Expand Down
9 changes: 8 additions & 1 deletion cmd/flags/prover.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,16 @@ var (
var (
Dummy = cli.BoolFlag{
Name: "dummy",
Usage: "Produce dummy proofs",
Usage: "Produce dummy proofs, testing purposes only",
Value: false,
Category: proverCategory,
}
RandomDummyProofDelay = cli.StringFlag{
Name: "randomDummyProofDelay",
Usage: "Set the random dummy proof delay between the bounds using the format: " +
"`lowerBound-upperBound` (e.g. `30m-1h`), testing purposes only",
Category: proverCategory,
}
)

// All prover flags.
Expand All @@ -43,4 +49,5 @@ var ProverFlags = MergeFlags(CommonFlags, []cli.Flag{
&ZkEvmRpcdParamsPath,
&L1ProverPrivKey,
&Dummy,
&RandomDummyProofDelay,
})
67 changes: 51 additions & 16 deletions prover/config.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@ package prover
import (
"crypto/ecdsa"
"fmt"
"strings"
"time"

"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/crypto"
Expand All @@ -12,14 +14,16 @@ import (

// Config contains the configurations to initialize a Taiko prover.
type Config struct {
L1Endpoint string
L2Endpoint string
TaikoL1Address common.Address
TaikoL2Address common.Address
L1ProverPrivKey *ecdsa.PrivateKey
ZKEvmRpcdEndpoint string
ZkEvmRpcdParamsPath string
Dummy bool
L1Endpoint string
L2Endpoint string
TaikoL1Address common.Address
TaikoL2Address common.Address
L1ProverPrivKey *ecdsa.PrivateKey
ZKEvmRpcdEndpoint string
ZkEvmRpcdParamsPath string
Dummy bool
RandomDummyProofDelayLowerBound *time.Duration
RandomDummyProofDelayUpperBound *time.Duration
}

// NewConfigFromCliContext creates a new config instance from command line flags.
Expand All @@ -31,14 +35,45 @@ func NewConfigFromCliContext(c *cli.Context) (*Config, error) {
return nil, fmt.Errorf("invalid L1 prover private key: %w", err)
}

var (
randomDummyProofDelayLowerBound *time.Duration
randomDummyProofDelayUpperBound *time.Duration
)
if c.IsSet(flags.RandomDummyProofDelay.Name) {
flagValue := c.String(flags.RandomDummyProofDelay.Name)
splitted := strings.Split(flagValue, "-")
if len(splitted) != 2 {
return nil, fmt.Errorf("invalid random dummy proof delay value: %s", flagValue)
}

lower, err := time.ParseDuration(splitted[0])
if err != nil {
return nil, fmt.Errorf("invalid random dummy proof delay value: %s, err: %w", flagValue, err)
}
upper, err := time.ParseDuration(splitted[1])
if err != nil {
return nil, fmt.Errorf("invalid random dummy proof delay value: %s, err: %w", flagValue, err)
}
if lower > upper {
return nil, fmt.Errorf("invalid random dummy proof delay value (lower > upper): %s", flagValue)
}

if upper != time.Duration(0) {
randomDummyProofDelayLowerBound = &lower
randomDummyProofDelayUpperBound = &upper
}
}

return &Config{
L1Endpoint: c.String(flags.L1WSEndpoint.Name),
L2Endpoint: c.String(flags.L2WSEndpoint.Name),
TaikoL1Address: common.HexToAddress(c.String(flags.TaikoL1Address.Name)),
TaikoL2Address: common.HexToAddress(c.String(flags.TaikoL2Address.Name)),
L1ProverPrivKey: l1ProverPrivKey,
ZKEvmRpcdEndpoint: c.String(flags.ZkEvmRpcdEndpoint.Name),
ZkEvmRpcdParamsPath: c.String(flags.ZkEvmRpcdParamsPath.Name),
Dummy: c.Bool(flags.Dummy.Name),
L1Endpoint: c.String(flags.L1WSEndpoint.Name),
L2Endpoint: c.String(flags.L2WSEndpoint.Name),
TaikoL1Address: common.HexToAddress(c.String(flags.TaikoL1Address.Name)),
TaikoL2Address: common.HexToAddress(c.String(flags.TaikoL2Address.Name)),
L1ProverPrivKey: l1ProverPrivKey,
ZKEvmRpcdEndpoint: c.String(flags.ZkEvmRpcdEndpoint.Name),
ZkEvmRpcdParamsPath: c.String(flags.ZkEvmRpcdParamsPath.Name),
Dummy: c.Bool(flags.Dummy.Name),
RandomDummyProofDelayLowerBound: randomDummyProofDelayLowerBound,
RandomDummyProofDelayUpperBound: randomDummyProofDelayUpperBound,
}, nil
}
5 changes: 5 additions & 0 deletions prover/config_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package prover
import (
"context"
"os"
"time"

"github.com/ethereum/go-ethereum/crypto"
"github.com/taikoxyz/taiko-client/cmd/flags"
Expand All @@ -23,6 +24,7 @@ func (s *ProverTestSuite) TestNewConfigFromCliContext() {
&cli.StringFlag{Name: flags.TaikoL2Address.Name},
&cli.StringFlag{Name: flags.L1ProverPrivKey.Name},
&cli.BoolFlag{Name: flags.Dummy.Name},
&cli.StringFlag{Name: flags.RandomDummyProofDelay.Name},
}
app.Action = func(ctx *cli.Context) error {
c, err := NewConfigFromCliContext(ctx)
Expand All @@ -35,6 +37,8 @@ func (s *ProverTestSuite) TestNewConfigFromCliContext() {
crypto.PubkeyToAddress(s.p.cfg.L1ProverPrivKey.PublicKey),
crypto.PubkeyToAddress(c.L1ProverPrivKey.PublicKey),
)
s.Equal(30*time.Minute, *c.RandomDummyProofDelayLowerBound)
s.Equal(time.Hour, *c.RandomDummyProofDelayUpperBound)
s.True(c.Dummy)
s.Nil(new(Prover).InitFromCli(context.Background(), ctx))

Expand All @@ -49,5 +53,6 @@ func (s *ProverTestSuite) TestNewConfigFromCliContext() {
"-" + flags.TaikoL2Address.Name, taikoL2,
"-" + flags.L1ProverPrivKey.Name, os.Getenv("L1_PROVER_PRIVATE_KEY"),
"-" + flags.Dummy.Name,
"-" + flags.RandomDummyProofDelay.Name, "30m-1h",
}))
}
35 changes: 35 additions & 0 deletions prover/producer/dummpy_producer_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,41 @@ func TestRequestProof(t *testing.T) {
require.NotEmpty(t, res.ZkProof)
}

func TestProofDelay(t *testing.T) {
dummyProofProducer := &DummyProofProducer{}
require.Equal(t, time.Duration(0), dummyProofProducer.proofDelay())

var (
delays []time.Duration
oneSecond = 1 * time.Second
oneDay = 24 * time.Hour
)
for i := 0; i < 1024; i++ {
dummyProofProducer := &DummyProofProducer{
RandomDummyProofDelayLowerBound: &oneSecond,
RandomDummyProofDelayUpperBound: &oneDay,
}

delay := dummyProofProducer.proofDelay()

require.LessOrEqual(t, delay, oneDay)
require.Greater(t, delay, oneSecond)

delays = append(delays, delay)
}

allSame := func(d []time.Duration) bool {
for i := 1; i < len(d); i++ {
if d[i] != d[0] {
return false
}
}
return true
}

require.False(t, allSame(delays))
}

func randHash() common.Hash {
b := make([]byte, 32)
if _, err := rand.Read(b); err != nil {
Expand Down
36 changes: 32 additions & 4 deletions prover/producer/dummy_producer.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,14 +2,19 @@ package producer

import (
"math/big"
"math/rand"
"time"

"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/log"
"github.com/taikoxyz/taiko-client/bindings"
)

// DummyProofProducer always returns a dummy proof.
type DummyProofProducer struct{}
type DummyProofProducer struct {
RandomDummyProofDelayLowerBound *time.Duration
RandomDummyProofDelayUpperBound *time.Duration
}

// RequestProof implements the ProofProducer interface.
func (d *DummyProofProducer) RequestProof(
Expand All @@ -26,8 +31,31 @@ func (d *DummyProofProducer) RequestProof(
"height", header.Number,
"hash", header.Hash(),
)
resultCh <- &ProofWithHeader{
BlockID: blockID, Meta: meta, Header: header, ZkProof: []byte{0xff},
}

time.AfterFunc(d.proofDelay(), func() {
resultCh <- &ProofWithHeader{
BlockID: blockID, Meta: meta, Header: header, ZkProof: []byte{0xff},
}
})

return nil
}

// proofDelay calculates a random proof delay between the bounds.
func (d *DummyProofProducer) proofDelay() time.Duration {
if d.RandomDummyProofDelayLowerBound == nil ||
d.RandomDummyProofDelayUpperBound == nil ||
*d.RandomDummyProofDelayUpperBound == time.Duration(0) {
return time.Duration(0)
}

lowerSeconds := int(d.RandomDummyProofDelayLowerBound.Seconds())
upperSeconds := int(d.RandomDummyProofDelayUpperBound.Seconds())

randomDurationSeconds := rand.Intn((upperSeconds - lowerSeconds)) + lowerSeconds
delay := time.Duration(randomDurationSeconds) * time.Second

log.Info("Random dummy proof delay", "delay", delay)

return delay
}
5 changes: 4 additions & 1 deletion prover/prover.go
Original file line number Diff line number Diff line change
Expand Up @@ -115,7 +115,10 @@ func InitFromConfig(ctx context.Context, p *Prover, cfg *Config) (err error) {
}

if cfg.Dummy {
p.proofProducer = new(producer.DummyProofProducer)
p.proofProducer = &producer.DummyProofProducer{
RandomDummyProofDelayLowerBound: p.cfg.RandomDummyProofDelayLowerBound,
RandomDummyProofDelayUpperBound: p.cfg.RandomDummyProofDelayUpperBound,
}
} else {
if p.proofProducer, err = producer.NewZkevmRpcdProducer(cfg.ZKEvmRpcdEndpoint); err != nil {
return err
Expand Down
2 changes: 1 addition & 1 deletion version/verison.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ package version

// Version info.
var (
Version = "0.1.8"
Version = "0.1.9"
Meta = "dev"
)

Expand Down

0 comments on commit b5e5179

Please sign in to comment.