github.com/ethereum-optimism/optimism@v1.7.2/packages/contracts-bedrock/src/cannon/PreimageKeyLib.sol (about)

     1  // SPDX-License-Identifier: MIT
     2  pragma solidity 0.8.15;
     3  
     4  /// @title PreimageKeyLib
     5  /// @notice Shared utilities for localizing local keys in the preimage oracle.
     6  library PreimageKeyLib {
     7      /// @notice Generates a context-specific local key for the given local data identifier.
     8      /// @dev See `localize` for a description of the localization operation.
     9      /// @param _ident The identifier of the local data. [0, 32) bytes in size.
    10      /// @param _localContext The local context for the key.
    11      /// @return key_ The context-specific local key.
    12      function localizeIdent(uint256 _ident, bytes32 _localContext) internal view returns (bytes32 key_) {
    13          assembly {
    14              // Set the type byte in the given identifier to `1` (Local). We only care about
    15              // the [1, 32) bytes in this value.
    16              key_ := or(shl(248, 1), and(_ident, not(shl(248, 0xFF))))
    17          }
    18          // Localize the key with the given local context.
    19          key_ = localize(key_, _localContext);
    20      }
    21  
    22      /// @notice Localizes a given local data key for the caller's context.
    23      /// @dev The localization operation is defined as:
    24      ///      localize(k) = H(k .. sender .. local_context) & ~(0xFF << 248) | (0x01 << 248)
    25      ///      where H is the Keccak-256 hash function.
    26      /// @param _key The local data key to localize.
    27      /// @param _localContext The local context for the key.
    28      /// @return localizedKey_ The localized local data key.
    29      function localize(bytes32 _key, bytes32 _localContext) internal view returns (bytes32 localizedKey_) {
    30          assembly {
    31              // Grab the current free memory pointer to restore later.
    32              let ptr := mload(0x40)
    33              // Store the local data key and caller next to each other in memory for hashing.
    34              mstore(0, _key)
    35              mstore(0x20, caller())
    36              mstore(0x40, _localContext)
    37              // Localize the key with the above `localize` operation.
    38              localizedKey_ := or(and(keccak256(0, 0x60), not(shl(248, 0xFF))), shl(248, 1))
    39              // Restore the free memory pointer.
    40              mstore(0x40, ptr)
    41          }
    42      }
    43  
    44      /// @notice Computes and returns the key for a global keccak pre-image.
    45      /// @param _preimage The pre-image.
    46      /// @return key_ The pre-image key.
    47      function keccak256PreimageKey(bytes memory _preimage) internal pure returns (bytes32 key_) {
    48          assembly {
    49              // Grab the size of the `_preimage`
    50              let size := mload(_preimage)
    51  
    52              // Compute the pre-image keccak256 hash (aka the pre-image key)
    53              let h := keccak256(add(_preimage, 0x20), size)
    54  
    55              // Mask out prefix byte, replace with type 2 byte
    56              key_ := or(and(h, not(shl(248, 0xFF))), shl(248, 2))
    57          }
    58      }
    59  }