github.com/theQRL/go-zond@v0.1.1/consensus/misc/eip4844/eip4844.go (about) 1 // Copyright 2023 The go-ethereum Authors 2 // This file is part of the go-ethereum library. 3 // 4 // The go-ethereum library is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU Lesser General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // The go-ethereum library is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU Lesser General Public License for more details. 13 // 14 // You should have received a copy of the GNU Lesser General Public License 15 // along with the go-ethereum library. If not, see <http://www.gnu.org/licenses/>. 16 17 package eip4844 18 19 import ( 20 "errors" 21 "fmt" 22 "math/big" 23 24 "github.com/theQRL/go-zond/core/types" 25 "github.com/theQRL/go-zond/params" 26 ) 27 28 var ( 29 minBlobGasPrice = big.NewInt(params.BlobTxMinBlobGasprice) 30 blobGaspriceUpdateFraction = big.NewInt(params.BlobTxBlobGaspriceUpdateFraction) 31 ) 32 33 // VerifyEIP4844Header verifies the presence of the excessBlobGas field and that 34 // if the current block contains no transactions, the excessBlobGas is updated 35 // accordingly. 36 func VerifyEIP4844Header(parent, header *types.Header) error { 37 // Verify the header is not malformed 38 if header.ExcessBlobGas == nil { 39 return errors.New("header is missing excessBlobGas") 40 } 41 if header.BlobGasUsed == nil { 42 return errors.New("header is missing blobGasUsed") 43 } 44 // Verify that the blob gas used remains within reasonable limits. 45 if *header.BlobGasUsed > params.MaxBlobGasPerBlock { 46 return fmt.Errorf("blob gas used %d exceeds maximum allowance %d", *header.BlobGasUsed, params.MaxBlobGasPerBlock) 47 } 48 if *header.BlobGasUsed%params.BlobTxBlobGasPerBlob != 0 { 49 return fmt.Errorf("blob gas used %d not a multiple of blob gas per blob %d", header.BlobGasUsed, params.BlobTxBlobGasPerBlob) 50 } 51 // Verify the excessBlobGas is correct based on the parent header 52 var ( 53 parentExcessBlobGas uint64 54 parentBlobGasUsed uint64 55 ) 56 if parent.ExcessBlobGas != nil { 57 parentExcessBlobGas = *parent.ExcessBlobGas 58 parentBlobGasUsed = *parent.BlobGasUsed 59 } 60 expectedExcessBlobGas := CalcExcessBlobGas(parentExcessBlobGas, parentBlobGasUsed) 61 if *header.ExcessBlobGas != expectedExcessBlobGas { 62 return fmt.Errorf("invalid excessBlobGas: have %d, want %d, parent excessBlobGas %d, parent blobDataUsed %d", 63 *header.ExcessBlobGas, expectedExcessBlobGas, parentExcessBlobGas, parentBlobGasUsed) 64 } 65 return nil 66 } 67 68 // CalcExcessBlobGas calculates the excess blob gas after applying the set of 69 // blobs on top of the excess blob gas. 70 func CalcExcessBlobGas(parentExcessBlobGas uint64, parentBlobGasUsed uint64) uint64 { 71 excessBlobGas := parentExcessBlobGas + parentBlobGasUsed 72 if excessBlobGas < params.BlobTxTargetBlobGasPerBlock { 73 return 0 74 } 75 return excessBlobGas - params.BlobTxTargetBlobGasPerBlock 76 } 77 78 // CalcBlobFee calculates the blobfee from the header's excess blob gas field. 79 func CalcBlobFee(excessBlobGas uint64) *big.Int { 80 return fakeExponential(minBlobGasPrice, new(big.Int).SetUint64(excessBlobGas), blobGaspriceUpdateFraction) 81 } 82 83 // fakeExponential approximates factor * e ** (numerator / denominator) using 84 // Taylor expansion. 85 func fakeExponential(factor, numerator, denominator *big.Int) *big.Int { 86 var ( 87 output = new(big.Int) 88 accum = new(big.Int).Mul(factor, denominator) 89 ) 90 for i := 1; accum.Sign() > 0; i++ { 91 output.Add(output, accum) 92 93 accum.Mul(accum, numerator) 94 accum.Div(accum, denominator) 95 accum.Div(accum, big.NewInt(int64(i))) 96 } 97 return output.Div(output, denominator) 98 }