From da85581e125734dfe8345a1be1ae9939d00064a8 Mon Sep 17 00:00:00 2001 From: Ethen Pociask Date: Thu, 18 Jul 2024 19:43:21 -0400 Subject: [PATCH] fix: Remove finalized block client --- .env.example.holesky | 2 +- .env.example.mainnet | 2 +- server/config.go | 10 ++-- server/eigenda_store.go | 5 +- server/load_store.go | 2 +- verify/cert.go | 35 ++++++-------- verify/finalized_block_number_client.go | 63 ------------------------- verify/verifier.go | 6 +-- 8 files changed, 28 insertions(+), 97 deletions(-) delete mode 100644 verify/finalized_block_number_client.go diff --git a/.env.example.holesky b/.env.example.holesky index 210ab4b..e28f407 100644 --- a/.env.example.holesky +++ b/.env.example.holesky @@ -18,7 +18,7 @@ EIGENDA_PROXY_SERVICE_MANAGER_ADDR=0xD4A7E1Bd8015057293f0D0A557088c286942e84b # Directory path to SRS tables # EIGENDA_PROXY_TARGET_CACHE_PATH=resources/SRSTables -# The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy should wait for weak-subjectivity finalization (12-14 minutes). +# The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy shouldn't wait for any confirmations. # EIGENDA_PROXY_ETH_CONFIRMATION_DEPTH=6 # Directory path to g1.point file diff --git a/.env.example.mainnet b/.env.example.mainnet index 53b016c..5e3fc96 100644 --- a/.env.example.mainnet +++ b/.env.example.mainnet @@ -18,7 +18,7 @@ EIGENDA_PROXY_SERVICE_MANAGER_ADDR=0x870679E138bCdf293b7Ff14dD44b70FC97e12fc0 # Directory path to SRS tables # EIGENDA_PROXY_TARGET_CACHE_PATH=resources/SRSTables -# The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy should wait for weak-subjectivity finalization (12-14 minutes). +# The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy shouldn't wait for any confirmations. # EIGENDA_PROXY_ETH_CONFIRMATION_DEPTH=6 # Directory path to g1.point file diff --git a/server/config.go b/server/config.go index 2f1b109..b422a9b 100644 --- a/server/config.go +++ b/server/config.go @@ -53,7 +53,7 @@ type Config struct { // ETH vars EthRPC string SvcManagerAddr string - EthConfirmationDepth uint64 + EthConfirmationDepth int64 // KZG vars CacheDir string @@ -117,7 +117,7 @@ func (c *Config) VerificationCfg() *verify.Config { RPCURL: c.EthRPC, SvcManagerAddr: c.SvcManagerAddr, KzgConfig: kzgCfg, - EthConfirmationDepth: c.EthConfirmationDepth, + EthConfirmationDepth: uint64(c.EthConfirmationDepth), } } @@ -143,11 +143,11 @@ func ReadConfig(ctx *cli.Context) Config { MaxBlobLength: ctx.String(MaxBlobLengthFlagName), SvcManagerAddr: ctx.String(SvcManagerAddrFlagName), EthRPC: ctx.String(EthRPCFlagName), - EthConfirmationDepth: ctx.Uint64(EthConfirmationDepthFlagName), + EthConfirmationDepth: ctx.Int64(EthConfirmationDepthFlagName), MemstoreEnabled: ctx.Bool(MemstoreFlagName), MemstoreBlobExpiration: ctx.Duration(MemstoreExpirationFlagName), } - cfg.ClientConfig.WaitForFinalization = (cfg.EthConfirmationDepth != 0) + cfg.ClientConfig.WaitForFinalization = (cfg.EthConfirmationDepth < 0) return cfg } @@ -252,7 +252,7 @@ func CLIFlags(envPrefix string) []cli.Flag { }, &cli.Uint64Flag{ Name: EthConfirmationDepthFlagName, - Usage: "The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy should wait for weak-subjectivity finalization (12-14 minutes).", + Usage: "The number of Ethereum blocks of confirmation that the DA briging transaction must have before it is assumed by the proxy to be final. The value of `0` indicates that the proxy shouldn't wait for any confirmations.", EnvVars: prefixEnvVars("ETH_CONFIRMATION_DEPTH"), Value: 6, }, diff --git a/server/eigenda_store.go b/server/eigenda_store.go index f4a2a04..47232ef 100644 --- a/server/eigenda_store.go +++ b/server/eigenda_store.go @@ -98,7 +98,7 @@ func (e EigenDAStore) Put(ctx context.Context, value []byte) (comm []byte, err e dispersalDuration := time.Since(dispersalStart) remainingTimeout := e.cfg.StatusQueryTimeout - dispersalDuration - ticker := time.NewTicker(12 * time.Second) + ticker := time.NewTicker(12 * time.Second) // avg. eth block time defer ticker.Stop() ctx, cancel := context.WithTimeout(context.Background(), remainingTimeout) defer cancel() @@ -107,11 +107,12 @@ func (e EigenDAStore) Put(ctx context.Context, value []byte) (comm []byte, err e for !done { select { case <-ctx.Done(): - return nil, ctx.Err() + return nil, fmt.Errorf("timed out when trying to verify the DA certificate for a blob batch after dispersal") case <-ticker.C: err = e.verifier.VerifyCert(cert) if err == nil { done = true + } else if !errors.Is(err, verify.ErrBatchMetadataHashNotFound) { return nil, err } else { diff --git a/server/load_store.go b/server/load_store.go index 327cc3c..7114162 100644 --- a/server/load_store.go +++ b/server/load_store.go @@ -46,7 +46,7 @@ func LoadStore(cfg CLIConfig, ctx context.Context, log log.Logger) (Store, error log, &EigenDAStoreConfig{ MaxBlobSizeBytes: maxBlobLength, - EthConfirmationDepth: cfg.EigenDAConfig.EthConfirmationDepth, + EthConfirmationDepth: uint64(cfg.EigenDAConfig.EthConfirmationDepth), StatusQueryTimeout: cfg.EigenDAConfig.ClientConfig.StatusQueryTimeout, }, ) diff --git a/verify/cert.go b/verify/cert.go index 48d5f2e..a520e19 100644 --- a/verify/cert.go +++ b/verify/cert.go @@ -21,13 +21,15 @@ var ErrBatchMetadataHashNotFound = errors.New("BatchMetadataHash not found for B // CertVerifier verifies the DA certificate against on-chain EigenDA contracts // to ensure disperser returned fields haven't been tampered with type CertVerifier struct { + l log.Logger ethConfirmationDepth uint64 manager *binding.ContractEigenDAServiceManagerCaller - finalizedBlockClient *FinalizedBlockClient ethClient *ethclient.Client } func NewCertVerifier(cfg *Config, l log.Logger) (*CertVerifier, error) { + log.Info("Enabling certificate verification", "confirmation_depth", cfg.EthConfirmationDepth) + client, err := ethclient.Dial(cfg.RPCURL) if err != nil { return nil, fmt.Errorf("failed to dial ETH RPC node: %s", err.Error()) @@ -40,21 +42,20 @@ func NewCertVerifier(cfg *Config, l log.Logger) (*CertVerifier, error) { } return &CertVerifier{ + l: l, manager: m, - finalizedBlockClient: NewFinalizedBlockClient(client.Client()), ethConfirmationDepth: cfg.EthConfirmationDepth, ethClient: client, }, nil } func (cv *CertVerifier) VerifyBatch(header *binding.IEigenDAServiceManagerBatchHeader, - id uint32, recordHash [32]byte, blockNum uint32) error { + id uint32, recordHash [32]byte, confirmationNumber uint32) error { // 0 - Determine block context number blockNumber, err := cv.getContextBlock() if err != nil { return err } - // 1 - Verify batch hash // 1.a - ensure that a batch hash can be looked up for a batch ID @@ -67,7 +68,7 @@ func (cv *CertVerifier) VerifyBatch(header *binding.IEigenDAServiceManagerBatchH } // 1.b - ensure that hash generated from local cert matches one stored on-chain - actualHash, err := HashBatchMetadata(header, recordHash, blockNum) + actualHash, err := HashBatchMetadata(header, recordHash, confirmationNumber) if err != nil { return err @@ -81,7 +82,7 @@ func (cv *CertVerifier) VerifyBatch(header *binding.IEigenDAServiceManagerBatchH return nil } -// VerifyMerkleProof +// VerifyMerkleProof ... Verifies the blob batch inclusion proof against the blob root hash func (cv *CertVerifier) VerifyMerkleProof(inclusionProof []byte, root []byte, blobIndex uint32, blobHeader BlobHeader) error { leafHash, err := HashEncodeBlobHeader(blobHeader) if err != nil { @@ -101,27 +102,19 @@ func (cv *CertVerifier) VerifyMerkleProof(inclusionProof []byte, root []byte, bl return nil } -// 3 - (TODO) verify blob security params -func (cv *CertVerifier) VerifyBlobParams(inclusionProof []byte, rootHash []byte, leafHash []byte, index uint64) error { - return nil -} - func (cv *CertVerifier) getContextBlock() (*big.Int, error) { var blockNumber *big.Int - if cv.ethConfirmationDepth == 0 { - // Get the latest finalized block - blockHeader, err := cv.finalizedBlockClient.GetBlock(context.Background(), "finalized", false) - if err != nil { - return nil, err - } - blockNumber = blockHeader.Number() - } else { blockHeader, err := cv.ethClient.BlockByNumber(context.Background(), nil) if err != nil { return nil, err } - blockNumber = new(big.Int) + + if cv.ethConfirmationDepth == 0 { + return blockHeader.Number(), nil + } + + blockNumber = new(big.Int) blockNumber.Sub(blockHeader.Number(), big.NewInt(int64(cv.ethConfirmationDepth-1))) - } + return blockNumber, nil } diff --git a/verify/finalized_block_number_client.go b/verify/finalized_block_number_client.go deleted file mode 100644 index 79760e1..0000000 --- a/verify/finalized_block_number_client.go +++ /dev/null @@ -1,63 +0,0 @@ -package verify - -import ( - "context" - "encoding/json" - - "github.com/ethereum/go-ethereum" - "github.com/ethereum/go-ethereum/core/types" - "github.com/ethereum/go-ethereum/rpc" -) - -type FinalizedBlockClient struct { - c *rpc.Client -} - -// Dial connects a client to the given URL. -func Dial(rawurl string) (*FinalizedBlockClient, error) { - return DialContext(context.Background(), rawurl) -} - -// DialContext connects a client to the given URL with context. -func DialContext(ctx context.Context, rawurl string) (*FinalizedBlockClient, error) { - c, err := rpc.DialContext(ctx, rawurl) - if err != nil { - return nil, err - } - return NewFinalizedBlockClient(c), nil -} - -// NewFinalizedBlockClient creates a client that uses the given RPC client. -func NewFinalizedBlockClient(c *rpc.Client) *FinalizedBlockClient { - return &FinalizedBlockClient{c} -} - -// Close closes the underlying RPC connection. -func (ec *FinalizedBlockClient) Close() { - ec.c.Close() -} - -// Client gets the underlying RPC client. -func (ec *FinalizedBlockClient) Client() *rpc.Client { - return ec.c -} - -func (c *FinalizedBlockClient) GetBlock(ctx context.Context, method string, args ...interface{}) (*types.Block, error) { - var raw json.RawMessage - err := c.c.CallContext(ctx, &raw, method, args...) - if err != nil { - return nil, err - } - - // Decode header and transactions. - var head *types.Header - if err := json.Unmarshal(raw, &head); err != nil { - return nil, err - } - // When the block is not found, the API returns JSON null. - if head == nil { - return nil, ethereum.NotFound - } - - return types.NewBlockWithHeader(head), nil -} diff --git a/verify/verifier.go b/verify/verifier.go index a4dd28f..d02753f 100644 --- a/verify/verifier.go +++ b/verify/verifier.go @@ -26,7 +26,7 @@ type Config struct { type Verifier struct { verifyCert bool - prover *prover.Prover + kzgProver *prover.Prover cv *CertVerifier } @@ -48,7 +48,7 @@ func NewVerifier(cfg *Config, l log.Logger) (*Verifier, error) { return &Verifier{ verifyCert: cfg.Verify, - prover: prover, + kzgProver: prover, cv: cv, }, nil } @@ -89,7 +89,7 @@ func (v *Verifier) VerifyCert(cert *Certificate) error { func (v *Verifier) Commit(blob []byte) (*bn254.G1Affine, error) { // ChunkLength and TotalChunks aren't relevant for computing data // commitment which is why they're currently set arbitrarily - encoder, err := v.prover.GetKzgEncoder( + encoder, err := v.kzgProver.GetKzgEncoder( encoding.ParamsFromSysPar(420, 69, uint64(len(blob))), ) if err != nil {