Commit d6f80baf authored by clabby's avatar clabby

init

parent e86703dd
...@@ -168,6 +168,19 @@ contract MIPS { ...@@ -168,6 +168,19 @@ contract MIPS {
else if (a0 == FD_PREIMAGE_READ) { else if (a0 == FD_PREIMAGE_READ) {
// verify proof 1 is correct, and get the existing memory. // verify proof 1 is correct, and get the existing memory.
uint32 mem = readMem(a1 & 0xFFffFFfc, 1); // mask the addr to align it to 4 bytes uint32 mem = readMem(a1 & 0xFFffFFfc, 1); // mask the addr to align it to 4 bytes
bytes32 preimageKey = state.preimageKey;
assembly {
// If the preimage key has a local data type, we need to hash it with the sender address
// (the dispute game) to get the context-specific key and re-set it's type byte.
if eq(byte(0, preimageKey), 1) {
// Store preimage key and caller in scratch space
mstore(0x00, preimageKey)
mstore(0x20, caller())
// Local key alteration for the sender's context:
// localize(k) = H(k .. sender) & ~(0xFF << 248) | (0x01 << 248)
preimageKey := or(and(keccak256(0x00, 0x40), not(shl(248, 0xFF))), shl(248, 0x01))
}
}
(bytes32 dat, uint256 datLen) = oracle.readPreimage(state.preimageKey, state.preimageOffset); (bytes32 dat, uint256 datLen) = oracle.readPreimage(state.preimageKey, state.preimageOffset);
// Transform data for writing to memory // Transform data for writing to memory
......
...@@ -6,10 +6,8 @@ pragma solidity ^0.8.15; ...@@ -6,10 +6,8 @@ pragma solidity ^0.8.15;
contract PreimageOracle { contract PreimageOracle {
/// @notice Mapping of pre-image keys to pre-image lengths. /// @notice Mapping of pre-image keys to pre-image lengths.
mapping(bytes32 => uint256) public preimageLengths; mapping(bytes32 => uint256) public preimageLengths;
/// @notice Mapping of pre-image keys to pre-image parts. /// @notice Mapping of pre-image keys to pre-image parts.
mapping(bytes32 => mapping(uint256 => bytes32)) public preimageParts; mapping(bytes32 => mapping(uint256 => bytes32)) public preimageParts;
/// @notice Mapping of pre-image keys to pre-image part offsets. /// @notice Mapping of pre-image keys to pre-image part offsets.
mapping(bytes32 => mapping(uint256 => bool)) public preimagePartOk; mapping(bytes32 => mapping(uint256 => bool)) public preimagePartOk;
...@@ -57,9 +55,8 @@ contract PreimageOracle { ...@@ -57,9 +55,8 @@ contract PreimageOracle {
/// @param _preimage The pre-image. /// @param _preimage The pre-image.
/// @return key_ The pre-image key. /// @return key_ The pre-image key.
function computePreimageKey(bytes calldata _preimage) external pure returns (bytes32 key_) { function computePreimageKey(bytes calldata _preimage) external pure returns (bytes32 key_) {
uint256 size;
assembly { assembly {
size := calldataload(0x24) let size := calldataload(0x24)
// Leave slots 0x40 and 0x60 untouched, // Leave slots 0x40 and 0x60 untouched,
// and everything after as scratch-memory. // and everything after as scratch-memory.
...@@ -85,34 +82,35 @@ contract PreimageOracle { ...@@ -85,34 +82,35 @@ contract PreimageOracle {
/// @param _partOffset The offset of the pre-image to read. /// @param _partOffset The offset of the pre-image to read.
/// @param _preimage The preimage data. /// @param _preimage The preimage data.
function loadKeccak256PreimagePart(uint256 _partOffset, bytes calldata _preimage) external { function loadKeccak256PreimagePart(uint256 _partOffset, bytes calldata _preimage) external {
uint256 size; (uint256 size, bytes32 key, bytes32 part) = loadPart(_partOffset, _preimage);
bytes32 key; preimagePartOk[key][_partOffset] = true;
bytes32 part; preimageParts[key][_partOffset] = part;
preimageLengths[key] = size;
}
function loadPart(uint256 _partOffset, bytes calldata _preimage) internal pure returns (uint256 size_, bytes32 key_, bytes32 part_) {
assembly { assembly {
// len(sig) + len(partOffset) + len(preimage offset) = 4 + 32 + 32 = 0x44 // len(sig) + len(partOffset) + len(preimage offset) = 4 + 32 + 32 = 0x44
size := calldataload(0x44) size_ := calldataload(0x44)
// revert if part offset > size+8 (i.e. parts must be within bounds) // revert if part offset > size+8 (i.e. parts must be within bounds)
if gt(_partOffset, add(size, 8)) { if gt(_partOffset, add(size_, 8)) {
revert(0, 0) revert(0, 0)
} }
// we leave solidity slots 0x40 and 0x60 untouched, // we leave solidity slots 0x40 and 0x60 untouched,
// and everything after as scratch-memory. // and everything after as scratch-memory.
let ptr := 0x80 let ptr := 0x80
// put size as big-endian uint64 at start of pre-image // put size as big-endian uint64 at start of pre-image
mstore(ptr, shl(192, size)) mstore(ptr, shl(192, size_))
ptr := add(ptr, 8) ptr := add(ptr, 8)
// copy preimage payload into memory so we can hash and read it. // copy preimage payload into memory so we can hash and read it.
calldatacopy(ptr, _preimage.offset, size) calldatacopy(ptr, _preimage.offset, size_)
// Note that it includes the 8-byte big-endian uint64 length prefix. // Note that it includes the 8-byte big-endian uint64 length prefix.
// this will be zero-padded at the end, since memory at end is clean. // this will be zero-padded at the end, since memory at end is clean.
part := mload(add(sub(ptr, 8), _partOffset)) part_ := mload(add(sub(ptr, 8), _partOffset))
let h := keccak256(ptr, size) // compute preimage keccak256 hash let h := keccak256(ptr, size_) // compute preimage keccak256 hash
// mask out prefix byte, replace with type 2 byte // mask out prefix byte, replace with type 2 byte
key := or(and(h, not(shl(248, 0xFF))), shl(248, 2)) key_ := or(and(h, not(shl(248, 0xFF))), shl(248, 2))
} }
preimagePartOk[key][_partOffset] = true;
preimageParts[key][_partOffset] = part;
preimageLengths[key] = size;
} }
} }
...@@ -93,7 +93,7 @@ contract DisputeGameFactory is OwnableUpgradeable, IDisputeGameFactory, Semver { ...@@ -93,7 +93,7 @@ contract DisputeGameFactory is OwnableUpgradeable, IDisputeGameFactory, Semver {
} }
// Clone the implementation contract and initialize it with the given parameters. // Clone the implementation contract and initialize it with the given parameters.
proxy = IDisputeGame(address(impl).clone(abi.encodePacked(rootClaim, extraData))); proxy = IDisputeGame(address(impl).clone(abi.encodePacked(rootClaim, extraData.length, extraData)));
proxy.initialize(); proxy.initialize();
// Compute the unique identifier for the dispute game. // Compute the unique identifier for the dispute game.
......
...@@ -334,12 +334,16 @@ contract FaultDisputeGame is IFaultDisputeGame, Clone, Semver { ...@@ -334,12 +334,16 @@ contract FaultDisputeGame is IFaultDisputeGame, Clone, Semver {
rootClaim_ = Claim.wrap(_getArgFixedBytes(0x00)); rootClaim_ = Claim.wrap(_getArgFixedBytes(0x00));
} }
/// @inheritdoc IDisputeGame
function extraDataLen() public pure returns (uint256 extraDataLen_) {
// The extra data length is in the second word of the cwia calldata.
extraDataLen_ = _getArgUint256(0x20);
}
/// @inheritdoc IDisputeGame /// @inheritdoc IDisputeGame
function extraData() public pure returns (bytes memory extraData_) { function extraData() public pure returns (bytes memory extraData_) {
// The extra data starts at the second word within the cwia calldata. // The extra data starts at the third word within the cwia calldata.
// TODO: What data do we need to pass along to this contract from the factory? extraData_ = _getArgDynBytes(0x40, uint64(extraDataLen()));
// Block hash, preimage data, etc.?
extraData_ = _getArgDynBytes(0x20, 0x20);
} }
/// @inheritdoc IDisputeGame /// @inheritdoc IDisputeGame
......
...@@ -22,17 +22,21 @@ interface IDisputeGame is IInitializable { ...@@ -22,17 +22,21 @@ interface IDisputeGame is IInitializable {
function status() external view returns (GameStatus status_); function status() external view returns (GameStatus status_);
/// @notice Getter for the game type. /// @notice Getter for the game type.
/// @dev `clones-with-immutable-args` argument #1
/// @dev The reference impl should be entirely different depending on the type (fault, validity) /// @dev The reference impl should be entirely different depending on the type (fault, validity)
/// i.e. The game type should indicate the security model. /// i.e. The game type should indicate the security model.
/// @return gameType_ The type of proof system being used. /// @return gameType_ The type of proof system being used.
function gameType() external pure returns (GameType gameType_); function gameType() external pure returns (GameType gameType_);
/// @notice Getter for the root claim. /// @notice Getter for the root claim.
/// @dev `clones-with-immutable-args` argument #2 /// @dev `clones-with-immutable-args` argument #1
/// @return rootClaim_ The root claim of the DisputeGame. /// @return rootClaim_ The root claim of the DisputeGame.
function rootClaim() external pure returns (Claim rootClaim_); function rootClaim() external pure returns (Claim rootClaim_);
/// @notice Getter for the length of the extra data.
/// @dev `clones-with-immutable-args` argument #2
/// @return extraDataLen_ The length of the `extraData`
function extraDataLen() external pure returns (uint256 extraDataLen_);
/// @notice Getter for the extra data. /// @notice Getter for the extra data.
/// @dev `clones-with-immutable-args` argument #3 /// @dev `clones-with-immutable-args` argument #3
/// @return extraData_ Any extra data supplied to the dispute game contract by the creator. /// @return extraData_ Any extra data supplied to the dispute game contract by the creator.
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment