Using a keystore account
bytes32 keystoreAddress format, which users can counterfactually initialize using the process described in Account Initialization. The state of the Axiom keystore is a mapping
bytes data holds the signing data for the keystore accountbytes vkey is a verification key for a ZK circuit that ingests data and verifies a ZK authentication proof for the update rule for keystoreAddress which will enable a user to update the (data, vkey) pair.KeystoreStateOracle: The contract which trustlessly caches keystore state roots onto the L2, exposing it to the L2’s execution environment.KeystoreValidator: The contract which facilitates IMT Merkle proofs to verify data against the state root, and validates smart account authentication data against data.outputRoots into storage during finalization, where an outputRoot is computed as
stateRoot is the state root after executing the transactions in the batch.withdrawalsRoot is the withdrawals root after executing the transactions in the batch.lastValidBlockhash is the keystore blockhash of the most recent valid block as of the batch.outputRoot from L1, extract the stateRoot from it, and cache it for use on the L2. The KSO can read outputRoots from L1 in two ways:
outputRoot and checking a hash equivalence.
Axiom is committed to syncing state roots for all supported L2s approximately once per hour.
In cases where this sync is delayed or there is a need to expedite the propagation of a finalized state root, a manual sync—whether via storage proof or bridge transaction—can also be triggered permissionlessly.
data against state roots cached on the KSO, and validates smart account authentication data against data.
To enable this integration, the KV must be installed as a module within the smart account, which requires compatibility with either the ERC-7579 or ERC-6900 standard. Without compatibility with one of these standards, the smart account cannot support the Keystore Validator.
Deployment details of the KV across all supported L2s are available in Contract Addresses.
The KV expects data to conform to the following structure:
(data, vkey) pair with an IMT proof, but will outsource further authentication against data to an external Key Data Consumer (KDC). There is (generally) a one-to-one correspondence between a vkey and a KDC and data[1..33] allows a vkey to signal how it desires to be authenticated on chain through a CODEHASH which commits to the validation logic of a KDC.
l1BlockTimestamp—the timestamp of the L1 block whose blockhash against which the Merkle trie proof was verified or the bridge transaction was sent. This metadata enables the KV to perform expiry checks, leveraging ERC-4337’s validateUserOp interface, which incorporates native timestamp validation through a return value embedding the validAfter and validUntil fields.
During the installation of the KV, the smart account specifies a stateRootValidityInterval. The validAfter and validUntil fields are then derived as l1BlockTimestamp and l1BlockTimestamp + stateRootValidityInterval, respectively. Given that Axiom guarantees a refresh interval of one hour, it is recommended to set the stateRootValidityInterval to at least 1 hour.
cacheValidityInterval. If some cached key data that was read from a state root with an l1BlockTimestamp is used, then the validAfter and validUntil fields are derived as l1BlockTimestamp and l1BlockTimestamp + cacheValidityInterval, respectively. Setting the cacheValidityInterval to 0 effectively disallows use of the cache.
When caching is enabled, UIs should clearly display the currently valid set(s) of signing data across all chains. This is crucial as cached values remain valid until either the cacheValidityInterval expires or they are overwritten by newer values. In the case the key rotation is time-sensitive (e.g. due to a compromised key), users should be presented with an option to proactively send cache-overwriting transactions to all relevant chains.