EIP-8141: Frame Transaction

I also STRONGLY think frames should include a value.

I think this was a part of one PR I have seen, though I don’t know it was removed.

One of the advantages that frame transactions have over traditional 7702 wallets, is that it makes it clear in auth only situation what the transaction is having the wallet execute. This is great because it provides a standardized view of what’s happening, which is incredibly useful for wallets and explorers.

Value is also needed when using pure EOA signature handling modes.

1 Like

Yes value should definitely be part of the frame, otherwise every smart account needlessly has to add a custom execute method.

I believe the EIP coauthors are supportive of enabling accounts to use SENDER frames to transfer value without implementing their own execute() function, though there are a few different ways to achieve that. Adding a value field is the most obvious approach, but there was also a different idea where we allow SENDER frames to do DELEGATECALL (possibly toggled via a bit flag), and then we define a precompile that implements an execute() function that supports value transfer and atomic batching. So now an account can just DELEGATECALL the precompile for execution.

Note that if we go with the DELEGATECALL + precompile approach, we’d presumably remove the atomic batching flag since then it’d be redundant.

I’m curious to hear if people in this thread would prefer the value + atomic flag approach, or the DELEGATECALL + precompile approach?

it would be beneficial to also allow loading the return data.

Could you give some examples on how that might be useful?

When evaluating our learnings from Safe we came to the conclusion that we would like to remove DELEGATECALLs completely, therefore we tend to just add the `value` field (with the atomic flag). Not having DELEGATECALL makes formal verification easier and provides stronger security guarantess.

1 Like

Actually accessing return data of a frame might not be a good idea :sweat_smile: I was thinking about it in the context of handling modules. My optimistic approach would be that account contract actually only holds logic for signature verification, the rest would be done via SENDER frames. But if do this and remove DELEGATECALLs then some of the more complex module flows become harder/ impossible to cover. Ultimately this is a tradeoff where we will most likely not get having some “execute” method on the account contract.

1 Like

Having value in the SENDER frame means that frame transactions can provide a clean separation between what you want the transaction to do (which frames would standardize for AA), and the authorization and payment for that transaction.

Removing value forces frames to be only dumb message pipes to smart contracts. This is bad because this:

  1. Kills the “drop in transaction upgrade” nature of frames that would make for the easiest initial adoption.
  2. Requires that wallets build full featured smart contract wallets for even the least adoption.
  3. Removes the tooling and ecosystem benefits that comes from having the transaction actions default to defined and visible in the frame.
1 Like

I prefer the value in the frame approach, it is more intuitive.

I am interested if I’m missing something though, what is the case for the delegatecall + precompile approach?

1 Like

Now that we are leaning more towards having frames support atomic batching, minimizing the need for an execute loop in wallets, I think it makes sense to support value in the frame. The reason for hesitation is that value only makes sense in the SENDER frame. We were hoping for frames to be totally generic across modes and not have a mismatch of usable fields, but it may be unavoidable. The DELEGATECALL approach could replace the need for value because you could delegatecall into a standardized contract to handle your execution.

1 Like

Not sure if this has been noted, but VERIFY frames are implicitly capped at 2 per transaction.

Every VERIFY must call APPROVE, there are only two approval flags (sender_approved, payer_approved), and each can only be set once. So you either have 1 VERIFY with APPROVE(0x3) or 2 VERIFYs splitting APPROVE(0x1) and APPROVE(0x2). A third VERIFY would have no valid scope left and would fail to APPROVE, invalidating the tx.

Might be worth stating this explicitly in the Constraints section as a static check it’s the kind of thing an implementer could easily miss when reading the spec.

2 Likes

Opened a PR for this along with a few other nits I found while reading through the spec: Update EIP-8141: Fix spec inconsistencies in APPROVE scopes, default code, and added verify frame count check by chiranjeev13 · Pull Request #11488 · ethereum/EIPs · GitHub

Relatedly, access to frame returndata would enable using it as input in multi-step flows without requiring wrapper contracts, which is desirable in many cases (similar to the motivation behind ERC-8211).

Has native support been considered, e.g. via FRAMERETURNDATASIZE and FRAMERETURNDATACOPY, with per-byte gas cost and a cap per frame?