Skip to content

Commit

Permalink
Problem: gas consumed differs after enabled cache
Browse files Browse the repository at this point in the history
  • Loading branch information
mmsqe committed Jul 15, 2024
1 parent f7d64a2 commit f33944e
Show file tree
Hide file tree
Showing 2 changed files with 48 additions and 5 deletions.
2 changes: 1 addition & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ Ref: https://keepachangelog.com/en/1.0.0/
* [#252](https://github.com/crypto-org-chain/cosmos-sdk/pull/252) Add `BlockGasWanted` to `Context` to support feemarket module.
* [#269](https://github.com/crypto-org-chain/cosmos-sdk/pull/269) Add `StreamingManager` to baseapp to extend the abci listeners.
* (crypto/keyring) [#20212](https://github.com/cosmos/cosmos-sdk/pull/20212) Expose the db keyring used in the keystore.
* (baseapp) [#565](https://github.com/crypto-org-chain/cosmos-sdk/pull/565) Support incarnation cache when executed in block-stm.
* (baseapp) [#565](https://github.com/crypto-org-chain/cosmos-sdk/pull/565) Support incarnation cache when executed in block-stm, [#570](https://github.com/crypto-org-chain/cosmos-sdk/pull/570) Align gas consumed in cache.

### Improvements

Expand Down
51 changes: 47 additions & 4 deletions x/auth/ante/sigverify.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,10 +31,10 @@ var (
key = make([]byte, secp256k1.PubKeySize)
simSecp256k1Pubkey = &secp256k1.PubKey{Key: key}
simSecp256k1Sig [64]byte

SigVerificationResultCacheKey = "ante:SigVerificationResult"
)

const SigVerificationResultCacheKey = "ante:SigVerificationResult"

func init() {
// This decodes a valid hex string into a sepc256k1Pubkey for use in transaction simulation
bz, _ := hex.DecodeString("035AD6810A47F073553FF30D2FCC7E0D3B1C0B74B61A1AAA2582344037151E143A")
Expand Down Expand Up @@ -340,15 +340,58 @@ func (svd SigVerificationDecorator) anteHandle(ctx sdk.Context, tx sdk.Tx, simul
return nil
}

type gasConsumeRecord struct {
Amount storetypes.Gas
Descriptor string
Consume bool
}

type recordingGasMeter struct {
storetypes.GasMeter
GasConsumes []gasConsumeRecord
}

func (m *recordingGasMeter) ConsumeGas(amount storetypes.Gas, descriptor string) {
m.GasMeter.ConsumeGas(amount, descriptor)
m.GasConsumes = append(m.GasConsumes, gasConsumeRecord{amount, descriptor, true})
}

func (m *recordingGasMeter) RefundGas(amount storetypes.Gas, descriptor string) {
m.GasMeter.RefundGas(amount, descriptor)
m.GasConsumes = append(m.GasConsumes, gasConsumeRecord{amount, descriptor, false})
}

type sigVerifyResult struct {
GasRecords []gasConsumeRecord
Error error
}

func (svd SigVerificationDecorator) AnteHandle(ctx sdk.Context, tx sdk.Tx, simulate bool, next sdk.AnteHandler) (newCtx sdk.Context, err error) {
if v, ok := ctx.GetIncarnationCache(SigVerificationResultCacheKey); ok {
// can't convert `nil` to interface
if v != nil {
err = v.(error)
result := v.(*sigVerifyResult)
err = result.Error
for _, record := range result.GasRecords {
if record.Consume {
ctx.GasMeter().ConsumeGas(record.Amount, record.Descriptor)
} else {
ctx.GasMeter().RefundGas(record.Amount, record.Descriptor)
}
}
}
} else {
meter := ctx.GasMeter()
recordingMeter := &recordingGasMeter{
GasMeter: meter,
}
ctx = ctx.WithGasMeter(recordingMeter)
err = svd.anteHandle(ctx, tx, simulate)
ctx.SetIncarnationCache(SigVerificationResultCacheKey, err)
ctx = ctx.WithGasMeter(meter)
ctx.SetIncarnationCache(SigVerificationResultCacheKey, &sigVerifyResult{
GasRecords: recordingMeter.GasConsumes,
Error: err,
})
}
if err != nil {
return ctx, err
Expand Down

0 comments on commit f33944e

Please sign in to comment.