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

fix: use simulation to estimate gas used #11211

Open
wants to merge 63 commits into
base: master
Choose a base branch
from
Open

Conversation

spypsy
Copy link
Member

@spypsy spypsy commented Jan 14, 2025

Relevant to #10991 but not 'Fixes' because anvil doesn't support eth_simulateV1 so we can't yet remove all time-based inputs in L1

Fixes #11341

  • We now try to simulate the 'propose' & 'proposeAndClaim' transactions, using the appropriate timestamp, instead of using hardcoded 12M gas.
  • Also some updates to logging where we
    1. Try to decode errors from our Rollup ABI
    2. truncate large Hexes but still include them in error data so txs can be investigated
  • Update slot duration to 36 for sepolia deployments

Follow-up from this: #11390 #11440

@spypsy spypsy marked this pull request as ready for review January 14, 2025 12:09
@spypsy spypsy force-pushed the spy/simulate-l1-txs branch from a3586fb to dc8198a Compare January 17, 2025 15:33
@@ -528,17 +528,19 @@ describe('L1Publisher integration', () => {
await expect(publisher.proposeL2Block(block)).resolves.toEqual(false);

// Test for both calls
expect(loggerErrorSpy).toHaveBeenCalledTimes(2);
// NOTE: First error is from the simulate fn, which isn't supported by anvil
Copy link
Contributor

Choose a reason for hiding this comment

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

The simulate with time overrides?

Copy link
Member Author

Choose a reason for hiding this comment

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

yep

* @param abi - The ABI to use for decoding.
* @returns A FormattedViemError instance.
*/
export function formatViemError(error: any, abi: Abi = RollupAbi): FormattedViemError {
Copy link
Contributor

Choose a reason for hiding this comment

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

I altered the script that we use to generate the artifacts such that the errors should be included inside the other ABIs. So they are in the rollup one or whetever is being used. But maybe it should not be specifically the RollupAbi that is being checked against here. Mainly if some other contract were used this formatter gets pretty strange.

https://github.com/AztecProtocol/aztec-packages/pull/10697/files

Comment on lines 612 to 613
// By simulation issue, I mean the fact that the block.timestamp is equal to the last block, not the next, which
// make time consistency checks break.
Copy link
Contributor

Choose a reason for hiding this comment

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

Should not be the case. Also, we should be able to get rid of the validateBlockForSubmission here if the send can actually simulate it.

// @note we override checkBlob to false since blobs are not part simulate()
stateDiff: [
{
slot: toHex(9n, true),
Copy link
Contributor

Choose a reason for hiding this comment

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

I think we could probably just use the forge inspect <CONTRACT> storageLayout --json to populate, then it should be fairly easy to fetch from there. Sounds like a good idea to have.

Its a kinda annoying one though, as ideally the variable itself should not exists 😬.

],
);

if (simulationResult === -1n) {
Copy link
Contributor

Choose a reason for hiding this comment

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

Throwing an error as mentioner earlier would make more sense to me here.

Copy link
Contributor

Changes to public function bytecode sizes

Generated at commit: 4c2833fa0650f18192cd4572b22d5f2ef6000a15, compared to commit: 30a063a65f95403773d13da0d9a896da45d9608d

🧾 Summary (100% most significant diffs)

Program Bytecode size in bytes (+/-) %
AvmTest::bulk_testing +70 ❌ +0.31%
AvmTest::public_dispatch +59 ❌ +0.09%

Full diff report 👇
Program Bytecode size in bytes (+/-) %
AvmTest::bulk_testing 22,676 (+70) +0.31%
AvmTest::public_dispatch 62,199 (+59) +0.09%

Copy link
Collaborator

@spalladino spalladino left a comment

Choose a reason for hiding this comment

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

LGTM! Just an issue with the things being thrown.

Comment on lines +195 to +197
if [ -n "${EXTERNAL_ETHEREUM_HOST}" ]; then
export ETHEREUM_HOST="${EXTERNAL_ETHEREUM_HOST}"
fi
Copy link
Collaborator

Choose a reason for hiding this comment

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

Curious why we have two different env vars

const formattedError = formatViemError(err);

const res = err;
// console.log('res', res);
Copy link
Collaborator

Choose a reason for hiding this comment

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

Suggested change
// console.log('res', res);

throw formattedErr;
const { message, metaMessages } = formatViemError(err);
this.logger?.error(`Failed to send L1 transaction`, message, { metaMessages });
throw { ...err, message, metaMessages };
Copy link
Collaborator

Choose a reason for hiding this comment

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

Heads up that you're not throwing an Error here, but a plain object. So any checks downstream for instanceof Error will fail, and any formatting specific to errors (such as printing the stack trace) will get lost. We should always throw a proper Error (or subclass) instance to avoid issues.

if (err.message?.includes('reverted')) {
throw formattedErr;
throw { ...error, message };
Copy link
Collaborator

Choose a reason for hiding this comment

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

Same as above

Comment on lines +1181 to +1187
if (simErr instanceof MethodNotFoundRpcError || simErr instanceof MethodNotSupportedRpcError) {
// @note node doesn't support simulation API, we will use gas guesstimate
this.log.warn('Using gas guesstimate');
simulationResult = L1Publisher.PROPOSE_GAS_GUESS;
} else {
throw simErr;
}
Copy link
Collaborator

Choose a reason for hiding this comment

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

It seems that we'll be doing this pretty often. Should we have simulateGasUsed accept a fallbackGasIfMethodNotSupported option to handle this automatically?

Comment on lines 612 to 613
// By simulation issue, I mean the fact that the block.timestamp is equal to the last block, not the next, which
// make time consistency checks break.
Copy link
Collaborator

Choose a reason for hiding this comment

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

I take it this will be addressed in another PR then, right?

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Include arguments in errors
3 participants