Introducing P2P Authentication and Mismatch Resolution in v0.12.2

Simple Summary and Motivation

The upcoming v0.12.2 release introduces two key features to enhance Starknet’s reliability and performance:

  1. Enabling P2P Authentication: To establish a secure peer-to-peer network, Starknet is adding an endpoint in the sequencer gateway to provide a signature on the state diff commitment and block hash. This allows nodes to check the integrity of peer’s data and avoid DoS attacks.
  2. Resolving Mismatches in Queries: Starknet is introducing an extension to the get_state_update endpoint in the sequencer gateway that returns both the pending state diff and the pending block together. This simplifies the process for full nodes to address discrepancies between pending block and state diff queries.

Sequencer gateway API Changes

Signature on State Diff Commitment and Block Hash

  • New endpoint: get_signature
    • Parameters: blockHash (hex) or blockNumber (int)
    • Output: block_hash, block_number, state_diff_commitment, and a signature on the Poseidon hash of block_hash+state_diff_commitment
    • The key pair will be updated every year (unless the key is compromised, in which case we will replace it immediately).
    • The service will keep only the most up-to-date key pair, and the feeder will sign all block_hash + state_diff_commitment with the up-to-date private key.
    • The state diff will be sorted by order of (contract address, storage key)
    • Purpose: This new endpoint enables full nodes to sync data from other nodes and verify the reliability of the information. By providing a signature on the state diff commitment and block hash, it ensures the integrity of the data being exchanged, allowing full nodes to know that the data originated from the Sequencer.
  • New endpoint: get_public_key
    • Output the up-to-date public_key (felt)
    • The signature is an ECDSA over the STARK curve

This mechanism is temporary and will be replaced by the Starknet Consensus protocol once it is released.

The state_diff_commitment computation will follow these steps:

  • To ensure future compatibility, the number of available DA modes will be encoded in the outer level of the encoding. Currently, there is one only possible DA modes - L1DA with value da_mode=0 (see more details in Volition forum post).

  • For each DA_mode, we will note its DA mode number, followed by the encoding of this mode’s state diff The only memberes relevant for a specific DA modes’s state diff is the “storage_diff” and the “nonces”. We consider the members: deployed_contracts, declared_classes, old_declared_contracts, and replaced_classes as L1 - specific DA mode.

  • The members deployed_contracts and replaced_classes will be squashed together for this encoding.

  • For each member of state_diff, it will be flattened and hashed as follows:

    • flattened_storage_diffs = [number_of_updated_contracts, contract_address_1, number_of_updates_in_contract, key_1, value_1, key_2, value_2, ..., contract_address_2, number_of_updates_in_contract, ...]

    • flattened_nonces = [number_of_updated_contracts, address_1, nonce_1, address_2, nonce_2, ...]

    • hash_of_deployed_contracts=hash([number_of_deployed_contracts, address_1, class_hash_1, address_2, class_hash_2, ...])

    • hash_of_declared_classes = hash([number_of_declared_classes, class_hash_1, compiled_class_hash_1, class_hash_2, compiled_class_hash_2, ...])

    • hash_of_old_declared_classes = hash([number_of_old_declared_classes, class_hash_1, class_hash_2, ...])

  • Then, for each DA mode, for a given state_diff, we will encode:

    • hash_of_storage_domain_state_diff = hash([*flattened_storage_diffs, *flattened_nonces])
  • Finally, we concatenate the different storage domains with the rest of the general L1 data. Note: currently, state_diff_version = 0.

    • flattened_total_state_diff = hash([state_diff_version, hash_of_deployed_contracts, hash_of_declared_classes, hash_of_old_declared_classes, number_of_DA_modes, DA_mode_0, hash_of_storage_domain_state_diff_0, DA_mode_1, hash_of_storage_domain_state_diff_1, …])
  • Where the hash function is Poseidon, DA_mode_0 = 0, and there are no other DA modes in this version.

Combined State Diff and Block Endpoint

A new parameter has been added to the get_state_update endpoint - includeBlock - which allows getting the relevant block together with the state diff.

This new extension simplifies the process for full nodes to resolve mismatches between get_state_update and get_block of the pending block. By fetching both the state diff and block in one request, full nodes can ensure consistency in the data they retrieve, reducing potential discrepancies and enhancing synchronization efficiency.

  • Endpoint get_state_update
    • Parameters:
      • blockHash (hex) or blockNumber (Union(int,”pending”,”latest”))
      • New: includeBlock (bool), default=false.
    • Output:
      • State diff
      • Block if includeBlock=true