Skip to content

Commit

Permalink
fix l1 gas estimation for l2 chain
Browse files Browse the repository at this point in the history
  • Loading branch information
rouzwelt committed Jan 13, 2025
1 parent a6fe477 commit 253b381
Show file tree
Hide file tree
Showing 10 changed files with 237 additions and 24 deletions.
8 changes: 3 additions & 5 deletions src/gas.ts
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,6 @@ export async function estimateGasCost(
const result = {
gas,
gasPrice,
l1Gas: 0n,
l1GasPrice: 0n,
l1Cost: 0n,
totalGasCost: gasPrice * gas,
Expand All @@ -31,14 +30,13 @@ export async function estimateGasCost(
if (typeof l1GasPrice !== "bigint") {
l1GasPrice = (await l1Signer_.getL1BaseFee()) as bigint;
}
const l1Gas = await l1Signer_.estimateL1Gas({
const l1Cost = await l1Signer_.estimateL1Fee({
to: tx.to,
data: tx.data,
});
result.l1Gas = l1Gas;
result.l1GasPrice = l1GasPrice;
result.l1Cost = l1Gas * l1GasPrice;
result.totalGasCost += result.l1Cost;
result.l1Cost = l1Cost;
result.totalGasCost += l1Cost;
} catch {}
}
return result;
Expand Down
22 changes: 22 additions & 0 deletions src/modes/interOrderbook.ts
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,13 @@ export async function dryrun({
const estimation = await estimateGasCost(rawtx, signer, config, l1GasPrice);
l1Cost = estimation.l1Cost;
gasLimit = ethers.BigNumber.from(estimation.gas).mul(config.gasLimitMultiplier).div(100);
spanAttributes["gasEst.headroom.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.headroom.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.headroom.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["gasEst.headroom.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.headroom.l1Cost"] = estimation.l1Cost.toString();
}
} catch (e) {
const isNodeError = containsNodeError(e as BaseError);
const errMsg = errorSnapshot("", e);
Expand Down Expand Up @@ -153,6 +160,10 @@ export async function dryrun({
// sender output which is already called above
if (config.gasCoveragePercentage !== "0") {
const headroom = (Number(config.gasCoveragePercentage) * 1.03).toFixed();
spanAttributes["gasEst.headroom.minBountyExpected"] = gasCost
.mul(headroom)
.div("100")
.toString();
task.evaluable.bytecode = await parseRainlang(
await getBountyEnsureRainlang(
ethers.utils.parseUnits(inputToEthPrice),
Expand All @@ -177,6 +188,13 @@ export async function dryrun({
.div(100);
rawtx.gas = gasLimit.toBigInt();
gasCost = gasLimit.mul(gasPrice).add(estimation.l1Cost);
spanAttributes["gasEst.final.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.final.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.final.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["gasEst.final.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.final.l1Cost"] = estimation.l1Cost.toString();
}
task.evaluable.bytecode = await parseRainlang(
await getBountyEnsureRainlang(
ethers.utils.parseUnits(inputToEthPrice),
Expand All @@ -192,6 +210,10 @@ export async function dryrun({
takeOrdersConfigStruct,
task,
]);
spanAttributes["gasEst.final.minBountyExpected"] = gasCost
.mul(config.gasCoveragePercentage)
.div("100")
.toString();
} catch (e) {
const isNodeError = containsNodeError(e as BaseError);
const errMsg = errorSnapshot("", e);
Expand Down
22 changes: 22 additions & 0 deletions src/modes/intraOrderbook.ts
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,13 @@ export async function dryrun({
const estimation = await estimateGasCost(rawtx, signer, config, l1GasPrice);
l1Cost = estimation.l1Cost;
gasLimit = ethers.BigNumber.from(estimation.gas).mul(config.gasLimitMultiplier).div(100);
spanAttributes["gasEst.headroom.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.headroom.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.headroom.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["gasEst.headroom.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.headroom.l1Cost"] = estimation.l1Cost.toString();
}
} catch (e) {
// reason, code, method, transaction, error, stack, message
const isNodeError = containsNodeError(e as BaseError);
Expand Down Expand Up @@ -146,6 +153,10 @@ export async function dryrun({
// sender output which is already called above
if (config.gasCoveragePercentage !== "0") {
const headroom = (Number(config.gasCoveragePercentage) * 1.03).toFixed();
spanAttributes["gasEst.headroom.minBountyExpected"] = gasCost
.mul(headroom)
.div("100")
.toString();
task.evaluable.bytecode = await parseRainlang(
await getWithdrawEnsureRainlang(
signer.account.address,
Expand Down Expand Up @@ -179,6 +190,13 @@ export async function dryrun({
.div(100);
rawtx.gas = gasLimit.toBigInt();
gasCost = gasLimit.mul(gasPrice).add(estimation.l1Cost);
spanAttributes["gasEst.final.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.final.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.final.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["gasEst.final.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.final.l1Cost"] = estimation.l1Cost.toString();
}
task.evaluable.bytecode = await parseRainlang(
await getWithdrawEnsureRainlang(
signer.account.address,
Expand All @@ -203,6 +221,10 @@ export async function dryrun({
rawtx.data = obInterface.encodeFunctionData("multicall", [
[clear2Calldata, withdrawInputCalldata, withdrawOutputCalldata],
]);
spanAttributes["gasEst.final.minBountyExpected"] = gasCost
.mul(config.gasCoveragePercentage)
.div("100")
.toString();
} catch (e) {
const isNodeError = containsNodeError(e as BaseError);
const errMsg = errorSnapshot("", e);
Expand Down
29 changes: 15 additions & 14 deletions src/modes/routeProcessor.ts
Original file line number Diff line number Diff line change
Expand Up @@ -189,13 +189,12 @@ export async function dryrun({
gasLimit = ethers.BigNumber.from(estimation.gas)
.mul(config.gasLimitMultiplier)
.div(100);
spanAttributes["headroom.estGasLimit"] = estimation.gas.toString();
spanAttributes["headroom.estTotalCost"] = estimation.totalGasCost.toString();
spanAttributes["headroom.gasPrice"] = estimation.gasPrice.toString();
spanAttributes["gasEst.headroom.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.headroom.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.headroom.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["headroom.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["headroom.estL1GasLimit"] = estimation.l1Gas.toString();
spanAttributes["headroom.estL1Cost"] = l1Cost.toString();
spanAttributes["gasEst.headroom.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.headroom.l1Cost"] = estimation.l1Cost.toString();
}
} catch (e) {
// reason, code, method, transaction, error, stack, message
Expand Down Expand Up @@ -227,7 +226,10 @@ export async function dryrun({
// sender output which is already called above
if (config.gasCoveragePercentage !== "0") {
const headroom = (Number(config.gasCoveragePercentage) * 1.03).toFixed();
spanAttributes["headroom.minExpected"] = gasCost.mul(headroom).div("100").toString();
spanAttributes["gasEst.headroom.minBountyExpected"] = gasCost
.mul(headroom)
.div("100")
.toString();
task.evaluable.bytecode = await parseRainlang(
await getBountyEnsureRainlang(
ethers.utils.parseUnits(ethPrice),
Expand All @@ -252,13 +254,12 @@ export async function dryrun({
.div(100);
rawtx.gas = gasLimit.toBigInt();
gasCost = gasLimit.mul(gasPrice).add(estimation.l1Cost);
spanAttributes["actual.estGasLimit"] = estimation.gas.toString();
spanAttributes["actual.estTotalCost"] = estimation.totalGasCost.toString();
spanAttributes["actual.gasPrice"] = estimation.gasPrice.toString();
spanAttributes["gasEst.final.gasLimit"] = estimation.gas.toString();
spanAttributes["gasEst.final.totalCost"] = estimation.totalGasCost.toString();
spanAttributes["gasEst.final.gasPrice"] = estimation.gasPrice.toString();
if (config.isSpecialL2) {
spanAttributes["actual.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["actual.estL1GasLimit"] = estimation.l1Gas.toString();
spanAttributes["actual.estL1Cost"] = l1Cost.toString();
spanAttributes["gasEst.final.l1GasPrice"] = estimation.l1GasPrice.toString();
spanAttributes["gasEst.final.l1Cost"] = estimation.l1Cost.toString();
}
task.evaluable.bytecode = await parseRainlang(
await getBountyEnsureRainlang(
Expand All @@ -275,7 +276,7 @@ export async function dryrun({
takeOrdersConfigStruct,
task,
]);
spanAttributes["actual.minExpected"] = gasCost
spanAttributes["gasEst.final.minBountyExpected"] = gasCost
.mul(config.gasCoveragePercentage)
.div("100")
.toString();
Expand Down
36 changes: 36 additions & 0 deletions test/findOpp.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -141,6 +141,18 @@ describe("Test find opp", async function () {
marketPrice: formatUnits(getCurrentPrice(vaultBalance)),
route: expectedRouteVisual,
clearModePick: "rp4",
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down Expand Up @@ -237,6 +249,18 @@ describe("Test find opp", async function () {
foundOpp: true,
maxInput: vaultBalance.toString(),
clearModePick: "inter",
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down Expand Up @@ -338,6 +362,18 @@ describe("Test find opp", async function () {
oppBlockNumber,
foundOpp: true,
clearModePick: "intra",
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down
8 changes: 3 additions & 5 deletions test/gas.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ describe("Test gas", async function () {
// mock L1 signer for L2 client
const l1Signer = {
getL1BaseFee: async () => 20n,
estimateL1Gas: async () => 5n,
estimateL1Fee: async () => 5n,
};
// mock normal L1 signer
const signer = {
Expand All @@ -30,10 +30,9 @@ describe("Test gas", async function () {
const expected1 = {
gas: 55n,
gasPrice: 2n,
l1Gas: 5n,
l1GasPrice: 20n,
l1Cost: 20n * 5n,
totalGasCost: 2n * 55n + 20n * 5n,
l1Cost: 5n,
totalGasCost: 2n * 55n + 5n,
};
assert.deepEqual(result1, expected1);

Expand All @@ -43,7 +42,6 @@ describe("Test gas", async function () {
const expected2 = {
gas: 55n,
gasPrice: 2n,
l1Gas: 0n,
l1GasPrice: 0n,
l1Cost: 0n,
totalGasCost: 2n * 55n,
Expand Down
24 changes: 24 additions & 0 deletions test/mode-interOrderbook.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -124,6 +124,18 @@ describe("Test inter-orderbook dryrun", async function () {
oppBlockNumber,
foundOpp: true,
maxInput: vaultBalance.toString(),
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down Expand Up @@ -263,6 +275,18 @@ describe("Test inter-orderbook find opp", async function () {
oppBlockNumber,
foundOpp: true,
maxInput: vaultBalance.toString(),
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down
24 changes: 24 additions & 0 deletions test/mode-intraOrderbook.test.js
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,18 @@ describe("Test intra-orderbook dryrun", async function () {
spanAttributes: {
oppBlockNumber,
foundOpp: true,
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down Expand Up @@ -263,6 +275,18 @@ describe("Test intra-orderbook find opp", async function () {
spanAttributes: {
oppBlockNumber,
foundOpp: true,
"gasEst.final.gasLimit": gasLimitEstimation.toString(),
"gasEst.final.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.final.gasPrice": gasPrice.toString(),
"gasEst.final.minBountyExpected": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasLimit": gasLimitEstimation.toString(),
"gasEst.headroom.totalCost": gasLimitEstimation.mul(gasPrice).toString(),
"gasEst.headroom.gasPrice": gasPrice.toString(),
"gasEst.headroom.minBountyExpected": gasLimitEstimation
.mul(gasPrice)
.mul(103)
.div(100)
.toString(),
},
};
assert.deepEqual(result, expected);
Expand Down
Loading

0 comments on commit 253b381

Please sign in to comment.