Skip to content

Commit

Permalink
disallow blob calldata from being used for batches, factor out isVali…
Browse files Browse the repository at this point in the history
…dBatchTx code
  • Loading branch information
Roberto Bayardo committed Dec 19, 2023
1 parent cd4b94a commit 899346c
Show file tree
Hide file tree
Showing 4 changed files with 29 additions and 36 deletions.
31 changes: 8 additions & 23 deletions op-node/rollup/derive/blob_data_source.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ import (
// BlobDataSource fetches both call-data (backup) and blobs and transforms them into usable rollup data.
type BlobDataSource struct {
open bool
callData []eth.Data
blobDataHashes []eth.IndexedDataHash

blobs []*eth.Blob
Expand Down Expand Up @@ -52,19 +51,14 @@ func (ds *BlobDataSource) Next(ctx context.Context) (eth.Data, error) {
if !ds.open {
if _, txs, err := ds.fetcher.InfoAndTxsByHash(ctx, ds.ref.Hash); err == nil {
ds.open = true
ds.callData, ds.blobDataHashes = BlobDataFromEVMTransactions(ds.dsCfg, ds.batcherAddr, txs, ds.log)
ds.blobDataHashes = BlobDataFromEVMTransactions(ds.dsCfg, ds.batcherAddr, txs, ds.log)
} else if errors.Is(err, ethereum.NotFound) {
return nil, NewResetError(fmt.Errorf("failed to open blob-data source: %w", err))
} else {
return nil, NewTemporaryError(fmt.Errorf("failed to open blob-data source: %w", err))
}
}
// prioritize call-data
if len(ds.callData) != 0 {
data := ds.callData[0]
ds.callData = ds.callData[1:]
return data, nil
}
if len(ds.blobDataHashes) > 0 { // check if there is any blob data in this block we have opened.
if ds.blobs == nil { // fetch blobs if we haven't already
blobs, err := ds.blobsFetcher.BlobsByRefAndIndexedDataHashes(ctx, ds.ref, ds.blobDataHashes)
Expand Down Expand Up @@ -93,26 +87,17 @@ func (ds *BlobDataSource) Next(ctx context.Context) (eth.Data, error) {
// from transactions that are sent to the batch inbox address from the batch sender address.
// This will return an empty array if no valid transactions are found.
// Call-data can be used as fallback in case blobs are overpriced or unstable.
func BlobDataFromEVMTransactions(dsCfg DataSourceConfig, batcherAddr common.Address, txs types.Transactions, log log.Logger) ([]eth.Data, []eth.IndexedDataHash) {
var callData []eth.Data
func BlobDataFromEVMTransactions(dsCfg DataSourceConfig, batcherAddr common.Address, txs types.Transactions, log log.Logger) []eth.IndexedDataHash {
var indexedDataHashes []eth.IndexedDataHash
blobIndex := uint64(0)
for j, tx := range txs {
for _, tx := range txs {
if to := tx.To(); to != nil && *to == dsCfg.batchInboxAddress {
seqDataSubmitter, err := dsCfg.l1Signer.Sender(tx) // optimization: only derive sender if To is correct
if err != nil {
log.Warn("tx in inbox with invalid signature", "index", j, "err", err)
blobIndex += uint64(len(tx.BlobHashes()))
continue // bad signature, ignore
}
// some random L1 user might have sent a transaction to our batch inbox, ignore them
if seqDataSubmitter != batcherAddr {
log.Warn("tx in inbox with unauthorized submitter", "index", j, "err", err)
if !isValidBatchTx(tx, dsCfg.l1Signer, batcherAddr) {
blobIndex += uint64(len(tx.BlobHashes()))
continue // not an authorized batch submitter, ignore
continue
}
if len(tx.Data()) > 0 { // ignore empty calldata
callData = append(callData, tx.Data())
if len(tx.Data()) > 0 { // ignore calldata since
log.Warn("blob tx has calldata, which will be ignored")
}
for _, h := range tx.BlobHashes() {
indexedDataHashes = append(indexedDataHashes, eth.IndexedDataHash{
Expand All @@ -125,5 +110,5 @@ func BlobDataFromEVMTransactions(dsCfg DataSourceConfig, batcherAddr common.Addr
blobIndex += uint64(len(tx.BlobHashes()))
}
}
return callData, indexedDataHashes
return indexedDataHashes
}
13 changes: 3 additions & 10 deletions op-node/rollup/derive/call_data_source.go
Original file line number Diff line number Diff line change
Expand Up @@ -67,17 +67,10 @@ func (ds *CallDataSource) Next(ctx context.Context) (eth.Data, error) {
// This will return an empty array if no valid transactions are found.
func CallDataFromEVMTransactions(dsCfg DataSourceConfig, batcherAddr common.Address, txs types.Transactions, log log.Logger) []eth.Data {
var out []eth.Data
for j, tx := range txs {
for _, tx := range txs {
if to := tx.To(); to != nil && *to == dsCfg.batchInboxAddress {
seqDataSubmitter, err := dsCfg.l1Signer.Sender(tx) // optimization: only derive sender if To is correct
if err != nil {
log.Warn("tx in inbox with invalid signature", "index", j, "txHash", tx.Hash(), "err", err)
continue // bad signature, ignore
}
// some random L1 user might have sent a transaction to our batch inbox, ignore them
if seqDataSubmitter != batcherAddr {
log.Warn("tx in inbox with unauthorized submitter", "index", j, "txHash", tx.Hash(), "err", err)
continue // not an authorized batch submitter, ignore
if !isValidBatchTx(tx, dsCfg.l1Signer, batcherAddr) {
continue
}
out = append(out, tx.Data())
}
Expand Down
14 changes: 14 additions & 0 deletions op-node/rollup/derive/data_source.go
Original file line number Diff line number Diff line change
Expand Up @@ -57,3 +57,17 @@ type DataSourceConfig struct {
batchInboxAddress common.Address
blobsEnabledL1Timestamp *uint64
}

func isValidBatchTx(tx *types.Transaction, l1Signer types.Signer, batcherAddr common.Address) bool {
seqDataSubmitter, err := l1Signer.Sender(tx) // optimization: only derive sender if To is correct
if err != nil {
log.Warn("tx in inbox with invalid signature", "hash", tx.Hash(), "err", err)
return false
}
// some random L1 user might have sent a transaction to our batch inbox, ignore them
if seqDataSubmitter != batcherAddr {
log.Warn("tx in inbox with unauthorized submitter", "hash", tx.Hash(), "err", err)
return false
}
return true
}
7 changes: 4 additions & 3 deletions op-service/txmgr/txmgr.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,12 +31,13 @@ const (
blobPriceBump int64 = 100
)

// new = old * (100 + priceBump) / 100
var (
// new = old * (100 + [blob]priceBump) / 100
priceBumpPercent = big.NewInt(100 + priceBump)
oneHundred = big.NewInt(100)
blobPriceBumpPercent = big.NewInt(100 + blobPriceBump)
two = big.NewInt(2)

oneHundred = big.NewInt(100)
two = big.NewInt(2)
)

// TxManager is an interface that allows callers to reliably publish txs,
Expand Down

0 comments on commit 899346c

Please sign in to comment.