Skip to content

Commit

Permalink
[Github] Max fee per gas issue (#1892)
Browse files Browse the repository at this point in the history
  • Loading branch information
begmaroman authored Sep 8, 2023
1 parent 7a04a89 commit 400f388
Show file tree
Hide file tree
Showing 5 changed files with 53 additions and 17 deletions.
8 changes: 1 addition & 7 deletions docker/local/polygon-edge.sh
Original file line number Diff line number Diff line change
Expand Up @@ -2,13 +2,6 @@

set -e

# Check if jq is installed. If not exit and inform user.
if ! command -v jq >/dev/null 2>&1; then
echo "The jq utility is not installed or is not in the PATH. Please install it and run the script again."
exit 1
fi


POLYGON_EDGE_BIN=./polygon-edge
CHAIN_CUSTOM_OPTIONS=$(tr "\n" " " << EOL
--block-gas-limit 10000000
Expand Down Expand Up @@ -61,6 +54,7 @@ case "$1" in
--validators-prefix data- \
--reward-wallet 0xDEADBEEF:1000000 \
--native-token-config "Polygon:MATIC:18:true:$(echo "$secrets" | jq -r '.[0] | .address')" \
--governor-admin "$(echo "$secrets" | jq -r '.[0] | .address')" \
--bootnode "/dns4/node-1/tcp/1478/p2p/$(echo "$secrets" | jq -r '.[0] | .node_id')" \
--bootnode "/dns4/node-2/tcp/1478/p2p/$(echo "$secrets" | jq -r '.[1] | .node_id')" \
--bootnode "/dns4/node-3/tcp/1478/p2p/$(echo "$secrets" | jq -r '.[2] | .node_id')" \
Expand Down
53 changes: 47 additions & 6 deletions jsonrpc/eth_endpoint.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ type ethTxPoolStore interface {
// GetNonce returns the next nonce for this address
GetNonce(addr types.Address) uint64

// returns the current base fee of TxPool
// GetBaseFee returns the current base fee of TxPool
GetBaseFee() uint64
}

Expand Down Expand Up @@ -393,23 +393,53 @@ func (e *Eth) GetStorageAt(
return argBytesPtr(result), nil
}

// GasPrice returns the average gas price based on the last x blocks
// taking into consideration operator defined price limit
// GasPrice exposes "getGasPrice"'s function logic to public RPC interface
func (e *Eth) GasPrice() (interface{}, error) {
gasPrice, err := e.getGasPrice()
if err != nil {
return nil, err
}

return argUint64(gasPrice), nil
}

// getGasPrice returns the average gas price based on the last x blocks
// taking into consideration operator defined price limit
func (e *Eth) getGasPrice() (uint64, error) {
// Return --price-limit flag defined value if it is greater than avgGasPrice/baseFee+priorityFee
if e.store.GetForksInTime(e.store.Header().Number).London {
priorityFee, err := e.store.MaxPriorityFeePerGas()
if err != nil {
return nil, err
return 0, err
}

return argUint64(common.Max(e.priceLimit, priorityFee.Uint64()+e.store.GetBaseFee())), nil
return common.Max(e.priceLimit, priorityFee.Uint64()+e.store.GetBaseFee()), nil
}

// Fetch average gas price in uint64
avgGasPrice := e.store.GetAvgGasPrice().Uint64()

return argUint64(common.Max(e.priceLimit, avgGasPrice)), nil
return common.Max(e.priceLimit, avgGasPrice), nil
}

// fillTransactionGasPrice fills transaction gas price if no provided
func (e *Eth) fillTransactionGasPrice(tx *types.Transaction) error {
if tx.GetGasPrice(e.store.GetBaseFee()).BitLen() > 0 {
return nil
}

estimatedGasPrice, err := e.getGasPrice()
if err != nil {
return err
}

if tx.Type == types.DynamicFeeTx {
tx.GasFeeCap = new(big.Int).SetUint64(estimatedGasPrice)
} else {
tx.GasPrice = new(big.Int).SetUint64(estimatedGasPrice)
}

return nil
}

type overrideAccount struct {
Expand Down Expand Up @@ -460,11 +490,17 @@ func (e *Eth) Call(arg *txnArgs, filter BlockNumberOrHash, apiOverride *stateOve
if err != nil {
return nil, err
}

// If the caller didn't supply the gas limit in the message, then we set it to maximum possible => block gas limit
if transaction.Gas == 0 {
transaction.Gas = header.GasLimit
}

// Force transaction gas price if empty
if err = e.fillTransactionGasPrice(transaction); err != nil {
return nil, err
}

var override types.StateOverride
if apiOverride != nil {
override = types.StateOverride{}
Expand Down Expand Up @@ -510,6 +546,11 @@ func (e *Eth) EstimateGas(arg *txnArgs, rawNum *BlockNumber) (interface{}, error
return nil, err
}

// Force transaction gas price if empty
if err = e.fillTransactionGasPrice(transaction); err != nil {
return nil, err
}

forksInTime := e.store.GetForksInTime(header.Number)

var standardGas uint64
Expand Down
1 change: 1 addition & 0 deletions jsonrpc/eth_state_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -589,6 +589,7 @@ func constructMockTx(gasLimit *argUint64, data *argBytes) *txnArgs {

func getExampleStore() *mockSpecialStore {
return &mockSpecialStore{
ethStore: newMockBlockStore(),
account: &mockAccount{
address: addr0,
account: &Account{
Expand Down
2 changes: 1 addition & 1 deletion state/executor_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ func Test_Transition_checkDynamicFees(t *testing.T) {
},
wantErr: func(t assert.TestingT, err error, i ...interface{}) bool {
expectedError := fmt.Sprintf("max fee per gas less than block base fee: "+
"address %s, GasFeeCap: 10, BaseFee: 20", types.ZeroAddress)
"address %s, GasFeeCap/GasPrice: 10, BaseFee: 20", types.ZeroAddress)
assert.EqualError(t, err, expectedError, i)

return true
Expand Down
6 changes: 3 additions & 3 deletions state/londonFix_fork.go
Original file line number Diff line number Diff line change
Expand Up @@ -114,9 +114,9 @@ func (l *LondonFixForkV2) checkDynamicFees(msg *types.Transaction, t *Transition

// This will panic if baseFee is nil, but basefee presence is verified
// as part of header validation.
if msg.GetGasFeeCap().Cmp(t.ctx.BaseFee) < 0 {
return fmt.Errorf("%w: address %v, GasFeeCap: %s, BaseFee: %s", ErrFeeCapTooLow,
msg.From.String(), msg.GasFeeCap, t.ctx.BaseFee)
if gasFeeCap := msg.GetGasFeeCap(); gasFeeCap.Cmp(t.ctx.BaseFee) < 0 {
return fmt.Errorf("%w: address %v, GasFeeCap/GasPrice: %s, BaseFee: %s", ErrFeeCapTooLow,
msg.From.String(), gasFeeCap, t.ctx.BaseFee)
}

return nil
Expand Down

0 comments on commit 400f388

Please sign in to comment.