Skip to content
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
efe6cb6
Versioned unsigned transaction with multisig credential (#2688)
theodorebugnet Apr 15, 2026
c8de5d1
Simplify Transaction versioned struct generics (#2737)
theodorebugnet Apr 16, 2026
b37593d
Remove redundant runtime_call getter (#2741)
theodorebugnet Apr 15, 2026
1f5b7fa
Add non malleable hash for Generation uniqueness (#2751)
theodorebugnet Apr 21, 2026
bed8420
Accounts Refactor PR 1: Adding account -> [credential_id] mapping (#2…
citizen-stig May 6, 2026
88c15c0
Accounts Refactor PR 2: Adding `address_override` param to tx (#2771)
citizen-stig May 8, 2026
11a214a
Accounts Refactor PR 3: Addinng more call messages to accounts module…
citizen-stig May 12, 2026
63f16d8
Typescript multisig upgrade (#2758)
theodorebugnet May 14, 2026
406b3d3
Accounts Refactor PR 4: Adding address registration without private k…
citizen-stig May 14, 2026
bcefbf8
Accounts Refactor PR 5: Cleanup, Events and other minor follow ups (…
citizen-stig May 15, 2026
f5457b2
Versioned state (#2856)
theodorebugnet May 15, 2026
ec7f75f
State migrations library (#2864)
theodorebugnet May 19, 2026
ae79c52
Fix test_unsigned_tx_wallet_serialization_window_uniqueness (#2894)
ross-weir May 20, 2026
4edff8a
Remove extra gas charge/udpate chain hash (#2899)
ross-weir May 21, 2026
d8f0ec1
Add borsh metered reader (#2890)
ross-weir May 22, 2026
cbe03dd
Update StateAccessor trait for `resolve_context` (#2908)
citizen-stig May 25, 2026
bca083c
Borsh microbenches for gas costs (#2906)
ross-weir May 25, 2026
c6ec074
Clean up `EVM_RECEIPT_ACTUAL_FEE_HEIGHT` constant (#2904)
citizen-stig May 25, 2026
28e965f
Split UnsignedTransction from TransactionSigningPayload types (#2876)
theodorebugnet Jun 1, 2026
46f1595
fix cargo lock
theodorebugnet Jun 2, 2026
c263d1c
Multisig solana v0 improvement (#2813)
theodorebugnet Jun 2, 2026
c27e19f
Remove `CHANGE_GAS_LIMIT_AFTER_HEIGHT` (#2934)
citizen-stig Jun 4, 2026
054a2d4
Make state_version required in the chain state genesis, to avoid bein…
theodorebugnet Jun 5, 2026
861ef1a
SOV-2: Fix unchecked fields during deserialization (#2948)
ross-weir Jun 9, 2026
6042e90
Make v1 migration idempotent (#2965)
citizen-stig Jun 11, 2026
6687122
Fixes after rebase
citizen-stig Jun 11, 2026
4f34190
Add state related gas constant calibration (#2931)
ross-weir Jun 15, 2026
5861e3f
Regenerate generated artifacts after rebase
ross-weir Jun 24, 2026
b9f195c
Fix test-code drift after rebase
ross-weir Jun 24, 2026
41bebac
Use rebuilt hyperlane agent image (multisig_upgrade2)
ross-weir Jun 24, 2026
675f818
Fix trailing-bytes count for rebased tx format; fix agent image comment
ross-weir Jun 24, 2026
3b56968
Fix demo-rollup feature issues after rebase
theodorebugnet Jul 9, 2026
e8ac605
Sequencing data refactor (#3034)
theodorebugnet Jul 10, 2026
e5b6782
Add global activation height for precompiles to avoid a state read ch…
theodorebugnet Jul 15, 2026
a63b65a
Limit generation/windowed-nonce growth (#3032)
theodorebugnet Jul 20, 2026
c0f05eb
Replace chain_id with chain_hash_fragment in TxDetails, to aid in det…
theodorebugnet Jul 20, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
32 changes: 32 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,8 @@
# 2026-05-20
- #2893 Adds a new interface for providing custom EVM precompiles that can access sov-state (read-only). Precompiles must implement the `EvmPrecopmile` trait. The `sov-evm::Evm` module is now generic on `EvmPrecompileSet`; a Set can be generated from several `EvmPrecopmile`s using the `generate_precompile_set!` macro. See e.g. `BankBalancePrecompile` or `SequencingTimestampPrecompile` for implementation examples, and the demo-rollup changes for a usage example.
* Breaking(code): This PR also changes the visibility of some `sov-evm` export which are intended for internal usage, as well as the signature and generic on `sov-evm` construction. Normal rollup usage should be unaffected.
# 2026-05-20
- #2890 **Breaking Change**: Borsh deserialization is now metered by work done. Adds `MeteredReader` + `MeteredBorshDeserialize` (blanket-impl'd for `T: BorshDeserialize`) and three new gas constants (`BIAS_BORSH_DESERIALIZATION`, `BORSH_PER_BYTE_READ`, `BORSH_PER_READ_BIAS`) replacing the per-type `*_GAS_TO_CHARGE_PER_BYTE_BORSH_DESERIALIZATION` / `*_BIAS_BORSH_DESERIALIZATION` constants (DEFAULT, TX, PROOF, STRING). Changes the chain hash.

# 2026-05-15
- #2875 Upgrades SP1 crates from 6.1.0 to 6.2.1. Centralizes the `sp1-*` and `slop-algebra` workspace dependencies in the root `Cargo.toml`; the upgrade also drops the transitive `halo2` / `zkhash` chain, allowing the `halo2` proprietary-license exception to be removed from `deny.toml`. Stale Plonky-3 / SP1 v5 entries in `.cargo/config.toml` are refreshed to match the v6 architecture.
Expand Down Expand Up @@ -135,6 +137,36 @@
- #2682 Upgrades axum from 0.7 to 0.8. OpenAPI specs are now served as version 3.1.0 (previously 3.0.2). Manual intervention for upgrading pinned dependencies might be needed. Check Cargo.lock after the upgrade
- #2683 Removes JMT based rollup from demo-rollup examples. JMT-based storage is still available in sov-state.

# MULTISIG UPGRADE
Temporary section for maintaining breaking changes from individual PRs, which will be consolidated into a single changelog entry when the feature branch is merged into `dev`.
- #2773 **Breaking change (code, wire, consensus)**: `sov_accounts::CallMessage` gains three variants — `AddCredentialToAddress { address, credential }`, `RemoveCredentialFromAddress { address, credential }`, and `RotateCredentialOnAddress { address, old_credential, new_credential }` — and is now generic in `S: Spec`. The enum's wire format changes, which changes the chain hash. All three new variants require `context.sender() == address` (callers can only modify credentials on the address they are currently signing as); `InsertCredentialId` semantics are unchanged. `Rotate` is functionally equivalent to a `Remove` + `Add` collapsed into a single call for key rotation. There is no orphan guard on remove.
- #2850 **Breaking change (code, wire, consensus)**: `sov_accounts::CallMessage` gains a fourth variant, `CreateSyntheticAddress { salt: [u8; 32] }`, for creating synthetic addresses (the same construct other ecosystems call *counterfactual* addresses, cf. ERC-4337 / CREATE2 — addresses with no canonical-signer derivation, suitable for DAO/treasury/pre-funded use cases). The new address is derived deterministically by hashing `(domain || visible_slot_hash || sender_addr || sender_credential || salt)` with `S::CryptoSpec::Hasher`, converting the resulting 32 bytes to `CredentialId`, and then to `S::Address`. The caller's current credential is auto-authorized for it. Re-issuing the same `(caller, salt)` in the same visible slot is an idempotent no-op. `sov-accounts` gains a `sov-chain-state` module dependency for reading the visible slot hash; no runtime wiring change is required for runtimes that already include `chain_state` (all current runtimes do). The enum's wire format changes, which changes the chain hash. The module also begins emitting `CredentialAdded`, `CredentialRemoved`, `CredentialRotated`, and `SyntheticAddressCreated` events — one per call message (`InsertCredentialId` and `AddCredentialToAddress` both emit `CredentialAdded`); `sov_accounts::Module::Event` changes from `()` to `Event<S>`.
- #2853 Accounts: `AuthorizationResponse` (REST `GET /authorizations/{address}/{credential_id}`) gains `admit_as_override` and `admit_as_default` fields that mirror the on-chain admit-path predicates directly. The existing `authorized` field is deprecated — it uses the canonical-fallback semantic, which can disagree with the chain for authenticators whose `default_address` is not the credential's canonical address (notably EVM, where `default_address` is a `MultiAddress::Vm` variant while `canonical(credential_id)` is `MultiAddress::Standard`). REST consumers should read `admit_as_default` for the equivalent of the chain's admit-path. Additive change; existing callers continue to work.
- #2688 **Breaking change(code, state, consensus)**: The transaction formats have changed in this version. This is a consensus breaking change and requires coordinating an upgrade using `--stop-at-rollup-height`, and using sov-rollup-manager for full resyncs from this point onwards for existing rollups. This fixes Credential ID malleability that allowed the same set of signed bytes to be replayed for different credentials, across V0 and V1 (multisig) transactions and with different V1 multisig parameters.
* #2864 Hard fork version tracking: a new `chain_state.state_version` state item has been added, and a corresponding `STATE_VERSION` entry in constants.toml. These must match for the rollup to start. The binary `STATE_VERSION` will be incremented on breaking hard forks. On genesis, the state value must be initialised to the starting rollup binary's version, and it will subsequently be incremented by migrations between versions.
* Existing rollups must now run a migration, and make use of the rollup manager (`sov-rollup-manager`). `sov-migration::v1` provides the migration logic for this upgrade. Refer to the rollup manager documentation for details on how to orchestrate multiple versions.
* The on-chain transaction data has changed, and multisig transactions now explicitly include the multisig id as part of the signed bytes.
* Previous signatures are no longer valid. Clients will need to upgrade to our latest SDKs to be able to sign transactions in the new format.
* #2876 The transaction signing preimage types have been renamed to `TransactionSigningPayload{,V0,V1}` and now include the chain hash directly. `UnsignedTransaction` is now the user-created payload containing only the runtime call, uniqueness data, and transaction details. For creating a multisig, use `UnsignedTransaction::to_multisig_tx()`.
* The CHAIN_HASH has changed.
* The `Generation` uniqueness (replay protection) mechanism has been amended to fix a transaction hash malleability vulnerability with V1 transactions. New, non-malleable hashes are used to prevent replay. **If the rollup has had public V1 transactions submitted**, a migration script must increment the current generation of every user that has submitted a V1 transaction by `PAST_TRANSACTION_GENERATIONS` to invalidate prior existing hashes. No action is needed if there are no users with a prior V1 submission.
- #2904 **Breaking change**: for EVM rollups only: removes the `EVM_RECEIPT_ACTUAL_FEE_HEIGHT` constant.
Receipt `effectiveGasPrice` and projected `gasUsed` are now unconditionally derived from the actual metered fee.
Forks that had set this to a non-zero future activation height must migrate; the new behavior is mandatory.
- #2934 **Breaking Change**: Removes the `CHANGE_GAS_LIMIT_AFTER_HEIGHT` gas-limit fork. The `INITIAL_GAS_LIMIT` and `UPDATED_GAS_LIMIT` constants are replaced by a single `BLOCK_GAS_LIMIT` constant (test override env var `SOV_TEST_CONST_OVERRIDE_INITIAL_GAS_LIMIT` → `SOV_TEST_CONST_OVERRIDE_BLOCK_GAS_LIMIT`). Removes the `sequencer.height_for_gas_limit_computation` rate-limiter config field and the `ChainStateCapability::block_gas_limit` / `ChainState::block_gas_limit{,_at}` methods (use `<S as GasSpec>::block_gas_limit()` instead). The block gas limit is now constant for all heights; the per-block sequencer safeguards (preferred-sequencer pre-exec escrow, zero-bond preferred-sequencer penalization, and the slot-gas-limit pre-check) remain unconditionally enabled.
- #3032 Generation and windowed-nonce based uniqueness checks now reject transactions that provide a value 2x greater than the last observed value (except for very low numbers where the limit is more lenient). This provides some protection against user error accidentally making an account unusable by submitting a transaction with a very high value, irreversibly ratcheting the generation or nonce window to an unergonomic value or even u64::MAX.
- #2965 sov-migrations: the v1 (state_version 0->1) migration is now idempotent. Re-running it against an already-migrated DB (state_version >= 1) logs a message and exits Ok instead of erroring, so a restarted rollup that re-invokes the migration binary no longer fails.
- #3034 **Breaking change (code)**: Refactors Runtime traits to make custom sequencing data support more ergonomic. As a side-effect, rollups that don't use sequencing data must now define
```
impl<S: Spec> HasSequencingData<S> for Runtime<S>
where
S::Address: FromVmAddress<EthereumAddress> + FromVmAddress<Base58Address> + HyperlaneAddress,
{
type SequencingData = ();
}
```
since a fully default blanket implementation is not possible with the new traits.

# 2026-04-01
- #2670 **Breaking change** Remove `InnerVm` and `OuterVm` generic type parameters from `StateTransitionFunction` trait and all downstream types.

Expand Down
23 changes: 23 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

4 changes: 3 additions & 1 deletion Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ members = [
"crates/utils/sov-evm-test-utils",
"crates/utils/sov-proxy-utils",
"crates/utils/sov-shutdown",
"crates/utils/sov-migrations",
# Module System
"crates/module-system/sov-cli",
"crates/module-system/sov-modules-stf-blueprint",
Expand Down Expand Up @@ -106,7 +107,7 @@ members = [
"crates/web3",
"python/py_sovereign_web3/rust",
]
default-members = ["crates/rollup-interface", "crates/adapters/mock-da", "crates/adapters/mock-zkvm", "crates/full-node/sov-blob-sender", "crates/full-node/sov-db", "crates/full-node/sov-sequencer", "crates/full-node/sov-ledger-apis", "crates/full-node/sov-rollup-apis", "crates/full-node/sov-rollup-full-node-interface", "crates/full-node/sov-stf-runner", "crates/full-node/sov-metrics", "crates/full-node/sov-api-spec", "crates/full-node/full-node-configs", "crates/utils/sov-rest-utils", "crates/utils/nearly-linear", "crates/utils/sov-zkvm-utils", "crates/utils/sov-build", "crates/module-system/hyperlane", "crates/module-system/sov-cli", "crates/module-system/sov-modules-stf-blueprint", "crates/module-system/sov-modules-rollup-blueprint", "crates/module-system/sov-modules-macros", "crates/module-system/sov-kernels", "crates/module-system/sov-state", "crates/module-system/sov-modules-api", "crates/module-system/sov-address", "crates/utils/sov-test-utils", "crates/utils/sov-evm-test-utils", "crates/module-system/module-implementations/sov-accounts", "crates/module-system/module-implementations/sov-bank", "crates/module-system/module-implementations/sov-chain-state", "crates/module-system/module-implementations/sov-blob-storage", "crates/module-system/module-implementations/sov-evm", "crates/module-system/module-implementations/sov-paymaster", "crates/module-system/module-implementations/sov-prover-incentives", "crates/module-system/module-implementations/sov-attester-incentives", "crates/module-system/module-implementations/sov-sequencer-registry", "crates/module-system/module-implementations/sov-value-setter", "crates/module-system/module-implementations/sov-revenue-share", "crates/module-system/module-implementations/sov-synthetic-load", "crates/module-system/module-implementations/module-template", "crates/module-system/module-implementations/integration-tests", "crates/module-system/sov-capabilities", "crates/module-system/module-implementations/sov-uniqueness", "crates/module-system/module-implementations/sov-timelock", "crates/utils/sov-node-client", "crates/universal-wallet/schema", "crates/universal-wallet/macros", "crates/universal-wallet/macro-helpers", "crates/utils/workspace-hack", "crates/web3", "python/py_sovereign_web3/rust", "crates/module-system/module-implementations/extern/hyperlane-solana-register"]
default-members = ["crates/rollup-interface", "crates/adapters/mock-da", "crates/adapters/mock-zkvm", "crates/full-node/sov-blob-sender", "crates/full-node/sov-db", "crates/full-node/sov-sequencer", "crates/full-node/sov-ledger-apis", "crates/full-node/sov-rollup-apis", "crates/full-node/sov-rollup-full-node-interface", "crates/full-node/sov-stf-runner", "crates/full-node/sov-metrics", "crates/full-node/sov-api-spec", "crates/full-node/full-node-configs", "crates/utils/sov-rest-utils", "crates/utils/nearly-linear", "crates/utils/sov-zkvm-utils", "crates/utils/sov-build", "crates/utils/sov-migrations", "crates/module-system/hyperlane", "crates/module-system/sov-cli", "crates/module-system/sov-modules-stf-blueprint", "crates/module-system/sov-modules-rollup-blueprint", "crates/module-system/sov-modules-macros", "crates/module-system/sov-kernels", "crates/module-system/sov-state", "crates/module-system/sov-modules-api", "crates/module-system/sov-address", "crates/utils/sov-test-utils", "crates/utils/sov-evm-test-utils", "crates/module-system/module-implementations/sov-accounts", "crates/module-system/module-implementations/sov-bank", "crates/module-system/module-implementations/sov-chain-state", "crates/module-system/module-implementations/sov-blob-storage", "crates/module-system/module-implementations/sov-evm", "crates/module-system/module-implementations/sov-paymaster", "crates/module-system/module-implementations/sov-prover-incentives", "crates/module-system/module-implementations/sov-attester-incentives", "crates/module-system/module-implementations/sov-sequencer-registry", "crates/module-system/module-implementations/sov-value-setter", "crates/module-system/module-implementations/sov-revenue-share", "crates/module-system/module-implementations/sov-synthetic-load", "crates/module-system/module-implementations/module-template", "crates/module-system/module-implementations/integration-tests", "crates/module-system/sov-capabilities", "crates/module-system/module-implementations/sov-uniqueness", "crates/module-system/module-implementations/sov-timelock", "crates/utils/sov-node-client", "crates/universal-wallet/schema", "crates/universal-wallet/macros", "crates/universal-wallet/macro-helpers", "crates/utils/workspace-hack", "crates/web3", "python/py_sovereign_web3/rust", "crates/module-system/module-implementations/extern/hyperlane-solana-register"]
[workspace.package]
version = "0.3.0"
edition = "2021"
Expand Down Expand Up @@ -194,6 +195,7 @@ sov-modules-macros = { path = "crates/module-system/sov-modules-macros", default
sov-modules-stf-blueprint = { path = "crates/module-system/sov-modules-stf-blueprint", default-features = false, version = "0.3" }
sov-test-utils = { path = "crates/utils/sov-test-utils", default-features = false, version = "0.3" }
sov-evm-test-utils = { path = "crates/utils/sov-evm-test-utils", default-features = false, version = "0.3" }
sov-migrations = { path = "crates/utils/sov-migrations", default-features = false, version = "0.3" }
sov-rpc-eth-types = { path = "crates/utils/sov-rpc-eth-types", default-features = false, version = "0.3" }
sov-db = { path = "crates/full-node/sov-db", default-features = false, version = "0.3" }
sov-db-types = { path = "crates/full-node/sov-db-types", version = "0.3" }
Expand Down
31 changes: 9 additions & 22 deletions constants.testing.toml
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ freeze = [1, 1]
# We use the ID 4321 for demo purposes. Change this value before deploying!
CHAIN_ID = 4321
CHAIN_NAME = "TestChain"
STATE_VERSION = 1
CHAIN_HASH_OVERRIDES = []
# The number of bytes a transaction can have.
MAX_TX_SIZE=1_048_576
Expand All @@ -34,9 +35,8 @@ EVM_BLOCK_PRUNING_THRESHOLD = 10000
EVM_GAS_METERING_MODE = "Rollup"
# After this evm block height, the max_fee check will be enforced.
EVM_MAX_FEE_CHECK_HEIGHT = 0
# After this evm block height, RPC receipts derive effectiveGasPrice
# from the actual fee charged by the Sovereign gas meter.
EVM_RECEIPT_ACTUAL_FEE_HEIGHT = 0
# Before this rollup height, custom EVM precompiles are disabled without reading their enabled set.
ENABLE_EVM_CUSTOM_PRECOMPILES_AT = 0
# How many rollup blocks to wait before terminating setup mode. While setup mode is enabled,
# the rollup does not charge gas. This is useful when initializing the rollup with a bridged gas token.
SETUP_MODE_TERMINATION_HEIGHT = 0 # Disable setup mode entirely by default.
Expand Down Expand Up @@ -124,26 +124,15 @@ PROCESS_TX_PRE_EXEC_GAS = [1, 1]
PROCESS_TX_PRE_EXEC_GAS_PER_TX_BYTE = [1, 1]
# --- End Gas parameters to specify how to charge gas for signature verification ---

# The cost of deserializing a message using Borsh
DEFAULT_GAS_TO_CHARGE_PER_BYTE_BORSH_DESERIALIZATION = [1, 1]
# --- Borsh deserialization gas constants ---
BIAS_BORSH_DESERIALIZATION = [1, 1]
BORSH_PER_BYTE_READ = [1, 1]
BORSH_PER_READ_BIAS = [0, 0]

# The cost of deserializing a tx using Borsh
TX_GAS_TO_CHARGE_PER_BYTE_BORSH_DESERIALIZATION = [1, 1]
TX_BIAS_BORSH_DESERIALIZATION = [1, 1]

# The cost of deserializing a tx using Borsh
# --- JSON deserialization gas constants ---
TX_GAS_TO_CHARGE_PER_BYTE_JSON_DESERIALIZATION = [1, 1]
TX_BIAS_JSON_DESERIALIZATION = [1, 1]

# The cost of deserializing a proof using Borsh
PROOF_GAS_TO_CHARGE_PER_BYTE_BORSH_DESERIALIZATION = [1, 1]
PROOF_BIAS_BORSH_DESERIALIZATION = [1, 1]

# The cost of deserializing a string using Borsh
STRING_GAS_TO_CHARGE_PER_BYTE_BORSH_DESERIALIZATION = [1, 1]
STRING_BIAS_BORSH_DESERIALIZATION = [1, 1]

# The amount of gas to charge per zk-proof byte
GAS_TO_CHARGE_PER_PROOF_BYTE = [1, 1]
# The amount of gas to charge per zk-proof
Expand All @@ -154,10 +143,8 @@ FIXED_GAS_TO_CHARGE_PER_PROOF = [100, 100]
# The portion that is not burned is awarded to provers and/or attesters on the network.
PERCENT_BASE_FEE_TO_BURN = 10
# --- Gas fee adjustment parameters: See https://eips.ethereum.org/EIPS/eip-1559 for a detailed description ---
# The initial gas limit of the rollup.
INITIAL_GAS_LIMIT = [100_000_000_000, 100_000_000_000]
UPDATED_GAS_LIMIT = [100_000_000_000, 100_000_000_000]
CHANGE_GAS_LIMIT_AFTER_HEIGHT = 9223372036854775807
# The gas limit applied to every rollup block.
BLOCK_GAS_LIMIT = [100_000_000_000, 100_000_000_000]
# The initial "base fee" that every transaction emits when executed.
INITIAL_BASE_FEE_PER_GAS = [10, 10]
# The maximum change denominator of the base fee.
Expand Down
Loading
Loading