Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[EVM] Allow multiple txs from same account in a block #397

Merged
merged 3 commits into from
Jan 19, 2024
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
21 changes: 13 additions & 8 deletions baseapp/abci.go
Original file line number Diff line number Diff line change
Expand Up @@ -226,22 +226,27 @@ func (app *BaseApp) CheckTx(ctx context.Context, req *abci.RequestCheckTx) (*abc
res := sdkerrors.ResponseCheckTx(err, 0, 0, app.trace)
return &abci.ResponseCheckTxV2{ResponseCheckTx: &res}, err
}
gInfo, result, _, priority, pendingTxChecker, expireTxHandler, err := app.runTx(sdkCtx, mode, tx, sha256.Sum256(req.Tx))
gInfo, result, _, priority, pendingTxChecker, expireTxHandler, txCtx, err := app.runTx(sdkCtx, mode, tx, sha256.Sum256(req.Tx))
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nit: maybe we can group some of those mempool-specific return values into a struct for readability sake

if err != nil {
res := sdkerrors.ResponseCheckTx(err, gInfo.GasWanted, gInfo.GasUsed, app.trace)
return &abci.ResponseCheckTxV2{ResponseCheckTx: &res}, err
}

res := &abci.ResponseCheckTxV2{ResponseCheckTx: &abci.ResponseCheckTx{
GasWanted: int64(gInfo.GasWanted), // TODO: Should type accept unsigned ints?
Data: result.Data,
Priority: priority,
}}
res := &abci.ResponseCheckTxV2{
ResponseCheckTx: &abci.ResponseCheckTx{
GasWanted: int64(gInfo.GasWanted), // TODO: Should type accept unsigned ints?
Data: result.Data,
Priority: priority,
},
ExpireTxHandler: expireTxHandler,
EVMNonce: txCtx.EVMNonce(),
EVMSenderAddress: txCtx.EVMSenderAddress(),
IsEVM: txCtx.IsEVM(),
}
if pendingTxChecker != nil {
res.IsPendingTransaction = true
res.Checker = pendingTxChecker
}
res.ExpireTxHandler = expireTxHandler

return res, nil
}
Expand Down Expand Up @@ -271,7 +276,7 @@ func (app *BaseApp) DeliverTx(ctx sdk.Context, req abci.RequestDeliverTx, tx sdk
telemetry.SetGauge(float32(gInfo.GasWanted), "tx", "gas", "wanted")
}()

gInfo, result, anteEvents, _, _, _, err := app.runTx(ctx.WithTxBytes(req.Tx).WithVoteInfos(app.voteInfos), runTxModeDeliver, tx, checksum)
gInfo, result, anteEvents, _, _, _, _, err := app.runTx(ctx.WithTxBytes(req.Tx).WithVoteInfos(app.voteInfos), runTxModeDeliver, tx, checksum)
if err != nil {
resultStr = "failed"
// if we have a result, use those events instead of just the anteEvents
Expand Down
13 changes: 7 additions & 6 deletions baseapp/baseapp.go
Original file line number Diff line number Diff line change
Expand Up @@ -829,6 +829,7 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [
priority int64,
pendingTxChecker abci.PendingTxChecker,
expireHandler abci.ExpireTxHandler,
txCtx sdk.Context,
err error,
) {
defer telemetry.MeasureThroughputSinceWithLabels(
Expand Down Expand Up @@ -864,7 +865,7 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [

// only run the tx if there is block gas remaining
if mode == runTxModeDeliver && ctx.BlockGasMeter().IsOutOfGas() {
return gInfo, nil, nil, -1, nil, nil, sdkerrors.Wrap(sdkerrors.ErrOutOfGas, "no block gas left to run tx")
return gInfo, nil, nil, -1, nil, nil, ctx, sdkerrors.Wrap(sdkerrors.ErrOutOfGas, "no block gas left to run tx")
}

defer func() {
Expand Down Expand Up @@ -901,13 +902,13 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [
}

if tx == nil {
return sdk.GasInfo{}, nil, nil, 0, nil, nil, sdkerrors.Wrap(sdkerrors.ErrTxDecode, "tx decode error")
return sdk.GasInfo{}, nil, nil, 0, nil, nil, ctx, sdkerrors.Wrap(sdkerrors.ErrTxDecode, "tx decode error")
}

msgs := tx.GetMsgs()

if err := validateBasicTxMsgs(msgs); err != nil {
return sdk.GasInfo{}, nil, nil, 0, nil, nil, err
return sdk.GasInfo{}, nil, nil, 0, nil, nil, ctx, err
}

if app.anteHandler != nil {
Expand Down Expand Up @@ -949,7 +950,7 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [
// GasMeter expected to be set in AnteHandler
gasWanted = ctx.GasMeter().Limit()
if err != nil {
return gInfo, nil, nil, 0, nil, nil, err
return gInfo, nil, nil, 0, nil, nil, ctx, err
}

// Dont need to validate in checkTx mode
Expand All @@ -964,7 +965,7 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [
op.EmitValidationFailMetrics()
}
errMessage := fmt.Sprintf("Invalid Concurrent Execution antehandler missing %d access operations", len(missingAccessOps))
return gInfo, nil, nil, 0, nil, nil, sdkerrors.Wrap(sdkerrors.ErrInvalidConcurrencyExecution, errMessage)
return gInfo, nil, nil, 0, nil, nil, ctx, sdkerrors.Wrap(sdkerrors.ErrInvalidConcurrencyExecution, errMessage)
}
}

Expand Down Expand Up @@ -1000,7 +1001,7 @@ func (app *BaseApp) runTx(ctx sdk.Context, mode runTxMode, tx sdk.Tx, checksum [
if ctx.CheckTxCallback() != nil {
ctx.CheckTxCallback()(err)
}
return gInfo, result, anteEvents, priority, pendingTxChecker, expireHandler, err
return gInfo, result, anteEvents, priority, pendingTxChecker, expireHandler, ctx, err
}

// runMsgs iterates through a list of messages and executes them with the provided
Expand Down
6 changes: 3 additions & 3 deletions baseapp/test_helpers.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ func (app *BaseApp) Check(txEncoder sdk.TxEncoder, tx sdk.Tx) (sdk.GasInfo, *sdk
return sdk.GasInfo{}, nil, sdkerrors.Wrapf(sdkerrors.ErrInvalidRequest, "%s", err)
}
ctx := app.checkState.ctx.WithTxBytes(bz).WithVoteInfos(app.voteInfos).WithConsensusParams(app.GetConsensusParams(app.checkState.ctx))
gasInfo, result, _, _, _, _, err := app.runTx(ctx, runTxModeCheck, tx, sha256.Sum256(bz))
gasInfo, result, _, _, _, _, _, err := app.runTx(ctx, runTxModeCheck, tx, sha256.Sum256(bz))
if len(ctx.MultiStore().GetEvents()) > 0 {
panic("Expected checkTx events to be empty")
}
Expand All @@ -31,7 +31,7 @@ func (app *BaseApp) Simulate(txBytes []byte) (sdk.GasInfo, *sdk.Result, error) {
if err != nil {
return sdk.GasInfo{}, nil, err
}
gasInfo, result, _, _, _, _, err := app.runTx(ctx, runTxModeSimulate, tx, sha256.Sum256(txBytes))
gasInfo, result, _, _, _, _, _, err := app.runTx(ctx, runTxModeSimulate, tx, sha256.Sum256(txBytes))
if len(ctx.MultiStore().GetEvents()) > 0 {
panic("Expected simulate events to be empty")
}
Expand All @@ -49,7 +49,7 @@ func (app *BaseApp) Deliver(txEncoder sdk.TxEncoder, tx sdk.Tx) (sdk.GasInfo, *s
if err != nil {
return sdk.GasInfo{}, &sdk.Result{}, err
}
gasInfo, result, _, _, _, _, err := app.runTx(ctx, runTxModeDeliver, decoded, sha256.Sum256(bz))
gasInfo, result, _, _, _, _, _, err := app.runTx(ctx, runTxModeDeliver, decoded, sha256.Sum256(bz))
return gasInfo, result, err
}

Expand Down
2 changes: 1 addition & 1 deletion go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -183,7 +183,7 @@ replace (
github.com/sei-protocol/sei-db => github.com/sei-protocol/sei-db v0.0.25
// Latest goleveldb is broken, we have to stick to this version
github.com/syndtr/goleveldb => github.com/syndtr/goleveldb v1.0.1-0.20210819022825-2ae1ddf74ef7
github.com/tendermint/tendermint => github.com/sei-protocol/sei-tendermint v0.2.36-evm-rebase
github.com/tendermint/tendermint => github.com/sei-protocol/sei-tendermint v0.2.37-0.20240118140937-5cb45fdc5262
// latest grpc doesn't work with with our modified proto compiler, so we need to enforce
// the following version across all dependencies.
google.golang.org/grpc => google.golang.org/grpc v1.33.2
Expand Down
4 changes: 2 additions & 2 deletions go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -785,8 +785,8 @@ github.com/sei-protocol/sei-db v0.0.25 h1:jC1ivcaNxSR7EmxqvxexqPpnN/G0vUTZNHZI+C
github.com/sei-protocol/sei-db v0.0.25/go.mod h1:F/ZKZA8HJPcUzSZPA8yt6pfwlGriJ4RDR4eHKSGLStI=
github.com/sei-protocol/sei-iavl v0.1.9 h1:y4mVYftxLNRs6533zl7N0/Ch+CzRQc04JDfHolIxgBE=
github.com/sei-protocol/sei-iavl v0.1.9/go.mod h1:7PfkEVT5dcoQE+s/9KWdoXJ8VVVP1QpYYPLdxlkSXFk=
github.com/sei-protocol/sei-tendermint v0.2.36-evm-rebase h1:qUD1G5IqlssdobYMN9GPJnQgKvF2tcUFAMKybkRcFAI=
github.com/sei-protocol/sei-tendermint v0.2.36-evm-rebase/go.mod h1:4LSlJdhl3nf3OmohliwRNUFLOB1XWlrmSodrIP7fLh4=
github.com/sei-protocol/sei-tendermint v0.2.37-0.20240118140937-5cb45fdc5262 h1:B+zQYDr1q1u7Sb3LBDZikJzwgHVn6yiGBJljcsDzQN4=
github.com/sei-protocol/sei-tendermint v0.2.37-0.20240118140937-5cb45fdc5262/go.mod h1:4LSlJdhl3nf3OmohliwRNUFLOB1XWlrmSodrIP7fLh4=
github.com/sei-protocol/sei-tm-db v0.0.5 h1:3WONKdSXEqdZZeLuWYfK5hP37TJpfaUa13vAyAlvaQY=
github.com/sei-protocol/sei-tm-db v0.0.5/go.mod h1:Cpa6rGyczgthq7/0pI31jys2Fw0Nfrc+/jKdP1prVqY=
github.com/sergi/go-diff v1.1.0/go.mod h1:STckp+ISIX8hZLjrqAeVduY0gWCT9IjLuqbuNXdaHfM=
Expand Down
63 changes: 48 additions & 15 deletions types/context.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,21 +24,22 @@ but please do not over-use it. We try to keep all data structured
and standard additions here would be better just to add to the Context struct
*/
type Context struct {
ctx context.Context
ms MultiStore
header tmproto.Header
headerHash tmbytes.HexBytes
chainID string
txBytes []byte
logger log.Logger
voteInfo []abci.VoteInfo
gasMeter GasMeter
blockGasMeter GasMeter
checkTx bool
recheckTx bool // if recheckTx == true, then checkTx must also be true
minGasPrice DecCoins
consParams *tmproto.ConsensusParams
eventManager *EventManager
ctx context.Context
ms MultiStore
header tmproto.Header
headerHash tmbytes.HexBytes
chainID string
txBytes []byte
logger log.Logger
voteInfo []abci.VoteInfo
gasMeter GasMeter
blockGasMeter GasMeter
checkTx bool
recheckTx bool // if recheckTx == true, then checkTx must also be true
minGasPrice DecCoins
consParams *tmproto.ConsensusParams
eventManager *EventManager

priority int64 // The tx priority, only relevant in CheckTx
pendingTxChecker abci.PendingTxChecker // Checker for pending transaction, only relevant in CheckTx
checkTxCallback func(error) // callback to make at the end of CheckTx. Input param is the error (nil-able) of `runMsgs`
Expand All @@ -48,6 +49,11 @@ type Context struct {
txCompletionChannels acltypes.MessageAccessOpsChannelMapping
txMsgAccessOps map[int][]acltypes.AccessOperation

// EVM properties
evm bool // EVM transaction flag
evmNonce uint64 // EVM Transaction nonce
evmSenderAddress string // EVM Sender address

msgValidator *acltypes.MsgValidator
messageIndex int // Used to track current message being processed
txIndex int
Expand Down Expand Up @@ -123,6 +129,18 @@ func (c Context) ExpireTxHandler() abci.ExpireTxHandler {
return c.expireTxHandler
}

func (c Context) EVMSenderAddress() string {
return c.evmSenderAddress
}

func (c Context) EVMNonce() uint64 {
return c.evmNonce
}

func (c Context) IsEVM() bool {
return c.evm
}

func (c Context) PendingTxChecker() abci.PendingTxChecker {
return c.pendingTxChecker
}
Expand Down Expand Up @@ -364,6 +382,21 @@ func (c Context) WithTraceSpanContext(ctx context.Context) Context {
return c
}

func (c Context) WithEVMSenderAddress(address string) Context {
c.evmSenderAddress = address
return c
}

func (c Context) WithEVMNonce(nonce uint64) Context {
c.evmNonce = nonce
return c
}

func (c Context) WithIsEVM(isEVM bool) Context {
c.evm = isEVM
return c
}

func (c Context) WithPendingTxChecker(checker abci.PendingTxChecker) Context {
c.pendingTxChecker = checker
return c
Expand Down
Loading