Overview
ETH Balance
0 ETH
ETH Value
$0.00More Info
Private Name Tags
ContractCreator
Loading...
Loading
Contract Name:
ChallengeManager
Compiler Version
v0.8.9+commit.e5eed63a
Optimization Enabled:
Yes with 100 runs
Other Settings:
default evmVersion
Contract Source Code (Solidity Standard Json-Input format)
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "../libraries/DelegateCallAware.sol"; import "../osp/IOneStepProofEntry.sol"; import "../state/GlobalState.sol"; import "./IChallengeResultReceiver.sol"; import "./ChallengeLib.sol"; import "./IChallengeManager.sol"; import {NO_CHAL_INDEX} from "../libraries/Constants.sol"; contract ChallengeManager is DelegateCallAware, IChallengeManager { using GlobalStateLib for GlobalState; using MachineLib for Machine; using ChallengeLib for ChallengeLib.Challenge; enum ChallengeModeRequirement { ANY, BLOCK, EXECUTION } string private constant NO_CHAL = "NO_CHAL"; uint256 private constant MAX_CHALLENGE_DEGREE = 40; uint64 public totalChallengesCreated; mapping(uint256 => ChallengeLib.Challenge) public challenges; IChallengeResultReceiver public resultReceiver; ISequencerInbox public sequencerInbox; IBridge public bridge; IOneStepProofEntry public osp; mapping(bytes32 => IOneStepProofEntry) public ospCond; function challengeInfo(uint64 challengeIndex) external view override returns (ChallengeLib.Challenge memory) { return challenges[challengeIndex]; } modifier takeTurn( uint64 challengeIndex, ChallengeLib.SegmentSelection calldata selection, ChallengeModeRequirement expectedMode ) { ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; require(msg.sender == currentResponder(challengeIndex), "CHAL_SENDER"); require(!isTimedOut(challengeIndex), "CHAL_DEADLINE"); if (expectedMode == ChallengeModeRequirement.ANY) { require(challenge.mode != ChallengeLib.ChallengeMode.NONE, NO_CHAL); } else if (expectedMode == ChallengeModeRequirement.BLOCK) { require(challenge.mode == ChallengeLib.ChallengeMode.BLOCK, "CHAL_NOT_BLOCK"); } else if (expectedMode == ChallengeModeRequirement.EXECUTION) { require(challenge.mode == ChallengeLib.ChallengeMode.EXECUTION, "CHAL_NOT_EXECUTION"); } else { assert(false); } require( challenge.challengeStateHash == ChallengeLib.hashChallengeState( selection.oldSegmentsStart, selection.oldSegmentsLength, selection.oldSegments ), "BIS_STATE" ); if ( selection.oldSegments.length < 2 || selection.challengePosition >= selection.oldSegments.length - 1 ) { revert("BAD_CHALLENGE_POS"); } _; if (challenge.mode == ChallengeLib.ChallengeMode.NONE) { // Early return since challenge must have terminated return; } ChallengeLib.Participant memory current = challenge.current; current.timeLeft -= block.timestamp - challenge.lastMoveTimestamp; challenge.current = challenge.next; challenge.next = current; challenge.lastMoveTimestamp = block.timestamp; } function initialize( IChallengeResultReceiver resultReceiver_, ISequencerInbox sequencerInbox_, IBridge bridge_, IOneStepProofEntry osp_ ) external override onlyDelegated { require(address(resultReceiver) == address(0), "ALREADY_INIT"); require(address(resultReceiver_) != address(0), "NO_RESULT_RECEIVER"); resultReceiver = resultReceiver_; sequencerInbox = sequencerInbox_; bridge = bridge_; osp = osp_; } /// @dev A osp breaking change is introduced as part of Stylus upgrade, where the new osp would not support /// pre-Stylus legacy wasmModuleRoot. To ensure that the new osp is not used for legacy wasmModuleRoot, /// we introduce a conditional OSP where condRoot should be set to the pre-Stylus root and condOsp should /// be set to the pre-Stylus osp. The correct value should be handled by the upgrade action contract. function postUpgradeInit( IOneStepProofEntry osp_, bytes32 condRoot, IOneStepProofEntry condOsp ) external onlyDelegated onlyProxyOwner { ospCond[condRoot] = condOsp; osp = osp_; } function getOsp(bytes32 wasmModuleRoot) public view returns (IOneStepProofEntry) { IOneStepProofEntry t = ospCond[wasmModuleRoot]; if (address(t) == address(0)) { return osp; } else { return t; } } function createChallenge( bytes32 wasmModuleRoot_, MachineStatus[2] calldata startAndEndMachineStatuses_, GlobalState[2] calldata startAndEndGlobalStates_, uint64 numBlocks, address asserter_, address challenger_, uint256 asserterTimeLeft_, uint256 challengerTimeLeft_ ) external override returns (uint64) { require(msg.sender == address(resultReceiver), "ONLY_ROLLUP_CHAL"); bytes32[] memory segments = new bytes32[](2); segments[0] = ChallengeLib.blockStateHash( startAndEndMachineStatuses_[0], startAndEndGlobalStates_[0].hash() ); segments[1] = ChallengeLib.blockStateHash( startAndEndMachineStatuses_[1], startAndEndGlobalStates_[1].hash() ); uint64 challengeIndex = ++totalChallengesCreated; // The following is an assertion since it should never be possible, but it's an important invariant assert(challengeIndex != NO_CHAL_INDEX); ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; challenge.wasmModuleRoot = wasmModuleRoot_; // See validator/assertion.go ExecutionState RequiredBatches() for reasoning uint64 maxInboxMessagesRead = startAndEndGlobalStates_[1].getInboxPosition(); if ( startAndEndMachineStatuses_[1] == MachineStatus.ERRORED || startAndEndGlobalStates_[1].getPositionInMessage() > 0 ) { maxInboxMessagesRead++; } challenge.maxInboxMessages = maxInboxMessagesRead; challenge.next = ChallengeLib.Participant({addr: asserter_, timeLeft: asserterTimeLeft_}); challenge.current = ChallengeLib.Participant({ addr: challenger_, timeLeft: challengerTimeLeft_ }); challenge.lastMoveTimestamp = block.timestamp; challenge.mode = ChallengeLib.ChallengeMode.BLOCK; emit InitiatedChallenge( challengeIndex, startAndEndGlobalStates_[0], startAndEndGlobalStates_[1] ); completeBisection(challengeIndex, 0, numBlocks, segments); return challengeIndex; } /** * @notice Initiate the next round in the bisection by objecting to execution correctness with a bisection * of an execution segment with the same length but a different endpoint. This is either the initial move * or follows another execution objection */ function bisectExecution( uint64 challengeIndex, ChallengeLib.SegmentSelection calldata selection, bytes32[] calldata newSegments ) external takeTurn(challengeIndex, selection, ChallengeModeRequirement.ANY) { (uint256 challengeStart, uint256 challengeLength) = ChallengeLib.extractChallengeSegment( selection ); require(challengeLength > 1, "TOO_SHORT"); { uint256 expectedDegree = challengeLength; if (expectedDegree > MAX_CHALLENGE_DEGREE) { expectedDegree = MAX_CHALLENGE_DEGREE; } require(newSegments.length == expectedDegree + 1, "WRONG_DEGREE"); } requireValidBisection(selection, newSegments[0], newSegments[newSegments.length - 1]); completeBisection(challengeIndex, challengeStart, challengeLength, newSegments); } function challengeExecution( uint64 challengeIndex, ChallengeLib.SegmentSelection calldata selection, MachineStatus[2] calldata machineStatuses, bytes32[2] calldata globalStateHashes, uint256 numSteps ) external takeTurn(challengeIndex, selection, ChallengeModeRequirement.BLOCK) { require(numSteps >= 1, "CHALLENGE_TOO_SHORT"); require(numSteps <= OneStepProofEntryLib.MAX_STEPS, "CHALLENGE_TOO_LONG"); requireValidBisection( selection, ChallengeLib.blockStateHash(machineStatuses[0], globalStateHashes[0]), ChallengeLib.blockStateHash(machineStatuses[1], globalStateHashes[1]) ); ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; (uint256 executionChallengeAtSteps, uint256 challengeLength) = ChallengeLib .extractChallengeSegment(selection); require(challengeLength == 1, "TOO_LONG"); if (machineStatuses[0] != MachineStatus.FINISHED) { // If the machine is in a halted state, it can't change require( machineStatuses[0] == machineStatuses[1] && globalStateHashes[0] == globalStateHashes[1], "HALTED_CHANGE" ); _currentWin(challengeIndex, ChallengeTerminationType.BLOCK_PROOF); return; } if (machineStatuses[1] == MachineStatus.ERRORED) { // If the machine errors, it must return to the previous global state require(globalStateHashes[0] == globalStateHashes[1], "ERROR_CHANGE"); } bytes32[] memory segments = new bytes32[](2); IOneStepProofEntry _osp = getOsp(challenge.wasmModuleRoot); segments[0] = _osp.getStartMachineHash(globalStateHashes[0], challenge.wasmModuleRoot); segments[1] = _osp.getEndMachineHash(machineStatuses[1], globalStateHashes[1]); challenge.mode = ChallengeLib.ChallengeMode.EXECUTION; completeBisection(challengeIndex, 0, numSteps, segments); emit ExecutionChallengeBegun(challengeIndex, executionChallengeAtSteps); } function oneStepProveExecution( uint64 challengeIndex, ChallengeLib.SegmentSelection calldata selection, bytes calldata proof ) external takeTurn(challengeIndex, selection, ChallengeModeRequirement.EXECUTION) { ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; uint256 challengeStart; { uint256 challengeLength; (challengeStart, challengeLength) = ChallengeLib.extractChallengeSegment(selection); require(challengeLength == 1, "TOO_LONG"); } bytes32 afterHash = getOsp(challenge.wasmModuleRoot).proveOneStep( ExecutionContext({maxInboxMessagesRead: challenge.maxInboxMessages, bridge: bridge}), challengeStart, selection.oldSegments[selection.challengePosition], proof ); require( afterHash != selection.oldSegments[selection.challengePosition + 1], "SAME_OSP_END" ); emit OneStepProofCompleted(challengeIndex); _currentWin(challengeIndex, ChallengeTerminationType.EXECUTION_PROOF); } function timeout(uint64 challengeIndex) external override { require(challenges[challengeIndex].mode != ChallengeLib.ChallengeMode.NONE, NO_CHAL); require(isTimedOut(challengeIndex), "TIMEOUT_DEADLINE"); _nextWin(challengeIndex, ChallengeTerminationType.TIMEOUT); } function clearChallenge(uint64 challengeIndex) external override { require(msg.sender == address(resultReceiver), "NOT_RES_RECEIVER"); require(challenges[challengeIndex].mode != ChallengeLib.ChallengeMode.NONE, NO_CHAL); delete challenges[challengeIndex]; emit ChallengeEnded(challengeIndex, ChallengeTerminationType.CLEARED); } function currentResponder(uint64 challengeIndex) public view override returns (address) { return challenges[challengeIndex].current.addr; } function isTimedOut(uint64 challengeIndex) public view virtual override returns (bool) { return challenges[challengeIndex].isTimedOut(); } function requireValidBisection( ChallengeLib.SegmentSelection calldata selection, bytes32 startHash, bytes32 endHash ) private pure { require(selection.oldSegments[selection.challengePosition] == startHash, "WRONG_START"); require(selection.oldSegments[selection.challengePosition + 1] != endHash, "SAME_END"); } function completeBisection( uint64 challengeIndex, uint256 challengeStart, uint256 challengeLength, bytes32[] memory newSegments ) private { assert(challengeLength >= 1); assert(newSegments.length >= 2); bytes32 challengeStateHash = ChallengeLib.hashChallengeState( challengeStart, challengeLength, newSegments ); challenges[challengeIndex].challengeStateHash = challengeStateHash; emit Bisected( challengeIndex, challengeStateHash, challengeStart, challengeLength, newSegments ); } /// @dev This function causes the mode of the challenge to be set to NONE by deleting the challenge function _nextWin(uint64 challengeIndex, ChallengeTerminationType reason) private { ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; address next = challenge.next.addr; address current = challenge.current.addr; delete challenges[challengeIndex]; resultReceiver.completeChallenge(challengeIndex, next, current); emit ChallengeEnded(challengeIndex, reason); } /** * @dev this currently sets a challenge hash of 0 - no move is possible for the next participant to progress the * state. It is assumed that wherever this function is consumed, the turn is then adjusted for the opposite party * to timeout. This is done as a safety measure so challenges can only be resolved by timeouts during mainnet beta. */ function _currentWin( uint64 challengeIndex, ChallengeTerminationType /* reason */ ) private { ChallengeLib.Challenge storage challenge = challenges[challengeIndex]; challenge.challengeStateHash = bytes32(0); // address next = challenge.next.addr; // address current = challenge.current.addr; // delete challenges[challengeIndex]; // resultReceiver.completeChallenge(challengeIndex, current, next); // emit ChallengeEnded(challengeIndex, reason); } }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 // solhint-disable-next-line compiler-version pragma solidity >=0.6.9 <0.9.0; import "./IOwnable.sol"; interface IBridge { /// @dev This is an instruction to offchain readers to inform them where to look /// for sequencer inbox batch data. This is not the type of data (eg. das, brotli encoded, or blob versioned hash) /// and this enum is not used in the state transition function, rather it informs an offchain /// reader where to find the data so that they can supply it to the replay binary enum BatchDataLocation { /// @notice The data can be found in the transaction call data TxInput, /// @notice The data can be found in an event emitted during the transaction SeparateBatchEvent, /// @notice This batch contains no data NoData, /// @notice The data can be found in the 4844 data blobs on this transaction Blob } struct TimeBounds { uint64 minTimestamp; uint64 maxTimestamp; uint64 minBlockNumber; uint64 maxBlockNumber; } event MessageDelivered( uint256 indexed messageIndex, bytes32 indexed beforeInboxAcc, address inbox, uint8 kind, address sender, bytes32 messageDataHash, uint256 baseFeeL1, uint64 timestamp ); event BridgeCallTriggered( address indexed outbox, address indexed to, uint256 value, bytes data ); event InboxToggle(address indexed inbox, bool enabled); event OutboxToggle(address indexed outbox, bool enabled); event SequencerInboxUpdated(address newSequencerInbox); event RollupUpdated(address rollup); function allowedDelayedInboxList(uint256) external returns (address); function allowedOutboxList(uint256) external returns (address); /// @dev Accumulator for delayed inbox messages; tail represents hash of the current state; each element represents the inclusion of a new message. function delayedInboxAccs(uint256) external view returns (bytes32); /// @dev Accumulator for sequencer inbox messages; tail represents hash of the current state; each element represents the inclusion of a new message. function sequencerInboxAccs(uint256) external view returns (bytes32); function rollup() external view returns (IOwnable); function sequencerInbox() external view returns (address); function activeOutbox() external view returns (address); function allowedDelayedInboxes(address inbox) external view returns (bool); function allowedOutboxes(address outbox) external view returns (bool); function sequencerReportedSubMessageCount() external view returns (uint256); function executeCall( address to, uint256 value, bytes calldata data ) external returns (bool success, bytes memory returnData); function delayedMessageCount() external view returns (uint256); function sequencerMessageCount() external view returns (uint256); // ---------- onlySequencerInbox functions ---------- function enqueueSequencerMessage( bytes32 dataHash, uint256 afterDelayedMessagesRead, uint256 prevMessageCount, uint256 newMessageCount ) external returns ( uint256 seqMessageIndex, bytes32 beforeAcc, bytes32 delayedAcc, bytes32 acc ); /** * @dev Allows the sequencer inbox to submit a delayed message of the batchPostingReport type * This is done through a separate function entrypoint instead of allowing the sequencer inbox * to call `enqueueDelayedMessage` to avoid the gas overhead of an extra SLOAD in either * every delayed inbox or every sequencer inbox call. */ function submitBatchSpendingReport(address batchPoster, bytes32 dataHash) external returns (uint256 msgNum); // ---------- onlyRollupOrOwner functions ---------- function setSequencerInbox(address _sequencerInbox) external; function setDelayedInbox(address inbox, bool enabled) external; function setOutbox(address inbox, bool enabled) external; function updateRollupAddress(IOwnable _rollup) external; }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 // solhint-disable-next-line compiler-version pragma solidity >=0.6.9 <0.9.0; interface IDelayedMessageProvider { /// @dev event emitted when a inbox message is added to the Bridge's delayed accumulator event InboxMessageDelivered(uint256 indexed messageNum, bytes data); /// @dev event emitted when a inbox message is added to the Bridge's delayed accumulator /// same as InboxMessageDelivered but the batch data is available in tx.input event InboxMessageDeliveredFromOrigin(uint256 indexed messageNum); }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 // solhint-disable-next-line compiler-version pragma solidity >=0.4.21 <0.9.0; interface IOwnable { function owner() external view returns (address); }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 // solhint-disable-next-line compiler-version pragma solidity >=0.6.9 <0.9.0; pragma experimental ABIEncoderV2; import "../libraries/IGasRefunder.sol"; import "./IDelayedMessageProvider.sol"; import "./IBridge.sol"; interface ISequencerInbox is IDelayedMessageProvider { struct MaxTimeVariation { uint256 delayBlocks; uint256 futureBlocks; uint256 delaySeconds; uint256 futureSeconds; } event SequencerBatchDelivered( uint256 indexed batchSequenceNumber, bytes32 indexed beforeAcc, bytes32 indexed afterAcc, bytes32 delayedAcc, uint256 afterDelayedMessagesRead, IBridge.TimeBounds timeBounds, IBridge.BatchDataLocation dataLocation ); event OwnerFunctionCalled(uint256 indexed id); /// @dev a separate event that emits batch data when this isn't easily accessible in the tx.input event SequencerBatchData(uint256 indexed batchSequenceNumber, bytes data); /// @dev a valid keyset was added event SetValidKeyset(bytes32 indexed keysetHash, bytes keysetBytes); /// @dev a keyset was invalidated event InvalidateKeyset(bytes32 indexed keysetHash); function totalDelayedMessagesRead() external view returns (uint256); function bridge() external view returns (IBridge); /// @dev The size of the batch header // solhint-disable-next-line func-name-mixedcase function HEADER_LENGTH() external view returns (uint256); /// @dev If the first batch data byte after the header has this bit set, /// the sequencer inbox has authenticated the data. Currently only used for 4844 blob support. /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function DATA_AUTHENTICATED_FLAG() external view returns (bytes1); /// @dev If the first data byte after the header has this bit set, /// then the batch data is to be found in 4844 data blobs /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function DATA_BLOB_HEADER_FLAG() external view returns (bytes1); /// @dev If the first data byte after the header has this bit set, /// then the batch data is a das message /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function DAS_MESSAGE_HEADER_FLAG() external view returns (bytes1); /// @dev If the first data byte after the header has this bit set, /// then the batch data is a das message that employs a merklesization strategy /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function TREE_DAS_MESSAGE_HEADER_FLAG() external view returns (bytes1); /// @dev If the first data byte after the header has this bit set, /// then the batch data has been brotli compressed /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function BROTLI_MESSAGE_HEADER_FLAG() external view returns (bytes1); /// @dev If the first data byte after the header has this bit set, /// then the batch data uses a zero heavy encoding /// See: https://github.com/OffchainLabs/nitro/blob/69de0603abf6f900a4128cab7933df60cad54ded/arbstate/das_reader.go // solhint-disable-next-line func-name-mixedcase function ZERO_HEAVY_MESSAGE_HEADER_FLAG() external view returns (bytes1); function rollup() external view returns (IOwnable); function isBatchPoster(address) external view returns (bool); function isSequencer(address) external view returns (bool); function maxDataSize() external view returns (uint256); /// @notice The batch poster manager has the ability to change the batch poster addresses /// This enables the batch poster to do key rotation function batchPosterManager() external view returns (address); struct DasKeySetInfo { bool isValidKeyset; uint64 creationBlock; } /// @dev returns 4 uint256 to be compatible with older version function maxTimeVariation() external view returns ( uint256 delayBlocks, uint256 futureBlocks, uint256 delaySeconds, uint256 futureSeconds ); function dasKeySetInfo(bytes32) external view returns (bool, uint64); /// @notice Remove force inclusion delay after a L1 chainId fork function removeDelayAfterFork() external; /// @notice Force messages from the delayed inbox to be included in the chain /// Callable by any address, but message can only be force-included after maxTimeVariation.delayBlocks and /// maxTimeVariation.delaySeconds has elapsed. As part of normal behaviour the sequencer will include these /// messages so it's only necessary to call this if the sequencer is down, or not including any delayed messages. /// @param _totalDelayedMessagesRead The total number of messages to read up to /// @param kind The kind of the last message to be included /// @param l1BlockAndTime The l1 block and the l1 timestamp of the last message to be included /// @param baseFeeL1 The l1 gas price of the last message to be included /// @param sender The sender of the last message to be included /// @param messageDataHash The messageDataHash of the last message to be included function forceInclusion( uint256 _totalDelayedMessagesRead, uint8 kind, uint64[2] calldata l1BlockAndTime, uint256 baseFeeL1, address sender, bytes32 messageDataHash ) external; function inboxAccs(uint256 index) external view returns (bytes32); function batchCount() external view returns (uint256); function isValidKeysetHash(bytes32 ksHash) external view returns (bool); /// @notice the creation block is intended to still be available after a keyset is deleted function getKeysetCreationBlock(bytes32 ksHash) external view returns (uint256); // ---------- BatchPoster functions ---------- function addSequencerL2BatchFromOrigin( uint256 sequenceNumber, bytes calldata data, uint256 afterDelayedMessagesRead, IGasRefunder gasRefunder ) external; function addSequencerL2BatchFromOrigin( uint256 sequenceNumber, bytes calldata data, uint256 afterDelayedMessagesRead, IGasRefunder gasRefunder, uint256 prevMessageCount, uint256 newMessageCount ) external; function addSequencerL2Batch( uint256 sequenceNumber, bytes calldata data, uint256 afterDelayedMessagesRead, IGasRefunder gasRefunder, uint256 prevMessageCount, uint256 newMessageCount ) external; function addSequencerL2BatchFromBlobs( uint256 sequenceNumber, uint256 afterDelayedMessagesRead, IGasRefunder gasRefunder, uint256 prevMessageCount, uint256 newMessageCount ) external; // ---------- onlyRollupOrOwner functions ---------- /** * @notice Set max delay for sequencer inbox * @param maxTimeVariation_ the maximum time variation parameters */ function setMaxTimeVariation(MaxTimeVariation memory maxTimeVariation_) external; /** * @notice Updates whether an address is authorized to be a batch poster at the sequencer inbox * @param addr the address * @param isBatchPoster_ if the specified address should be authorized as a batch poster */ function setIsBatchPoster(address addr, bool isBatchPoster_) external; /** * @notice Makes Data Availability Service keyset valid * @param keysetBytes bytes of the serialized keyset */ function setValidKeyset(bytes calldata keysetBytes) external; /** * @notice Invalidates a Data Availability Service keyset * @param ksHash hash of the keyset */ function invalidateKeysetHash(bytes32 ksHash) external; /** * @notice Updates whether an address is authorized to be a sequencer. * @dev The IsSequencer information is used only off-chain by the nitro node to validate sequencer feed signer. * @param addr the address * @param isSequencer_ if the specified address should be authorized as a sequencer */ function setIsSequencer(address addr, bool isSequencer_) external; /** * @notice Updates the batch poster manager, the address which has the ability to rotate batch poster keys * @param newBatchPosterManager The new batch poster manager to be set */ function setBatchPosterManager(address newBatchPosterManager) external; /// @notice Allows the rollup owner to sync the rollup address function updateRollupAddress() external; // ---------- initializer ---------- function initialize(IBridge bridge_, MaxTimeVariation calldata maxTimeVariation_) external; }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "../state/Machine.sol"; import "../state/GlobalState.sol"; library ChallengeLib { using MachineLib for Machine; using ChallengeLib for Challenge; /// @dev It's assumed that that uninitialzed challenges have mode NONE enum ChallengeMode { NONE, BLOCK, EXECUTION } struct Participant { address addr; uint256 timeLeft; } struct Challenge { Participant current; Participant next; uint256 lastMoveTimestamp; bytes32 wasmModuleRoot; bytes32 challengeStateHash; uint64 maxInboxMessages; ChallengeMode mode; } struct SegmentSelection { uint256 oldSegmentsStart; uint256 oldSegmentsLength; bytes32[] oldSegments; uint256 challengePosition; } function timeUsedSinceLastMove(Challenge storage challenge) internal view returns (uint256) { return block.timestamp - challenge.lastMoveTimestamp; } function isTimedOut(Challenge storage challenge) internal view returns (bool) { return challenge.timeUsedSinceLastMove() > challenge.current.timeLeft; } function extractChallengeSegment(SegmentSelection calldata selection) internal pure returns (uint256 segmentStart, uint256 segmentLength) { uint256 oldChallengeDegree = selection.oldSegments.length - 1; segmentLength = selection.oldSegmentsLength / oldChallengeDegree; // Intentionally done before challengeLength is potentially added to for the final segment segmentStart = selection.oldSegmentsStart + segmentLength * selection.challengePosition; if (selection.challengePosition == selection.oldSegments.length - 2) { segmentLength += selection.oldSegmentsLength % oldChallengeDegree; } } function hashChallengeState( uint256 segmentsStart, uint256 segmentsLength, bytes32[] memory segments ) internal pure returns (bytes32) { return keccak256(abi.encodePacked(segmentsStart, segmentsLength, segments)); } function blockStateHash(MachineStatus status, bytes32 globalStateHash) internal pure returns (bytes32) { if (status == MachineStatus.FINISHED) { return keccak256(abi.encodePacked("Block state:", globalStateHash)); } else if (status == MachineStatus.ERRORED) { return keccak256(abi.encodePacked("Block state, errored:", globalStateHash)); } else if (status == MachineStatus.TOO_FAR) { return keccak256(abi.encodePacked("Block state, too far:")); } else { revert("BAD_BLOCK_STATUS"); } } }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "../state/Machine.sol"; import "../bridge/IBridge.sol"; import "../bridge/ISequencerInbox.sol"; import "../osp/IOneStepProofEntry.sol"; import "./IChallengeResultReceiver.sol"; import "./ChallengeLib.sol"; interface IChallengeManager { enum ChallengeTerminationType { TIMEOUT, BLOCK_PROOF, EXECUTION_PROOF, CLEARED } event InitiatedChallenge( uint64 indexed challengeIndex, GlobalState startState, GlobalState endState ); event Bisected( uint64 indexed challengeIndex, bytes32 indexed challengeRoot, uint256 challengedSegmentStart, uint256 challengedSegmentLength, bytes32[] chainHashes ); event ExecutionChallengeBegun(uint64 indexed challengeIndex, uint256 blockSteps); event OneStepProofCompleted(uint64 indexed challengeIndex); event ChallengeEnded(uint64 indexed challengeIndex, ChallengeTerminationType kind); function initialize( IChallengeResultReceiver resultReceiver_, ISequencerInbox sequencerInbox_, IBridge bridge_, IOneStepProofEntry osp_ ) external; function postUpgradeInit( IOneStepProofEntry osp_, bytes32 condRoot, IOneStepProofEntry condOsp ) external; /// @notice Get the default osp, which is used for all wasm module roots that don't have a conditional OSP set /// Use getOsp(wasmModuleRoot) to get the OSP for a specific wasm module root function osp() external view returns (IOneStepProofEntry); /// @notice Get the OSP for a given wasm module root function getOsp(bytes32 wasmModuleRoot) external view returns (IOneStepProofEntry); function createChallenge( bytes32 wasmModuleRoot_, MachineStatus[2] calldata startAndEndMachineStatuses_, GlobalState[2] calldata startAndEndGlobalStates_, uint64 numBlocks, address asserter_, address challenger_, uint256 asserterTimeLeft_, uint256 challengerTimeLeft_ ) external returns (uint64); function challengeInfo(uint64 challengeIndex_) external view returns (ChallengeLib.Challenge memory); function currentResponder(uint64 challengeIndex) external view returns (address); function isTimedOut(uint64 challengeIndex) external view returns (bool); function clearChallenge(uint64 challengeIndex_) external; function timeout(uint64 challengeIndex_) external; }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; interface IChallengeResultReceiver { function completeChallenge( uint256 challengeIndex, address winner, address loser ) external; }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.4; uint64 constant NO_CHAL_INDEX = 0; // Expected seconds per block in Ethereum PoS uint256 constant ETH_POS_BLOCK_TIME = 12; /// @dev If nativeTokenDecimals is different than 18 decimals, bridge will inflate or deflate token amounts /// when depositing to child chain to match 18 decimal denomination. Opposite process happens when /// amount is withdrawn back to parent chain. In order to avoid uint256 overflows we restrict max number /// of decimals to 36 which should be enough for most practical use-cases. uint8 constant MAX_ALLOWED_NATIVE_TOKEN_DECIMALS = uint8(36); /// @dev Max amount of erc20 native token that can deposit when upscaling is required (i.e. < 18 decimals) /// Amounts higher than this would risk uint256 overflows when adjusting decimals. Considering /// 18 decimals are 60 bits, we choose 2^192 as the limit which equals to ~6.3*10^57 weis of token uint256 constant MAX_UPSCALE_AMOUNT = type(uint192).max;
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import {NotOwner} from "./Error.sol"; /// @dev A stateless contract that allows you to infer if the current call has been delegated or not /// Pattern used here is from UUPS implementation by the OpenZeppelin team abstract contract DelegateCallAware { address private immutable __self = address(this); /** * @dev Check that the execution is being performed through a delegate call. This allows a function to be * callable on the proxy contract but not on the logic contract. */ modifier onlyDelegated() { require(address(this) != __self, "Function must be called through delegatecall"); _; } /** * @dev Check that the execution is not being performed through a delegate call. This allows a function to be * callable on the implementing contract but not through proxies. */ modifier notDelegated() { require(address(this) == __self, "Function must not be called through delegatecall"); _; } /// @dev Check that msg.sender is the current EIP 1967 proxy admin modifier onlyProxyOwner() { // Storage slot with the admin of the proxy contract // This is the keccak-256 hash of "eip1967.proxy.admin" subtracted by 1 bytes32 slot = 0xb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d6103; address admin; assembly { admin := sload(slot) } if (msg.sender != admin) revert NotOwner(msg.sender, admin); _; } }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.4; /// @dev Init was already called error AlreadyInit(); /// @dev Init was called with param set to zero that must be nonzero error HadZeroInit(); /// @dev Thrown when post upgrade init validation fails error BadPostUpgradeInit(); /// @dev Thrown when the caller is not a codeless origin error NotCodelessOrigin(); /// @dev Thrown when non owner tries to access an only-owner function /// @param sender The msg.sender who is not the owner /// @param owner The owner address error NotOwner(address sender, address owner); /// @dev Thrown when an address that is not the rollup tries to call an only-rollup function /// @param sender The sender who is not the rollup /// @param rollup The rollup address authorized to call this function error NotRollup(address sender, address rollup); /// @dev Thrown when the contract was not called directly from the origin ie msg.sender != tx.origin error NotOrigin(); /// @dev Provided data was too large /// @param dataLength The length of the data that is too large /// @param maxDataLength The max length the data can be error DataTooLarge(uint256 dataLength, uint256 maxDataLength); /// @dev The provided is not a contract and was expected to be /// @param addr The adddress in question error NotContract(address addr); /// @dev The merkle proof provided was too long /// @param actualLength The length of the merkle proof provided /// @param maxProofLength The max length a merkle proof can have error MerkleProofTooLong(uint256 actualLength, uint256 maxProofLength); /// @dev Thrown when an un-authorized address tries to access an admin function /// @param sender The un-authorized sender /// @param rollup The rollup, which would be authorized /// @param owner The rollup's owner, which would be authorized error NotRollupOrOwner(address sender, address rollup, address owner); // Bridge Errors /// @dev Thrown when an un-authorized address tries to access an only-inbox function /// @param sender The un-authorized sender error NotDelayedInbox(address sender); /// @dev Thrown when an un-authorized address tries to access an only-sequencer-inbox function /// @param sender The un-authorized sender error NotSequencerInbox(address sender); /// @dev Thrown when an un-authorized address tries to access an only-outbox function /// @param sender The un-authorized sender error NotOutbox(address sender); /// @dev the provided outbox address isn't valid /// @param outbox address of outbox being set error InvalidOutboxSet(address outbox); /// @dev The provided token address isn't valid /// @param token address of token being set error InvalidTokenSet(address token); /// @dev Call to this specific address is not allowed /// @param target address of the call receiver error CallTargetNotAllowed(address target); /// @dev Call that changes the balance of ERC20Bridge is not allowed error CallNotAllowed(); // Inbox Errors /// @dev msg.value sent to the inbox isn't high enough error InsufficientValue(uint256 expected, uint256 actual); /// @dev submission cost provided isn't enough to create retryable ticket error InsufficientSubmissionCost(uint256 expected, uint256 actual); /// @dev address not allowed to interact with the given contract error NotAllowedOrigin(address origin); /// @dev used to convey retryable tx data in eth calls without requiring a tx trace /// this follows a pattern similar to EIP-3668 where reverts surface call information error RetryableData( address from, address to, uint256 l2CallValue, uint256 deposit, uint256 maxSubmissionCost, address excessFeeRefundAddress, address callValueRefundAddress, uint256 gasLimit, uint256 maxFeePerGas, bytes data ); /// @dev Thrown when a L1 chainId fork is detected error L1Forked(); /// @dev Thrown when a L1 chainId fork is not detected error NotForked(); /// @dev The provided gasLimit is larger than uint64 error GasLimitTooLarge(); /// @dev The provided amount cannot be adjusted to 18 decimals due to overflow error AmountTooLarge(uint256 amount); /// @dev Number of native token's decimals is restricted to enable conversions to 18 decimals error NativeTokenDecimalsTooLarge(uint256 decimals); // Outbox Errors /// @dev The provided proof was too long /// @param proofLength The length of the too-long proof error ProofTooLong(uint256 proofLength); /// @dev The output index was greater than the maximum /// @param index The output index /// @param maxIndex The max the index could be error PathNotMinimal(uint256 index, uint256 maxIndex); /// @dev The calculated root does not exist /// @param root The calculated root error UnknownRoot(bytes32 root); /// @dev The record has already been spent /// @param index The index of the spent record error AlreadySpent(uint256 index); /// @dev A call to the bridge failed with no return data error BridgeCallFailed(); // Sequencer Inbox Errors /// @dev Thrown when someone attempts to read fewer messages than have already been read error DelayedBackwards(); /// @dev Thrown when someone attempts to read more messages than exist error DelayedTooFar(); /// @dev Force include can only read messages more blocks old than the delay period error ForceIncludeBlockTooSoon(); /// @dev Force include can only read messages more seconds old than the delay period error ForceIncludeTimeTooSoon(); /// @dev The message provided did not match the hash in the delayed inbox error IncorrectMessagePreimage(); /// @dev This can only be called by the batch poster error NotBatchPoster(); /// @dev The sequence number provided to this message was inconsistent with the number of batches already included error BadSequencerNumber(uint256 stored, uint256 received); /// @dev The sequence message number provided to this message was inconsistent with the previous one error BadSequencerMessageNumber(uint256 stored, uint256 received); /// @dev Tried to create an already valid Data Availability Service keyset error AlreadyValidDASKeyset(bytes32); /// @dev Tried to use or invalidate an already invalid Data Availability Service keyset error NoSuchKeyset(bytes32); /// @dev Thrown when the provided address is not the designated batch poster manager error NotBatchPosterManager(address); /// @dev Thrown when a data blob feature is attempted to be used on a chain that doesnt support it error DataBlobsNotSupported(); /// @dev Thrown when an init param was supplied as empty error InitParamZero(string name); /// @dev Thrown when data hashes where expected but not where present on the tx error MissingDataHashes(); /// @dev Thrown when rollup is not updated with updateRollupAddress error RollupNotChanged(); /// @dev Unsupported header flag was provided error InvalidHeaderFlag(bytes1); /// @dev SequencerInbox and Bridge are not in the same feeToken/ETH mode error NativeTokenMismatch(); /// @dev Thrown when a deprecated function is called error Deprecated(); /// @dev Thrown when any component of maxTimeVariation is over uint64 error BadMaxTimeVariation();
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 // solhint-disable-next-line compiler-version pragma solidity >=0.6.9 <0.9.0; interface IGasRefunder { function onGasSpent( address payable spender, uint256 gasUsed, uint256 calldataSize ) external returns (bool success); }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./IOneStepProver.sol"; library OneStepProofEntryLib { uint256 internal constant MAX_STEPS = 1 << 43; } interface IOneStepProofEntry { function getStartMachineHash(bytes32 globalStateHash, bytes32 wasmModuleRoot) external pure returns (bytes32); function getEndMachineHash(MachineStatus status, bytes32 globalStateHash) external pure returns (bytes32); function proveOneStep( ExecutionContext calldata execCtx, uint256 machineStep, bytes32 beforeHash, bytes calldata proof ) external view returns (bytes32 afterHash); }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "../state/Machine.sol"; import "../state/Module.sol"; import "../state/Instructions.sol"; import "../state/GlobalState.sol"; import "../bridge/ISequencerInbox.sol"; import "../bridge/IBridge.sol"; struct ExecutionContext { uint256 maxInboxMessagesRead; IBridge bridge; } abstract contract IOneStepProver { function executeOneStep( ExecutionContext memory execCtx, Machine calldata mach, Module calldata mod, Instruction calldata instruction, bytes calldata proof ) external view virtual returns (Machine memory result, Module memory resultMod); }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; struct GlobalState { bytes32[2] bytes32Vals; uint64[2] u64Vals; } library GlobalStateLib { uint16 internal constant BYTES32_VALS_NUM = 2; uint16 internal constant U64_VALS_NUM = 2; function hash(GlobalState memory state) internal pure returns (bytes32) { return keccak256( abi.encodePacked( "Global state:", state.bytes32Vals[0], state.bytes32Vals[1], state.u64Vals[0], state.u64Vals[1] ) ); } function getBlockHash(GlobalState memory state) internal pure returns (bytes32) { return state.bytes32Vals[0]; } function getSendRoot(GlobalState memory state) internal pure returns (bytes32) { return state.bytes32Vals[1]; } function getInboxPosition(GlobalState memory state) internal pure returns (uint64) { return state.u64Vals[0]; } function getPositionInMessage(GlobalState memory state) internal pure returns (uint64) { return state.u64Vals[1]; } function isEmpty(GlobalState calldata state) internal pure returns (bool) { return (state.bytes32Vals[0] == bytes32(0) && state.bytes32Vals[1] == bytes32(0) && state.u64Vals[0] == 0 && state.u64Vals[1] == 0); } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; struct Instruction { uint16 opcode; uint256 argumentData; } library Instructions { uint16 internal constant UNREACHABLE = 0x00; uint16 internal constant NOP = 0x01; uint16 internal constant RETURN = 0x0F; uint16 internal constant CALL = 0x10; uint16 internal constant CALL_INDIRECT = 0x11; uint16 internal constant LOCAL_GET = 0x20; uint16 internal constant LOCAL_SET = 0x21; uint16 internal constant GLOBAL_GET = 0x23; uint16 internal constant GLOBAL_SET = 0x24; uint16 internal constant I32_LOAD = 0x28; uint16 internal constant I64_LOAD = 0x29; uint16 internal constant F32_LOAD = 0x2A; uint16 internal constant F64_LOAD = 0x2B; uint16 internal constant I32_LOAD8_S = 0x2C; uint16 internal constant I32_LOAD8_U = 0x2D; uint16 internal constant I32_LOAD16_S = 0x2E; uint16 internal constant I32_LOAD16_U = 0x2F; uint16 internal constant I64_LOAD8_S = 0x30; uint16 internal constant I64_LOAD8_U = 0x31; uint16 internal constant I64_LOAD16_S = 0x32; uint16 internal constant I64_LOAD16_U = 0x33; uint16 internal constant I64_LOAD32_S = 0x34; uint16 internal constant I64_LOAD32_U = 0x35; uint16 internal constant I32_STORE = 0x36; uint16 internal constant I64_STORE = 0x37; uint16 internal constant F32_STORE = 0x38; uint16 internal constant F64_STORE = 0x39; uint16 internal constant I32_STORE8 = 0x3A; uint16 internal constant I32_STORE16 = 0x3B; uint16 internal constant I64_STORE8 = 0x3C; uint16 internal constant I64_STORE16 = 0x3D; uint16 internal constant I64_STORE32 = 0x3E; uint16 internal constant MEMORY_SIZE = 0x3F; uint16 internal constant MEMORY_GROW = 0x40; uint16 internal constant DROP = 0x1A; uint16 internal constant SELECT = 0x1B; uint16 internal constant I32_CONST = 0x41; uint16 internal constant I64_CONST = 0x42; uint16 internal constant F32_CONST = 0x43; uint16 internal constant F64_CONST = 0x44; uint16 internal constant I32_EQZ = 0x45; uint16 internal constant I32_RELOP_BASE = 0x46; uint16 internal constant IRELOP_EQ = 0; uint16 internal constant IRELOP_NE = 1; uint16 internal constant IRELOP_LT_S = 2; uint16 internal constant IRELOP_LT_U = 3; uint16 internal constant IRELOP_GT_S = 4; uint16 internal constant IRELOP_GT_U = 5; uint16 internal constant IRELOP_LE_S = 6; uint16 internal constant IRELOP_LE_U = 7; uint16 internal constant IRELOP_GE_S = 8; uint16 internal constant IRELOP_GE_U = 9; uint16 internal constant IRELOP_LAST = IRELOP_GE_U; uint16 internal constant I64_EQZ = 0x50; uint16 internal constant I64_RELOP_BASE = 0x51; uint16 internal constant I32_UNOP_BASE = 0x67; uint16 internal constant IUNOP_CLZ = 0; uint16 internal constant IUNOP_CTZ = 1; uint16 internal constant IUNOP_POPCNT = 2; uint16 internal constant IUNOP_LAST = IUNOP_POPCNT; uint16 internal constant I32_ADD = 0x6A; uint16 internal constant I32_SUB = 0x6B; uint16 internal constant I32_MUL = 0x6C; uint16 internal constant I32_DIV_S = 0x6D; uint16 internal constant I32_DIV_U = 0x6E; uint16 internal constant I32_REM_S = 0x6F; uint16 internal constant I32_REM_U = 0x70; uint16 internal constant I32_AND = 0x71; uint16 internal constant I32_OR = 0x72; uint16 internal constant I32_XOR = 0x73; uint16 internal constant I32_SHL = 0x74; uint16 internal constant I32_SHR_S = 0x75; uint16 internal constant I32_SHR_U = 0x76; uint16 internal constant I32_ROTL = 0x77; uint16 internal constant I32_ROTR = 0x78; uint16 internal constant I64_UNOP_BASE = 0x79; uint16 internal constant I64_ADD = 0x7C; uint16 internal constant I64_SUB = 0x7D; uint16 internal constant I64_MUL = 0x7E; uint16 internal constant I64_DIV_S = 0x7F; uint16 internal constant I64_DIV_U = 0x80; uint16 internal constant I64_REM_S = 0x81; uint16 internal constant I64_REM_U = 0x82; uint16 internal constant I64_AND = 0x83; uint16 internal constant I64_OR = 0x84; uint16 internal constant I64_XOR = 0x85; uint16 internal constant I64_SHL = 0x86; uint16 internal constant I64_SHR_S = 0x87; uint16 internal constant I64_SHR_U = 0x88; uint16 internal constant I64_ROTL = 0x89; uint16 internal constant I64_ROTR = 0x8A; uint16 internal constant I32_WRAP_I64 = 0xA7; uint16 internal constant I64_EXTEND_I32_S = 0xAC; uint16 internal constant I64_EXTEND_I32_U = 0xAD; uint16 internal constant I32_REINTERPRET_F32 = 0xBC; uint16 internal constant I64_REINTERPRET_F64 = 0xBD; uint16 internal constant F32_REINTERPRET_I32 = 0xBE; uint16 internal constant F64_REINTERPRET_I64 = 0xBF; uint16 internal constant I32_EXTEND_8S = 0xC0; uint16 internal constant I32_EXTEND_16S = 0xC1; uint16 internal constant I64_EXTEND_8S = 0xC2; uint16 internal constant I64_EXTEND_16S = 0xC3; uint16 internal constant I64_EXTEND_32S = 0xC4; uint16 internal constant INIT_FRAME = 0x8002; uint16 internal constant ARBITRARY_JUMP = 0x8003; uint16 internal constant ARBITRARY_JUMP_IF = 0x8004; uint16 internal constant MOVE_FROM_STACK_TO_INTERNAL = 0x8005; uint16 internal constant MOVE_FROM_INTERNAL_TO_STACK = 0x8006; uint16 internal constant DUP = 0x8008; uint16 internal constant CROSS_MODULE_CALL = 0x8009; uint16 internal constant CALLER_MODULE_INTERNAL_CALL = 0x800A; uint16 internal constant CROSS_MODULE_FORWARD = 0x800B; uint16 internal constant CROSS_MODULE_INTERNAL_CALL = 0x800C; uint16 internal constant GET_GLOBAL_STATE_BYTES32 = 0x8010; uint16 internal constant SET_GLOBAL_STATE_BYTES32 = 0x8011; uint16 internal constant GET_GLOBAL_STATE_U64 = 0x8012; uint16 internal constant SET_GLOBAL_STATE_U64 = 0x8013; uint16 internal constant READ_PRE_IMAGE = 0x8020; uint16 internal constant READ_INBOX_MESSAGE = 0x8021; uint16 internal constant HALT_AND_SET_FINISHED = 0x8022; uint16 internal constant LINK_MODULE = 0x8023; uint16 internal constant UNLINK_MODULE = 0x8024; uint16 internal constant NEW_COTHREAD = 0x8030; uint16 internal constant POP_COTHREAD = 0x8031; uint16 internal constant SWITCH_COTHREAD = 0x8032; uint256 internal constant INBOX_INDEX_SEQUENCER = 0; uint256 internal constant INBOX_INDEX_DELAYED = 1; function hash(Instruction[] memory code) internal pure returns (bytes32) { // To avoid quadratic expense, we declare a `bytes` early and populate its contents. bytes memory data = new bytes(13 + 1 + 34 * code.length); assembly { // Represents the string "Instructions:", which we place after the length word. mstore( add(data, 32), 0x496e737472756374696f6e733a00000000000000000000000000000000000000 ) } // write the instruction count uint256 offset = 13; data[offset] = bytes1(uint8(code.length)); offset++; // write each instruction for (uint256 i = 0; i < code.length; i++) { Instruction memory inst = code[i]; data[offset] = bytes1(uint8(inst.opcode >> 8)); data[offset + 1] = bytes1(uint8(inst.opcode)); offset += 2; uint256 argumentData = inst.argumentData; assembly { mstore(add(add(data, 32), offset), argumentData) } offset += 32; } return keccak256(data); } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./ValueStack.sol"; import "./Instructions.sol"; import "./MultiStack.sol"; import "./StackFrame.sol"; enum MachineStatus { RUNNING, FINISHED, ERRORED, TOO_FAR } struct Machine { MachineStatus status; ValueStack valueStack; MultiStack valueMultiStack; ValueStack internalStack; StackFrameWindow frameStack; MultiStack frameMultiStack; bytes32 globalStateHash; uint32 moduleIdx; uint32 functionIdx; uint32 functionPc; bytes32 recoveryPc; bytes32 modulesRoot; } library MachineLib { using StackFrameLib for StackFrameWindow; using ValueStackLib for ValueStack; using MultiStackLib for MultiStack; bytes32 internal constant NO_RECOVERY_PC = ~bytes32(0); function hash(Machine memory mach) internal pure returns (bytes32) { // Warning: the non-running hashes are replicated in Challenge if (mach.status == MachineStatus.RUNNING) { bytes32 valueMultiHash = mach.valueMultiStack.hash( mach.valueStack.hash(), mach.recoveryPc != NO_RECOVERY_PC ); bytes32 frameMultiHash = mach.frameMultiStack.hash( mach.frameStack.hash(), mach.recoveryPc != NO_RECOVERY_PC ); bytes memory preimage = abi.encodePacked( "Machine running:", valueMultiHash, mach.internalStack.hash(), frameMultiHash, mach.globalStateHash, mach.moduleIdx, mach.functionIdx, mach.functionPc, mach.recoveryPc, mach.modulesRoot ); return keccak256(preimage); } else if (mach.status == MachineStatus.FINISHED) { return keccak256(abi.encodePacked("Machine finished:", mach.globalStateHash)); } else if (mach.status == MachineStatus.ERRORED) { return keccak256(abi.encodePacked("Machine errored:")); } else if (mach.status == MachineStatus.TOO_FAR) { return keccak256(abi.encodePacked("Machine too far:")); } else { revert("BAD_MACH_STATUS"); } } function switchCoThreadStacks(Machine memory mach) internal pure { bytes32 newActiveValue = mach.valueMultiStack.inactiveStackHash; bytes32 newActiveFrame = mach.frameMultiStack.inactiveStackHash; if ( newActiveFrame == MultiStackLib.NO_STACK_HASH || newActiveValue == MultiStackLib.NO_STACK_HASH ) { mach.status = MachineStatus.ERRORED; return; } mach.frameMultiStack.inactiveStackHash = mach.frameStack.hash(); mach.valueMultiStack.inactiveStackHash = mach.valueStack.hash(); mach.frameStack.overwrite(newActiveFrame); mach.valueStack.overwrite(newActiveValue); } function setPcFromData(Machine memory mach, uint256 data) internal pure returns (bool) { if (data >> 96 != 0) { return false; } mach.functionPc = uint32(data); mach.functionIdx = uint32(data >> 32); mach.moduleIdx = uint32(data >> 64); return true; } function setPcFromRecovery(Machine memory mach) internal pure returns (bool) { if (!setPcFromData(mach, uint256(mach.recoveryPc))) { return false; } mach.recoveryPc = NO_RECOVERY_PC; return true; } function setRecoveryFromPc(Machine memory mach, uint32 offset) internal pure returns (bool) { if (mach.recoveryPc != NO_RECOVERY_PC) { return false; } uint256 result; result = uint256(mach.moduleIdx) << 64; result = result | (uint256(mach.functionIdx) << 32); result = result | uint256(mach.functionPc + offset - 1); mach.recoveryPc = bytes32(result); return true; } function setPc(Machine memory mach, Value memory pc) internal pure { if (pc.valueType == ValueType.REF_NULL) { mach.status = MachineStatus.ERRORED; return; } if (pc.valueType != ValueType.INTERNAL_REF) { mach.status = MachineStatus.ERRORED; return; } if (!setPcFromData(mach, pc.contents)) { mach.status = MachineStatus.ERRORED; return; } } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./ModuleMemoryCompact.sol"; struct Module { bytes32 globalsMerkleRoot; ModuleMemory moduleMemory; bytes32 tablesMerkleRoot; bytes32 functionsMerkleRoot; bytes32 extraHash; uint32 internalsOffset; } library ModuleLib { using ModuleMemoryCompactLib for ModuleMemory; function hash(Module memory mod) internal pure returns (bytes32) { return keccak256( abi.encodePacked( "Module:", mod.globalsMerkleRoot, mod.moduleMemory.hash(), mod.tablesMerkleRoot, mod.functionsMerkleRoot, mod.extraHash, mod.internalsOffset ) ); } }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; struct ModuleMemory { uint64 size; uint64 maxSize; bytes32 merkleRoot; } library ModuleMemoryCompactLib { function hash(ModuleMemory memory mem) internal pure returns (bytes32) { return keccak256(abi.encodePacked("Memory:", mem.size, mem.maxSize, mem.merkleRoot)); } }
// Copyright 2021-2024, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; struct MultiStack { bytes32 inactiveStackHash; // NO_STACK_HASH if no stack, 0 if empty stack bytes32 remainingHash; // 0 if less than 2 cothreads exist } library MultiStackLib { bytes32 internal constant NO_STACK_HASH = ~bytes32(0); function hash( MultiStack memory multi, bytes32 activeStackHash, bool cothread ) internal pure returns (bytes32) { require(activeStackHash != NO_STACK_HASH, "MULTISTACK_NOSTACK_ACTIVE"); if (cothread) { require(multi.inactiveStackHash != NO_STACK_HASH, "MULTISTACK_NOSTACK_MAIN"); return keccak256( abi.encodePacked( "multistack:", multi.inactiveStackHash, activeStackHash, multi.remainingHash ) ); } else { return keccak256( abi.encodePacked( "multistack:", activeStackHash, multi.inactiveStackHash, multi.remainingHash ) ); } } function setEmpty(MultiStack memory multi) internal pure { multi.inactiveStackHash = NO_STACK_HASH; multi.remainingHash = 0; } function pushNew(MultiStack memory multi) internal pure { if (multi.inactiveStackHash != NO_STACK_HASH) { multi.remainingHash = keccak256( abi.encodePacked("cothread:", multi.inactiveStackHash, multi.remainingHash) ); } multi.inactiveStackHash = 0; } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./Value.sol"; struct StackFrame { Value returnPc; bytes32 localsMerkleRoot; uint32 callerModule; uint32 callerModuleInternals; } struct StackFrameWindow { StackFrame[] proved; bytes32 remainingHash; } library StackFrameLib { using ValueLib for Value; function hash(StackFrame memory frame) internal pure returns (bytes32) { return keccak256( abi.encodePacked( "Stack frame:", frame.returnPc.hash(), frame.localsMerkleRoot, frame.callerModule, frame.callerModuleInternals ) ); } function hash(StackFrameWindow memory window) internal pure returns (bytes32 h) { h = window.remainingHash; for (uint256 i = 0; i < window.proved.length; i++) { h = keccak256(abi.encodePacked("Stack frame stack:", hash(window.proved[i]), h)); } } function peek(StackFrameWindow memory window) internal pure returns (StackFrame memory) { require(window.proved.length == 1, "BAD_WINDOW_LENGTH"); return window.proved[0]; } function pop(StackFrameWindow memory window) internal pure returns (StackFrame memory frame) { require(window.proved.length == 1, "BAD_WINDOW_LENGTH"); frame = window.proved[0]; window.proved = new StackFrame[](0); } function push(StackFrameWindow memory window, StackFrame memory frame) internal pure { StackFrame[] memory newProved = new StackFrame[](window.proved.length + 1); for (uint256 i = 0; i < window.proved.length; i++) { newProved[i] = window.proved[i]; } newProved[window.proved.length] = frame; window.proved = newProved; } function overwrite(StackFrameWindow memory window, bytes32 root) internal pure { window.remainingHash = root; delete window.proved; } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; enum ValueType { I32, I64, F32, F64, REF_NULL, FUNC_REF, INTERNAL_REF } struct Value { ValueType valueType; uint256 contents; } library ValueLib { function hash(Value memory val) internal pure returns (bytes32) { return keccak256(abi.encodePacked("Value:", val.valueType, val.contents)); } function maxValueType() internal pure returns (ValueType) { return ValueType.INTERNAL_REF; } function assumeI32(Value memory val) internal pure returns (uint32) { uint256 uintval = uint256(val.contents); require(val.valueType == ValueType.I32, "NOT_I32"); require(uintval < (1 << 32), "BAD_I32"); return uint32(uintval); } function assumeI64(Value memory val) internal pure returns (uint64) { uint256 uintval = uint256(val.contents); require(val.valueType == ValueType.I64, "NOT_I64"); require(uintval < (1 << 64), "BAD_I64"); return uint64(uintval); } function newRefNull() internal pure returns (Value memory) { return Value({valueType: ValueType.REF_NULL, contents: 0}); } function newI32(uint32 x) internal pure returns (Value memory) { return Value({valueType: ValueType.I32, contents: uint256(x)}); } function newI64(uint64 x) internal pure returns (Value memory) { return Value({valueType: ValueType.I64, contents: uint256(x)}); } function newBoolean(bool x) internal pure returns (Value memory) { if (x) { return newI32(uint32(1)); } else { return newI32(uint32(0)); } } function newPc( uint32 funcPc, uint32 func, uint32 module ) internal pure returns (Value memory) { uint256 data = 0; data |= funcPc; data |= uint256(func) << 32; data |= uint256(module) << 64; return Value({valueType: ValueType.INTERNAL_REF, contents: data}); } }
// Copyright 2021-2022, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./Value.sol"; struct ValueArray { Value[] inner; } library ValueArrayLib { function get(ValueArray memory arr, uint256 index) internal pure returns (Value memory) { return arr.inner[index]; } function set( ValueArray memory arr, uint256 index, Value memory val ) internal pure { arr.inner[index] = val; } function length(ValueArray memory arr) internal pure returns (uint256) { return arr.inner.length; } function push(ValueArray memory arr, Value memory val) internal pure { Value[] memory newInner = new Value[](arr.inner.length + 1); for (uint256 i = 0; i < arr.inner.length; i++) { newInner[i] = arr.inner[i]; } newInner[arr.inner.length] = val; arr.inner = newInner; } function pop(ValueArray memory arr) internal pure returns (Value memory popped) { popped = arr.inner[arr.inner.length - 1]; Value[] memory newInner = new Value[](arr.inner.length - 1); for (uint256 i = 0; i < newInner.length; i++) { newInner[i] = arr.inner[i]; } arr.inner = newInner; } }
// Copyright 2021-2023, Offchain Labs, Inc. // For license information, see https://github.com/OffchainLabs/nitro-contracts/blob/main/LICENSE // SPDX-License-Identifier: BUSL-1.1 pragma solidity ^0.8.0; import "./Value.sol"; import "./ValueArray.sol"; struct ValueStack { ValueArray proved; bytes32 remainingHash; } library ValueStackLib { using ValueLib for Value; using ValueArrayLib for ValueArray; function hash(ValueStack memory stack) internal pure returns (bytes32 h) { h = stack.remainingHash; uint256 len = stack.proved.length(); for (uint256 i = 0; i < len; i++) { h = keccak256(abi.encodePacked("Value stack:", stack.proved.get(i).hash(), h)); } } function peek(ValueStack memory stack) internal pure returns (Value memory) { uint256 len = stack.proved.length(); return stack.proved.get(len - 1); } function pop(ValueStack memory stack) internal pure returns (Value memory) { return stack.proved.pop(); } function push(ValueStack memory stack, Value memory val) internal pure { return stack.proved.push(val); } function overwrite(ValueStack memory stack, bytes32 root) internal pure { stack.remainingHash = root; delete stack.proved; } }
{ "optimizer": { "enabled": true, "runs": 100 }, "outputSelection": { "*": { "*": [ "evm.bytecode", "evm.deployedBytecode", "devdoc", "userdoc", "metadata", "abi" ] } }, "metadata": { "useLiteralContent": true }, "libraries": {} }
Contract Security Audit
- No Contract Security Audit Submitted- Submit Audit Here
Contract ABI
API[{"inputs":[{"internalType":"address","name":"sender","type":"address"},{"internalType":"address","name":"owner","type":"address"}],"name":"NotOwner","type":"error"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"indexed":true,"internalType":"bytes32","name":"challengeRoot","type":"bytes32"},{"indexed":false,"internalType":"uint256","name":"challengedSegmentStart","type":"uint256"},{"indexed":false,"internalType":"uint256","name":"challengedSegmentLength","type":"uint256"},{"indexed":false,"internalType":"bytes32[]","name":"chainHashes","type":"bytes32[]"}],"name":"Bisected","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"indexed":false,"internalType":"enum IChallengeManager.ChallengeTerminationType","name":"kind","type":"uint8"}],"name":"ChallengeEnded","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"indexed":false,"internalType":"uint256","name":"blockSteps","type":"uint256"}],"name":"ExecutionChallengeBegun","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"components":[{"internalType":"bytes32[2]","name":"bytes32Vals","type":"bytes32[2]"},{"internalType":"uint64[2]","name":"u64Vals","type":"uint64[2]"}],"indexed":false,"internalType":"struct GlobalState","name":"startState","type":"tuple"},{"components":[{"internalType":"bytes32[2]","name":"bytes32Vals","type":"bytes32[2]"},{"internalType":"uint64[2]","name":"u64Vals","type":"uint64[2]"}],"indexed":false,"internalType":"struct GlobalState","name":"endState","type":"tuple"}],"name":"InitiatedChallenge","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"OneStepProofCompleted","type":"event"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"components":[{"internalType":"uint256","name":"oldSegmentsStart","type":"uint256"},{"internalType":"uint256","name":"oldSegmentsLength","type":"uint256"},{"internalType":"bytes32[]","name":"oldSegments","type":"bytes32[]"},{"internalType":"uint256","name":"challengePosition","type":"uint256"}],"internalType":"struct ChallengeLib.SegmentSelection","name":"selection","type":"tuple"},{"internalType":"bytes32[]","name":"newSegments","type":"bytes32[]"}],"name":"bisectExecution","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"bridge","outputs":[{"internalType":"contract IBridge","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"components":[{"internalType":"uint256","name":"oldSegmentsStart","type":"uint256"},{"internalType":"uint256","name":"oldSegmentsLength","type":"uint256"},{"internalType":"bytes32[]","name":"oldSegments","type":"bytes32[]"},{"internalType":"uint256","name":"challengePosition","type":"uint256"}],"internalType":"struct ChallengeLib.SegmentSelection","name":"selection","type":"tuple"},{"internalType":"enum MachineStatus[2]","name":"machineStatuses","type":"uint8[2]"},{"internalType":"bytes32[2]","name":"globalStateHashes","type":"bytes32[2]"},{"internalType":"uint256","name":"numSteps","type":"uint256"}],"name":"challengeExecution","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"challengeInfo","outputs":[{"components":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint256","name":"timeLeft","type":"uint256"}],"internalType":"struct ChallengeLib.Participant","name":"current","type":"tuple"},{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint256","name":"timeLeft","type":"uint256"}],"internalType":"struct ChallengeLib.Participant","name":"next","type":"tuple"},{"internalType":"uint256","name":"lastMoveTimestamp","type":"uint256"},{"internalType":"bytes32","name":"wasmModuleRoot","type":"bytes32"},{"internalType":"bytes32","name":"challengeStateHash","type":"bytes32"},{"internalType":"uint64","name":"maxInboxMessages","type":"uint64"},{"internalType":"enum ChallengeLib.ChallengeMode","name":"mode","type":"uint8"}],"internalType":"struct ChallengeLib.Challenge","name":"","type":"tuple"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint256","name":"","type":"uint256"}],"name":"challenges","outputs":[{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint256","name":"timeLeft","type":"uint256"}],"internalType":"struct ChallengeLib.Participant","name":"current","type":"tuple"},{"components":[{"internalType":"address","name":"addr","type":"address"},{"internalType":"uint256","name":"timeLeft","type":"uint256"}],"internalType":"struct ChallengeLib.Participant","name":"next","type":"tuple"},{"internalType":"uint256","name":"lastMoveTimestamp","type":"uint256"},{"internalType":"bytes32","name":"wasmModuleRoot","type":"bytes32"},{"internalType":"bytes32","name":"challengeStateHash","type":"bytes32"},{"internalType":"uint64","name":"maxInboxMessages","type":"uint64"},{"internalType":"enum ChallengeLib.ChallengeMode","name":"mode","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"clearChallenge","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"bytes32","name":"wasmModuleRoot_","type":"bytes32"},{"internalType":"enum MachineStatus[2]","name":"startAndEndMachineStatuses_","type":"uint8[2]"},{"components":[{"internalType":"bytes32[2]","name":"bytes32Vals","type":"bytes32[2]"},{"internalType":"uint64[2]","name":"u64Vals","type":"uint64[2]"}],"internalType":"struct GlobalState[2]","name":"startAndEndGlobalStates_","type":"tuple[2]"},{"internalType":"uint64","name":"numBlocks","type":"uint64"},{"internalType":"address","name":"asserter_","type":"address"},{"internalType":"address","name":"challenger_","type":"address"},{"internalType":"uint256","name":"asserterTimeLeft_","type":"uint256"},{"internalType":"uint256","name":"challengerTimeLeft_","type":"uint256"}],"name":"createChallenge","outputs":[{"internalType":"uint64","name":"","type":"uint64"}],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"currentResponder","outputs":[{"internalType":"address","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"wasmModuleRoot","type":"bytes32"}],"name":"getOsp","outputs":[{"internalType":"contract IOneStepProofEntry","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"contract IChallengeResultReceiver","name":"resultReceiver_","type":"address"},{"internalType":"contract ISequencerInbox","name":"sequencerInbox_","type":"address"},{"internalType":"contract IBridge","name":"bridge_","type":"address"},{"internalType":"contract IOneStepProofEntry","name":"osp_","type":"address"}],"name":"initialize","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"isTimedOut","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"},{"components":[{"internalType":"uint256","name":"oldSegmentsStart","type":"uint256"},{"internalType":"uint256","name":"oldSegmentsLength","type":"uint256"},{"internalType":"bytes32[]","name":"oldSegments","type":"bytes32[]"},{"internalType":"uint256","name":"challengePosition","type":"uint256"}],"internalType":"struct ChallengeLib.SegmentSelection","name":"selection","type":"tuple"},{"internalType":"bytes","name":"proof","type":"bytes"}],"name":"oneStepProveExecution","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"osp","outputs":[{"internalType":"contract IOneStepProofEntry","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"bytes32","name":"","type":"bytes32"}],"name":"ospCond","outputs":[{"internalType":"contract IOneStepProofEntry","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"contract IOneStepProofEntry","name":"osp_","type":"address"},{"internalType":"bytes32","name":"condRoot","type":"bytes32"},{"internalType":"contract IOneStepProofEntry","name":"condOsp","type":"address"}],"name":"postUpgradeInit","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"resultReceiver","outputs":[{"internalType":"contract IChallengeResultReceiver","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"sequencerInbox","outputs":[{"internalType":"contract ISequencerInbox","name":"","type":"address"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"uint64","name":"challengeIndex","type":"uint64"}],"name":"timeout","outputs":[],"stateMutability":"nonpayable","type":"function"},{"inputs":[],"name":"totalChallengesCreated","outputs":[{"internalType":"uint64","name":"","type":"uint64"}],"stateMutability":"view","type":"function"}]
Contract Creation Code
60a06040523060805234801561001457600080fd5b50608051612cab6100376000396000818161082501526114350152612cab6000f3fe608060405234801561001057600080fd5b50600436106101115760003560e01c80638f1d3776116100ad578063e78cea9211610071578063e78cea921461031a578063ee35f3271461032d578063f26a62c614610340578063f8c8765e14610353578063fb7be0a11461036657600080fd5b80638f1d3776146102055780639ede42b9146102a8578063a521b032146102cb578063d248d124146102de578063dc74bf8b146102f157600080fd5b806314eab5e7146101165780631b45c86a1461014657806323a9ef231461015b5780633504f1d7146101865780633690b011146101995780635038934d146101ac57806356e9df97146101bf5780635ef489e6146101d25780637fd07a9c146101e5575b600080fd5b610129610124366004612241565b610379565b6040516001600160401b0390911681526020015b60405180910390f35b6101596101543660046122d4565b6106f0565b005b61016e6101693660046122d4565b6107c0565b6040516001600160a01b03909116815260200161013d565b60025461016e906001600160a01b031681565b61016e6101a73660046122ef565b6107e4565b6101596101ba366004612308565b61081a565b6101596101cd3660046122d4565b610900565b600054610129906001600160401b031681565b6101f86101f33660046122d4565b610a6e565b60405161013d919061238c565b6102956102133660046122ef565b6001602081815260009283526040928390208351808501855281546001600160a01b0390811682529382015481840152845180860190955260028201549093168452600381015491840191909152600481015460058201546006830154600790930154939493919290916001600160401b03811690600160401b900460ff1687565b60405161013d97969594939291906123fe565b6102bb6102b63660046122d4565b610b47565b604051901515815260200161013d565b6101596102d9366004612461565b610b68565b6101596102ec366004612505565b610fde565b61016e6102ff3660046122ef565b6006602052600090815260409020546001600160a01b031681565b60045461016e906001600160a01b031681565b60035461016e906001600160a01b031681565b60055461016e906001600160a01b031681565b610159610361366004612597565b61142a565b6101596103743660046125f3565b611556565b6002546000906001600160a01b031633146103ce5760405162461bcd60e51b815260206004820152601060248201526f13d3931657d493d313155417d0d2105360821b60448201526064015b60405180910390fd5b6040805160028082526060820183526000926020830190803683370190505090506104936103ff60208b018b612697565b61048e8a60005b6080020180360381019061041a9190612756565b8051805160209182015192820151805190830151604080516c23b637b130b61039ba30ba329d60991b81870152602d810194909452604d8401959095526001600160c01b031960c092831b8116606d850152911b1660758201528251808203605d018152607d909101909252815191012090565b611cc4565b816000815181106104a6576104a6612681565b60209081029190910101526104d58960016020020160208101906104ca9190612697565b61048e8a6001610406565b816001815181106104e8576104e8612681565b6020908102919091010152600080548190819061050d906001600160401b0316612804565b91906101000a8154816001600160401b0302191690836001600160401b031602179055905060006001600160401b0316816001600160401b031614156105555761055561282b565b6001600160401b0381166000908152600160205260408120600581018d90559061058f61058a368d90038d0160808e01612756565b611de8565b905060026105a360408e0160208f01612697565b60038111156105b4576105b4612362565b14806105e2575060006105d76105d2368e90038e0160808f01612756565b611dfd565b6001600160401b0316115b156105f557806105f181612804565b9150505b6007820180546040805180820182526001600160a01b038d811680835260209283018d90526002880180546001600160a01b03199081169092179055600388018d905583518085018552918e16808352919092018b90528654909116178555600185018990554260048601556001600160401b0384811668ffffffffffffffffff1990931692909217600160401b179092559051908416907f76604fe17af46c9b5f53ffe99ff23e0f655dab91886b07ac1fc0254319f7145a906106bf908e90608082019061288b565b60405180910390a26106dd8360008c6001600160401b031687611e0c565b5090925050505b98975050505050505050565b60006001600160401b038216600090815260016020526040902060070154600160401b900460ff16600281111561072957610729612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906107695760405162461bcd60e51b81526004016103c591906128a7565b5061077381610b47565b6107b25760405162461bcd60e51b815260206004820152601060248201526f54494d454f55545f444541444c494e4560801b60448201526064016103c5565b6107bd816000611ea2565b50565b6001600160401b03166000908152600160205260409020546001600160a01b031690565b6000818152600660205260408120546001600160a01b0316806108145750506005546001600160a01b0316919050565b92915050565b306001600160a01b037f00000000000000000000000000000000000000000000000000000000000000001614156108635760405162461bcd60e51b81526004016103c5906128fc565b7fb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d61038054336001600160a01b038216146108c057604051631194af8760e11b81523360048201526001600160a01b03821660248201526044016103c5565b505060009182526006602052604090912080546001600160a01b039283166001600160a01b03199182161790915560058054939092169216919091179055565b6002546001600160a01b0316331461094d5760405162461bcd60e51b815260206004820152601060248201526f2727aa2fa922a9afa922a1a2a4ab22a960811b60448201526064016103c5565b60006001600160401b038216600090815260016020526040902060070154600160401b900460ff16600281111561098657610986612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906109c65760405162461bcd60e51b81526004016103c591906128a7565b506001600160401b038116600081815260016020819052604080832080546001600160a01b031990811682559281018490556002810180549093169092556003808301849055600483018490556005830184905560068301939093556007909101805468ffffffffffffffffff19169055517ffdaece6c274a4b56af16761f83fd6b1062823192630ea08e019fdf9b2d747f4091610a6391612958565b60405180910390a250565b610a76612197565b6001600160401b0382811660009081526001602081815260409283902083516101208101855281546001600160a01b0390811660e0830190815294830154610100830152938152845180860186526002808401549095168152600383015481850152928101929092526004810154938201939093526005830154606082015260068301546080820152600783015493841660a08201529260c0840191600160401b90910460ff1690811115610b2d57610b2d612362565b6002811115610b3e57610b3e612362565b90525092915050565b6001600160401b038116600090815260016020526040812061081490611fd0565b6001600160401b038416600090815260016020526040812085918591610b8d846107c0565b6001600160a01b0316336001600160a01b031614610bbd5760405162461bcd60e51b81526004016103c59061296b565b610bc684610b47565b15610be35760405162461bcd60e51b81526004016103c590612990565b6000826002811115610bf757610bf7612362565b1415610c655760006007820154600160401b900460ff166002811115610c1f57610c1f612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b81525090610c5f5760405162461bcd60e51b81526004016103c591906128a7565b50610d24565b6001826002811115610c7957610c79612362565b1415610cc35760016007820154600160401b900460ff166002811115610ca157610ca1612362565b14610cbe5760405162461bcd60e51b81526004016103c5906129b7565b610d24565b6002826002811115610cd757610cd7612362565b1415610d1c5760026007820154600160401b900460ff166002811115610cff57610cff612362565b14610cbe5760405162461bcd60e51b81526004016103c5906129df565b610d2461282b565b610d7283356020850135610d3b6040870187612a0b565b80806020026020016040519081016040528093929190818152602001838360200280828437600092019190915250611fe892505050565b816006015414610d945760405162461bcd60e51b81526004016103c590612a5b565b6002610da36040850185612a0b565b90501080610dce57506001610dbb6040850185612a0b565b610dc6929150612a7e565b836060013510155b15610deb5760405162461bcd60e51b81526004016103c590612a95565b600080610df78961201f565b9150915060018111610e375760405162461bcd60e51b81526020600482015260096024820152681513d3d7d4d213d49560ba1b60448201526064016103c5565b806028811115610e45575060285b610e50816001612ac0565b8814610e8d5760405162461bcd60e51b815260206004820152600c60248201526b57524f4e475f44454752454560a01b60448201526064016103c5565b50610ed78989896000818110610ea557610ea5612681565b602002919091013590508a8a610ebc600182612a7e565b818110610ecb57610ecb612681565b905060200201356120b0565b610f168a83838b8b80806020026020016040519081016040528093929190818152602001838360200280828437600092019190915250611e0c92505050565b50600090505b6007820154600160401b900460ff166002811115610f3c57610f3c612362565b1415610f485750610fd5565b6040805180820190915281546001600160a01b03168152600182015460208201526004820154610f789042612a7e565b81602001818151610f899190612a7e565b90525060028201805483546001600160a01b038083166001600160a01b031992831617865560038601805460018801558551929093169116179091556020909101519055426004909101555b50505050505050565b6001600160401b038416600090815260016020526040902084908490600290611006846107c0565b6001600160a01b0316336001600160a01b0316146110365760405162461bcd60e51b81526004016103c59061296b565b61103f84610b47565b1561105c5760405162461bcd60e51b81526004016103c590612990565b600082600281111561107057611070612362565b14156110de5760006007820154600160401b900460ff16600281111561109857611098612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906110d85760405162461bcd60e51b81526004016103c591906128a7565b5061119d565b60018260028111156110f2576110f2612362565b141561113c5760016007820154600160401b900460ff16600281111561111a5761111a612362565b146111375760405162461bcd60e51b81526004016103c5906129b7565b61119d565b600282600281111561115057611150612362565b14156111955760026007820154600160401b900460ff16600281111561117857611178612362565b146111375760405162461bcd60e51b81526004016103c5906129df565b61119d61282b565b6111b483356020850135610d3b6040870187612a0b565b8160060154146111d65760405162461bcd60e51b81526004016103c590612a5b565b60026111e56040850185612a0b565b90501080611210575060016111fd6040850185612a0b565b611208929150612a7e565b836060013510155b1561122d5760405162461bcd60e51b81526004016103c590612a95565b6001600160401b038816600090815260016020526040812090806112508a61201f565b9092509050600181146112755760405162461bcd60e51b81526004016103c590612ad8565b50600061128583600501546107e4565b60408051808201825260078601546001600160401b031681526004546001600160a01b0390811660208301529290921691635d3adcfb9185906112ca908f018f612a0b565b8f606001358181106112de576112de612681565b905060200201358d8d6040518663ffffffff1660e01b8152600401611307959493929190612afa565b60206040518083038186803b15801561131f57600080fd5b505afa158015611333573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906113579190612b51565b905061136660408b018b612a0b565b61137560608d01356001612ac0565b81811061138457611384612681565b905060200201358114156113c95760405162461bcd60e51b815260206004820152600c60248201526b14d0535157d3d4d417d1539160a21b60448201526064016103c5565b6040516001600160401b038c16907fc2cc42e04ff8c36de71c6a2937ea9f161dd0dd9e175f00caa26e5200643c781e90600090a261141e8b6001600160401b0316600090815260016020526040812060060155565b5060009150610f1c9050565b306001600160a01b037f00000000000000000000000000000000000000000000000000000000000000001614156114735760405162461bcd60e51b81526004016103c5906128fc565b6002546001600160a01b0316156114bb5760405162461bcd60e51b815260206004820152600c60248201526b1053149150511657d253925560a21b60448201526064016103c5565b6001600160a01b0384166115065760405162461bcd60e51b81526020600482015260126024820152712727afa922a9aaa62a2fa922a1a2a4ab22a960711b60448201526064016103c5565b600280546001600160a01b039586166001600160a01b0319918216179091556003805494861694821694909417909355600480549285169284169290921790915560058054919093169116179055565b6001600160401b03851660009081526001602081905260409091208691869161157e846107c0565b6001600160a01b0316336001600160a01b0316146115ae5760405162461bcd60e51b81526004016103c59061296b565b6115b784610b47565b156115d45760405162461bcd60e51b81526004016103c590612990565b60008260028111156115e8576115e8612362565b14156116565760006007820154600160401b900460ff16600281111561161057611610612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906116505760405162461bcd60e51b81526004016103c591906128a7565b50611715565b600182600281111561166a5761166a612362565b14156116b45760016007820154600160401b900460ff16600281111561169257611692612362565b146116af5760405162461bcd60e51b81526004016103c5906129b7565b611715565b60028260028111156116c8576116c8612362565b141561170d5760026007820154600160401b900460ff1660028111156116f0576116f0612362565b146116af5760405162461bcd60e51b81526004016103c5906129df565b61171561282b565b61172c83356020850135610d3b6040870187612a0b565b81600601541461174e5760405162461bcd60e51b81526004016103c590612a5b565b600261175d6040850185612a0b565b90501080611788575060016117756040850185612a0b565b611780929150612a7e565b836060013510155b156117a55760405162461bcd60e51b81526004016103c590612a95565b60018510156117ec5760405162461bcd60e51b815260206004820152601360248201527210d2105313115391d157d513d3d7d4d213d495606a1b60448201526064016103c5565b650800000000008511156118375760405162461bcd60e51b81526020600482015260126024820152714348414c4c454e47455f544f4f5f4c4f4e4760701b60448201526064016103c5565b6118798861185961184b60208b018b612697565b8960005b6020020135611cc4565b61187461186c60408c0160208d01612697565b8a600161184f565b6120b0565b6001600160401b0389166000908152600160205260408120908061189c8b61201f565b91509150806001146118c05760405162461bcd60e51b81526004016103c590612ad8565b60016118cf60208c018c612697565b60038111156118e0576118e0612362565b1461199a576118f560408b0160208c01612697565b600381111561190657611906612362565b61191360208c018c612697565b600381111561192457611924612362565b1480156119355750883560208a0135145b6119715760405162461bcd60e51b815260206004820152600d60248201526c48414c5445445f4348414e474560981b60448201526064016103c5565b6119928c6001600160401b0316600090815260016020526040812060060155565b505050611bff565b60026119ac60408c0160208d01612697565b60038111156119bd576119bd612362565b1415611a0657883560208a013514611a065760405162461bcd60e51b815260206004820152600c60248201526b4552524f525f4348414e474560a01b60448201526064016103c5565b6040805160028082526060820183526000926020830190803683370190505090506000611a3685600501546107e4565b60058601546040516301265ef960e21b81528d35600482015260248101919091529091506001600160a01b038216906304997be49060440160206040518083038186803b158015611a8657600080fd5b505afa158015611a9a573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611abe9190612b51565b82600081518110611ad157611ad1612681565b60209081029190910101526001600160a01b03811663d8558b878d6001602002016020810190611b019190612697565b8d600160200201356040518363ffffffff1660e01b8152600401611b26929190612b6a565b60206040518083038186803b158015611b3e57600080fd5b505afa158015611b52573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b769190612b51565b82600181518110611b8957611b89612681565b602090810291909101015260078501805460ff60401b1916600160411b179055611bb68e60008c85611e0c565b8d6001600160401b03167f24e032e170243bbea97e140174b22dc7e54fb85925afbf52c70e001cd6af16db85604051611bf191815260200190565b60405180910390a250505050505b60006007820154600160401b900460ff166002811115611c2157611c21612362565b1415611c2d5750611cba565b6040805180820190915281546001600160a01b03168152600182015460208201526004820154611c5d9042612a7e565b81602001818151611c6e9190612a7e565b90525060028201805483546001600160a01b038083166001600160a01b031992831617865560038601805460018801558551929093169116179091556020909101519055426004909101555b5050505050505050565b60006001836003811115611cda57611cda612362565b1415611d20576040516b213637b1b59039ba30ba329d60a11b6020820152602c8101839052604c015b604051602081830303815290604052805190602001209050610814565b6002836003811115611d3457611d34612362565b1415611d6a5760405174213637b1b59039ba30ba32961032b93937b932b21d60591b602082015260358101839052605501611d03565b6003836003811115611d7e57611d7e612362565b1415611dad5760405174213637b1b59039ba30ba3296103a37b7903330b91d60591b6020820152603501611d03565b60405162461bcd60e51b815260206004820152601060248201526f4241445f424c4f434b5f53544154555360801b60448201526064016103c5565b6020810151600090815b602002015192915050565b60208101516000906001611df2565b6001821015611e1d57611e1d61282b565b600281511015611e2f57611e2f61282b565b6000611e3c848484611fe8565b6001600160401b038616600081815260016020526040908190206006018390555191925082917f86b34e9455464834eca718f62d4481437603bb929d8a78ccde5d1bc79fa06d6890611e9390889088908890612b81565b60405180910390a35050505050565b6001600160401b03821660008181526001602081905260408083206002808201805483546001600160a01b0319808216865596850188905595811690915560038301869055600480840187905560058401879055600684019690965560078301805468ffffffffffffffffff1916905590549251630357aa4960e01b8152948501959095526001600160a01b03948516602485018190529285166044850181905290949293909290911690630357aa4990606401600060405180830381600087803b158015611f7057600080fd5b505af1158015611f84573d6000803e3d6000fd5b50505050846001600160401b03167ffdaece6c274a4b56af16761f83fd6b1062823192630ea08e019fdf9b2d747f4085604051611fc19190612958565b60405180910390a25050505050565b6001810154600090611fe183612185565b1192915050565b6000838383604051602001611fff93929190612bd6565b6040516020818303038152906040528051906020012090505b9392505050565b6000808060016120326040860186612a0b565b61203d929150612a7e565b905061204d816020860135612c2e565b915061205d606085013583612c42565b612068908535612ac0565b925060026120796040860186612a0b565b612084929150612a7e565b846060013514156120aa5761209d816020860135612c61565b6120a79083612ac0565b91505b50915091565b816120be6040850185612a0b565b85606001358181106120d2576120d2612681565b90506020020135146121145760405162461bcd60e51b815260206004820152600b60248201526a15d493d391d7d4d510549560aa1b60448201526064016103c5565b806121226040850185612a0b565b61213160608701356001612ac0565b81811061214057612140612681565b9050602002013514156121805760405162461bcd60e51b815260206004820152600860248201526714d0535157d1539160c21b60448201526064016103c5565b505050565b60008160040154426108149190612a7e565b604080516101208101909152600060e08201818152610100830191909152819081526020016121d6604080518082019091526000808252602082015290565b815260006020820181905260408201819052606082018190526080820181905260a09091015290565b806040810183101561081457600080fd5b80356001600160401b038116811461222757600080fd5b919050565b6001600160a01b03811681146107bd57600080fd5b600080600080600080600080610200898b03121561225e57600080fd5b8835975061226f8a60208b016121ff565b965061016089018a81111561228357600080fd5b60608a01965061229281612210565b9550506101808901356122a48161222c565b93506101a08901356122b58161222c565b979a96995094979396929592945050506101c0820135916101e0013590565b6000602082840312156122e657600080fd5b61201882612210565b60006020828403121561230157600080fd5b5035919050565b60008060006060848603121561231d57600080fd5b83356123288161222c565b925060208401359150604084013561233f8161222c565b809150509250925092565b80516001600160a01b03168252602090810151910152565b634e487b7160e01b600052602160045260246000fd5b6003811061238857612388612362565b9052565b6000610120820190506123a082845161234a565b60208301516123b2604084018261234a565b5060408301516080830152606083015160a0830152608083015160c08301526001600160401b0360a08401511660e083015260c08301516123f7610100840182612378565b5092915050565b610120810161240d828a61234a565b61241a604083018961234a565b8660808301528560a08301528460c08301526001600160401b03841660e08301526106e4610100830184612378565b60006080828403121561245b57600080fd5b50919050565b6000806000806060858703121561247757600080fd5b61248085612210565b935060208501356001600160401b038082111561249c57600080fd5b6124a888838901612449565b945060408701359150808211156124be57600080fd5b818701915087601f8301126124d257600080fd5b8135818111156124e157600080fd5b8860208260051b85010111156124f657600080fd5b95989497505060200194505050565b6000806000806060858703121561251b57600080fd5b61252485612210565b935060208501356001600160401b038082111561254057600080fd5b61254c88838901612449565b9450604087013591508082111561256257600080fd5b818701915087601f83011261257657600080fd5b81358181111561258557600080fd5b8860208285010111156124f657600080fd5b600080600080608085870312156125ad57600080fd5b84356125b88161222c565b935060208501356125c88161222c565b925060408501356125d88161222c565b915060608501356125e88161222c565b939692955090935050565b600080600080600060e0868803121561260b57600080fd5b61261486612210565b945060208601356001600160401b0381111561262f57600080fd5b61263b88828901612449565b94505061264b87604088016121ff565b925061265a87608088016121ff565b9497939650919460c0013592915050565b634e487b7160e01b600052604160045260246000fd5b634e487b7160e01b600052603260045260246000fd5b6000602082840312156126a957600080fd5b81356004811061201857600080fd5b604080519081016001600160401b03811182821017156126da576126da61266b565b60405290565b600082601f8301126126f157600080fd5b604051604081018181106001600160401b03821117156127135761271361266b565b806040525080604084018581111561272a57600080fd5b845b8181101561274b5761273d81612210565b83526020928301920161272c565b509195945050505050565b60006080828403121561276857600080fd5b604051604081018181106001600160401b038211171561278a5761278a61266b565b604052601f8301841361279c57600080fd5b6127a46126b8565b8060408501868111156127b657600080fd5b855b818110156127d05780358452602093840193016127b8565b508184526127de87826126e0565b6020850152509195945050505050565b634e487b7160e01b600052601160045260246000fd5b60006001600160401b0380831681811415612821576128216127ee565b6001019392505050565b634e487b7160e01b600052600160045260246000fd5b604081833760006040838101828152908301915b6002811015612884576001600160401b0361286f84612210565b16825260209283019290910190600101612855565b5050505050565b610100810161289a8285612841565b6120186080830184612841565b600060208083528351808285015260005b818110156128d4578581018301518582016040015282016128b8565b818111156128e6576000604083870101525b50601f01601f1916929092016040019392505050565b6020808252602c908201527f46756e6374696f6e206d7573742062652063616c6c6564207468726f7567682060408201526b19195b1959d85d1958d85b1b60a21b606082015260800190565b600481106107bd576107bd612362565b6020810161296583612948565b91905290565b6020808252600b908201526a21a420a62fa9a2a72222a960a91b604082015260600190565b6020808252600d908201526c4348414c5f444541444c494e4560981b604082015260600190565b6020808252600e908201526d4348414c5f4e4f545f424c4f434b60901b604082015260600190565b60208082526012908201527121a420a62fa727aa2fa2ac22a1aaaa24a7a760711b604082015260600190565b6000808335601e19843603018112612a2257600080fd5b8301803591506001600160401b03821115612a3c57600080fd5b6020019150600581901b3603821315612a5457600080fd5b9250929050565b6020808252600990820152684249535f535441544560b81b604082015260600190565b600082821015612a9057612a906127ee565b500390565b6020808252601190820152704241445f4348414c4c454e47455f504f5360781b604082015260600190565b60008219821115612ad357612ad36127ee565b500190565b602080825260089082015267544f4f5f4c4f4e4760c01b604082015260600190565b8551815260018060a01b03602087015116602082015284604082015283606082015260a060808201528160a0820152818360c0830137600081830160c090810191909152601f909201601f19160101949350505050565b600060208284031215612b6357600080fd5b5051919050565b60408101612b7784612948565b9281526020015290565b6000606082018583526020858185015260606040850152818551808452608086019150828701935060005b81811015612bc857845183529383019391830191600101612bac565b509098975050505050505050565b83815260006020848184015260408301845182860160005b82811015612c0a57815184529284019290840190600101612bee565b509198975050505050505050565b634e487b7160e01b600052601260045260246000fd5b600082612c3d57612c3d612c18565b500490565b6000816000190483118215151615612c5c57612c5c6127ee565b500290565b600082612c7057612c70612c18565b50069056fea2646970667358221220d1bac57c40e879ffe5492c445773e1293aadfc210845af4536fc292e062be3e164736f6c63430008090033
Deployed Bytecode
0x608060405234801561001057600080fd5b50600436106101115760003560e01c80638f1d3776116100ad578063e78cea9211610071578063e78cea921461031a578063ee35f3271461032d578063f26a62c614610340578063f8c8765e14610353578063fb7be0a11461036657600080fd5b80638f1d3776146102055780639ede42b9146102a8578063a521b032146102cb578063d248d124146102de578063dc74bf8b146102f157600080fd5b806314eab5e7146101165780631b45c86a1461014657806323a9ef231461015b5780633504f1d7146101865780633690b011146101995780635038934d146101ac57806356e9df97146101bf5780635ef489e6146101d25780637fd07a9c146101e5575b600080fd5b610129610124366004612241565b610379565b6040516001600160401b0390911681526020015b60405180910390f35b6101596101543660046122d4565b6106f0565b005b61016e6101693660046122d4565b6107c0565b6040516001600160a01b03909116815260200161013d565b60025461016e906001600160a01b031681565b61016e6101a73660046122ef565b6107e4565b6101596101ba366004612308565b61081a565b6101596101cd3660046122d4565b610900565b600054610129906001600160401b031681565b6101f86101f33660046122d4565b610a6e565b60405161013d919061238c565b6102956102133660046122ef565b6001602081815260009283526040928390208351808501855281546001600160a01b0390811682529382015481840152845180860190955260028201549093168452600381015491840191909152600481015460058201546006830154600790930154939493919290916001600160401b03811690600160401b900460ff1687565b60405161013d97969594939291906123fe565b6102bb6102b63660046122d4565b610b47565b604051901515815260200161013d565b6101596102d9366004612461565b610b68565b6101596102ec366004612505565b610fde565b61016e6102ff3660046122ef565b6006602052600090815260409020546001600160a01b031681565b60045461016e906001600160a01b031681565b60035461016e906001600160a01b031681565b60055461016e906001600160a01b031681565b610159610361366004612597565b61142a565b6101596103743660046125f3565b611556565b6002546000906001600160a01b031633146103ce5760405162461bcd60e51b815260206004820152601060248201526f13d3931657d493d313155417d0d2105360821b60448201526064015b60405180910390fd5b6040805160028082526060820183526000926020830190803683370190505090506104936103ff60208b018b612697565b61048e8a60005b6080020180360381019061041a9190612756565b8051805160209182015192820151805190830151604080516c23b637b130b61039ba30ba329d60991b81870152602d810194909452604d8401959095526001600160c01b031960c092831b8116606d850152911b1660758201528251808203605d018152607d909101909252815191012090565b611cc4565b816000815181106104a6576104a6612681565b60209081029190910101526104d58960016020020160208101906104ca9190612697565b61048e8a6001610406565b816001815181106104e8576104e8612681565b6020908102919091010152600080548190819061050d906001600160401b0316612804565b91906101000a8154816001600160401b0302191690836001600160401b031602179055905060006001600160401b0316816001600160401b031614156105555761055561282b565b6001600160401b0381166000908152600160205260408120600581018d90559061058f61058a368d90038d0160808e01612756565b611de8565b905060026105a360408e0160208f01612697565b60038111156105b4576105b4612362565b14806105e2575060006105d76105d2368e90038e0160808f01612756565b611dfd565b6001600160401b0316115b156105f557806105f181612804565b9150505b6007820180546040805180820182526001600160a01b038d811680835260209283018d90526002880180546001600160a01b03199081169092179055600388018d905583518085018552918e16808352919092018b90528654909116178555600185018990554260048601556001600160401b0384811668ffffffffffffffffff1990931692909217600160401b179092559051908416907f76604fe17af46c9b5f53ffe99ff23e0f655dab91886b07ac1fc0254319f7145a906106bf908e90608082019061288b565b60405180910390a26106dd8360008c6001600160401b031687611e0c565b5090925050505b98975050505050505050565b60006001600160401b038216600090815260016020526040902060070154600160401b900460ff16600281111561072957610729612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906107695760405162461bcd60e51b81526004016103c591906128a7565b5061077381610b47565b6107b25760405162461bcd60e51b815260206004820152601060248201526f54494d454f55545f444541444c494e4560801b60448201526064016103c5565b6107bd816000611ea2565b50565b6001600160401b03166000908152600160205260409020546001600160a01b031690565b6000818152600660205260408120546001600160a01b0316806108145750506005546001600160a01b0316919050565b92915050565b306001600160a01b037f000000000000000000000000ba8b7fb486eb8698c980194e934404c2ae07806c1614156108635760405162461bcd60e51b81526004016103c5906128fc565b7fb53127684a568b3173ae13b9f8a6016e243e63b6e8ee1178d6a717850b5d61038054336001600160a01b038216146108c057604051631194af8760e11b81523360048201526001600160a01b03821660248201526044016103c5565b505060009182526006602052604090912080546001600160a01b039283166001600160a01b03199182161790915560058054939092169216919091179055565b6002546001600160a01b0316331461094d5760405162461bcd60e51b815260206004820152601060248201526f2727aa2fa922a9afa922a1a2a4ab22a960811b60448201526064016103c5565b60006001600160401b038216600090815260016020526040902060070154600160401b900460ff16600281111561098657610986612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906109c65760405162461bcd60e51b81526004016103c591906128a7565b506001600160401b038116600081815260016020819052604080832080546001600160a01b031990811682559281018490556002810180549093169092556003808301849055600483018490556005830184905560068301939093556007909101805468ffffffffffffffffff19169055517ffdaece6c274a4b56af16761f83fd6b1062823192630ea08e019fdf9b2d747f4091610a6391612958565b60405180910390a250565b610a76612197565b6001600160401b0382811660009081526001602081815260409283902083516101208101855281546001600160a01b0390811660e0830190815294830154610100830152938152845180860186526002808401549095168152600383015481850152928101929092526004810154938201939093526005830154606082015260068301546080820152600783015493841660a08201529260c0840191600160401b90910460ff1690811115610b2d57610b2d612362565b6002811115610b3e57610b3e612362565b90525092915050565b6001600160401b038116600090815260016020526040812061081490611fd0565b6001600160401b038416600090815260016020526040812085918591610b8d846107c0565b6001600160a01b0316336001600160a01b031614610bbd5760405162461bcd60e51b81526004016103c59061296b565b610bc684610b47565b15610be35760405162461bcd60e51b81526004016103c590612990565b6000826002811115610bf757610bf7612362565b1415610c655760006007820154600160401b900460ff166002811115610c1f57610c1f612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b81525090610c5f5760405162461bcd60e51b81526004016103c591906128a7565b50610d24565b6001826002811115610c7957610c79612362565b1415610cc35760016007820154600160401b900460ff166002811115610ca157610ca1612362565b14610cbe5760405162461bcd60e51b81526004016103c5906129b7565b610d24565b6002826002811115610cd757610cd7612362565b1415610d1c5760026007820154600160401b900460ff166002811115610cff57610cff612362565b14610cbe5760405162461bcd60e51b81526004016103c5906129df565b610d2461282b565b610d7283356020850135610d3b6040870187612a0b565b80806020026020016040519081016040528093929190818152602001838360200280828437600092019190915250611fe892505050565b816006015414610d945760405162461bcd60e51b81526004016103c590612a5b565b6002610da36040850185612a0b565b90501080610dce57506001610dbb6040850185612a0b565b610dc6929150612a7e565b836060013510155b15610deb5760405162461bcd60e51b81526004016103c590612a95565b600080610df78961201f565b9150915060018111610e375760405162461bcd60e51b81526020600482015260096024820152681513d3d7d4d213d49560ba1b60448201526064016103c5565b806028811115610e45575060285b610e50816001612ac0565b8814610e8d5760405162461bcd60e51b815260206004820152600c60248201526b57524f4e475f44454752454560a01b60448201526064016103c5565b50610ed78989896000818110610ea557610ea5612681565b602002919091013590508a8a610ebc600182612a7e565b818110610ecb57610ecb612681565b905060200201356120b0565b610f168a83838b8b80806020026020016040519081016040528093929190818152602001838360200280828437600092019190915250611e0c92505050565b50600090505b6007820154600160401b900460ff166002811115610f3c57610f3c612362565b1415610f485750610fd5565b6040805180820190915281546001600160a01b03168152600182015460208201526004820154610f789042612a7e565b81602001818151610f899190612a7e565b90525060028201805483546001600160a01b038083166001600160a01b031992831617865560038601805460018801558551929093169116179091556020909101519055426004909101555b50505050505050565b6001600160401b038416600090815260016020526040902084908490600290611006846107c0565b6001600160a01b0316336001600160a01b0316146110365760405162461bcd60e51b81526004016103c59061296b565b61103f84610b47565b1561105c5760405162461bcd60e51b81526004016103c590612990565b600082600281111561107057611070612362565b14156110de5760006007820154600160401b900460ff16600281111561109857611098612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906110d85760405162461bcd60e51b81526004016103c591906128a7565b5061119d565b60018260028111156110f2576110f2612362565b141561113c5760016007820154600160401b900460ff16600281111561111a5761111a612362565b146111375760405162461bcd60e51b81526004016103c5906129b7565b61119d565b600282600281111561115057611150612362565b14156111955760026007820154600160401b900460ff16600281111561117857611178612362565b146111375760405162461bcd60e51b81526004016103c5906129df565b61119d61282b565b6111b483356020850135610d3b6040870187612a0b565b8160060154146111d65760405162461bcd60e51b81526004016103c590612a5b565b60026111e56040850185612a0b565b90501080611210575060016111fd6040850185612a0b565b611208929150612a7e565b836060013510155b1561122d5760405162461bcd60e51b81526004016103c590612a95565b6001600160401b038816600090815260016020526040812090806112508a61201f565b9092509050600181146112755760405162461bcd60e51b81526004016103c590612ad8565b50600061128583600501546107e4565b60408051808201825260078601546001600160401b031681526004546001600160a01b0390811660208301529290921691635d3adcfb9185906112ca908f018f612a0b565b8f606001358181106112de576112de612681565b905060200201358d8d6040518663ffffffff1660e01b8152600401611307959493929190612afa565b60206040518083038186803b15801561131f57600080fd5b505afa158015611333573d6000803e3d6000fd5b505050506040513d601f19601f820116820180604052508101906113579190612b51565b905061136660408b018b612a0b565b61137560608d01356001612ac0565b81811061138457611384612681565b905060200201358114156113c95760405162461bcd60e51b815260206004820152600c60248201526b14d0535157d3d4d417d1539160a21b60448201526064016103c5565b6040516001600160401b038c16907fc2cc42e04ff8c36de71c6a2937ea9f161dd0dd9e175f00caa26e5200643c781e90600090a261141e8b6001600160401b0316600090815260016020526040812060060155565b5060009150610f1c9050565b306001600160a01b037f000000000000000000000000ba8b7fb486eb8698c980194e934404c2ae07806c1614156114735760405162461bcd60e51b81526004016103c5906128fc565b6002546001600160a01b0316156114bb5760405162461bcd60e51b815260206004820152600c60248201526b1053149150511657d253925560a21b60448201526064016103c5565b6001600160a01b0384166115065760405162461bcd60e51b81526020600482015260126024820152712727afa922a9aaa62a2fa922a1a2a4ab22a960711b60448201526064016103c5565b600280546001600160a01b039586166001600160a01b0319918216179091556003805494861694821694909417909355600480549285169284169290921790915560058054919093169116179055565b6001600160401b03851660009081526001602081905260409091208691869161157e846107c0565b6001600160a01b0316336001600160a01b0316146115ae5760405162461bcd60e51b81526004016103c59061296b565b6115b784610b47565b156115d45760405162461bcd60e51b81526004016103c590612990565b60008260028111156115e8576115e8612362565b14156116565760006007820154600160401b900460ff16600281111561161057611610612362565b1415604051806040016040528060078152602001661393d7d0d2105360ca1b815250906116505760405162461bcd60e51b81526004016103c591906128a7565b50611715565b600182600281111561166a5761166a612362565b14156116b45760016007820154600160401b900460ff16600281111561169257611692612362565b146116af5760405162461bcd60e51b81526004016103c5906129b7565b611715565b60028260028111156116c8576116c8612362565b141561170d5760026007820154600160401b900460ff1660028111156116f0576116f0612362565b146116af5760405162461bcd60e51b81526004016103c5906129df565b61171561282b565b61172c83356020850135610d3b6040870187612a0b565b81600601541461174e5760405162461bcd60e51b81526004016103c590612a5b565b600261175d6040850185612a0b565b90501080611788575060016117756040850185612a0b565b611780929150612a7e565b836060013510155b156117a55760405162461bcd60e51b81526004016103c590612a95565b60018510156117ec5760405162461bcd60e51b815260206004820152601360248201527210d2105313115391d157d513d3d7d4d213d495606a1b60448201526064016103c5565b650800000000008511156118375760405162461bcd60e51b81526020600482015260126024820152714348414c4c454e47455f544f4f5f4c4f4e4760701b60448201526064016103c5565b6118798861185961184b60208b018b612697565b8960005b6020020135611cc4565b61187461186c60408c0160208d01612697565b8a600161184f565b6120b0565b6001600160401b0389166000908152600160205260408120908061189c8b61201f565b91509150806001146118c05760405162461bcd60e51b81526004016103c590612ad8565b60016118cf60208c018c612697565b60038111156118e0576118e0612362565b1461199a576118f560408b0160208c01612697565b600381111561190657611906612362565b61191360208c018c612697565b600381111561192457611924612362565b1480156119355750883560208a0135145b6119715760405162461bcd60e51b815260206004820152600d60248201526c48414c5445445f4348414e474560981b60448201526064016103c5565b6119928c6001600160401b0316600090815260016020526040812060060155565b505050611bff565b60026119ac60408c0160208d01612697565b60038111156119bd576119bd612362565b1415611a0657883560208a013514611a065760405162461bcd60e51b815260206004820152600c60248201526b4552524f525f4348414e474560a01b60448201526064016103c5565b6040805160028082526060820183526000926020830190803683370190505090506000611a3685600501546107e4565b60058601546040516301265ef960e21b81528d35600482015260248101919091529091506001600160a01b038216906304997be49060440160206040518083038186803b158015611a8657600080fd5b505afa158015611a9a573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611abe9190612b51565b82600081518110611ad157611ad1612681565b60209081029190910101526001600160a01b03811663d8558b878d6001602002016020810190611b019190612697565b8d600160200201356040518363ffffffff1660e01b8152600401611b26929190612b6a565b60206040518083038186803b158015611b3e57600080fd5b505afa158015611b52573d6000803e3d6000fd5b505050506040513d601f19601f82011682018060405250810190611b769190612b51565b82600181518110611b8957611b89612681565b602090810291909101015260078501805460ff60401b1916600160411b179055611bb68e60008c85611e0c565b8d6001600160401b03167f24e032e170243bbea97e140174b22dc7e54fb85925afbf52c70e001cd6af16db85604051611bf191815260200190565b60405180910390a250505050505b60006007820154600160401b900460ff166002811115611c2157611c21612362565b1415611c2d5750611cba565b6040805180820190915281546001600160a01b03168152600182015460208201526004820154611c5d9042612a7e565b81602001818151611c6e9190612a7e565b90525060028201805483546001600160a01b038083166001600160a01b031992831617865560038601805460018801558551929093169116179091556020909101519055426004909101555b5050505050505050565b60006001836003811115611cda57611cda612362565b1415611d20576040516b213637b1b59039ba30ba329d60a11b6020820152602c8101839052604c015b604051602081830303815290604052805190602001209050610814565b6002836003811115611d3457611d34612362565b1415611d6a5760405174213637b1b59039ba30ba32961032b93937b932b21d60591b602082015260358101839052605501611d03565b6003836003811115611d7e57611d7e612362565b1415611dad5760405174213637b1b59039ba30ba3296103a37b7903330b91d60591b6020820152603501611d03565b60405162461bcd60e51b815260206004820152601060248201526f4241445f424c4f434b5f53544154555360801b60448201526064016103c5565b6020810151600090815b602002015192915050565b60208101516000906001611df2565b6001821015611e1d57611e1d61282b565b600281511015611e2f57611e2f61282b565b6000611e3c848484611fe8565b6001600160401b038616600081815260016020526040908190206006018390555191925082917f86b34e9455464834eca718f62d4481437603bb929d8a78ccde5d1bc79fa06d6890611e9390889088908890612b81565b60405180910390a35050505050565b6001600160401b03821660008181526001602081905260408083206002808201805483546001600160a01b0319808216865596850188905595811690915560038301869055600480840187905560058401879055600684019690965560078301805468ffffffffffffffffff1916905590549251630357aa4960e01b8152948501959095526001600160a01b03948516602485018190529285166044850181905290949293909290911690630357aa4990606401600060405180830381600087803b158015611f7057600080fd5b505af1158015611f84573d6000803e3d6000fd5b50505050846001600160401b03167ffdaece6c274a4b56af16761f83fd6b1062823192630ea08e019fdf9b2d747f4085604051611fc19190612958565b60405180910390a25050505050565b6001810154600090611fe183612185565b1192915050565b6000838383604051602001611fff93929190612bd6565b6040516020818303038152906040528051906020012090505b9392505050565b6000808060016120326040860186612a0b565b61203d929150612a7e565b905061204d816020860135612c2e565b915061205d606085013583612c42565b612068908535612ac0565b925060026120796040860186612a0b565b612084929150612a7e565b846060013514156120aa5761209d816020860135612c61565b6120a79083612ac0565b91505b50915091565b816120be6040850185612a0b565b85606001358181106120d2576120d2612681565b90506020020135146121145760405162461bcd60e51b815260206004820152600b60248201526a15d493d391d7d4d510549560aa1b60448201526064016103c5565b806121226040850185612a0b565b61213160608701356001612ac0565b81811061214057612140612681565b9050602002013514156121805760405162461bcd60e51b815260206004820152600860248201526714d0535157d1539160c21b60448201526064016103c5565b505050565b60008160040154426108149190612a7e565b604080516101208101909152600060e08201818152610100830191909152819081526020016121d6604080518082019091526000808252602082015290565b815260006020820181905260408201819052606082018190526080820181905260a09091015290565b806040810183101561081457600080fd5b80356001600160401b038116811461222757600080fd5b919050565b6001600160a01b03811681146107bd57600080fd5b600080600080600080600080610200898b03121561225e57600080fd5b8835975061226f8a60208b016121ff565b965061016089018a81111561228357600080fd5b60608a01965061229281612210565b9550506101808901356122a48161222c565b93506101a08901356122b58161222c565b979a96995094979396929592945050506101c0820135916101e0013590565b6000602082840312156122e657600080fd5b61201882612210565b60006020828403121561230157600080fd5b5035919050565b60008060006060848603121561231d57600080fd5b83356123288161222c565b925060208401359150604084013561233f8161222c565b809150509250925092565b80516001600160a01b03168252602090810151910152565b634e487b7160e01b600052602160045260246000fd5b6003811061238857612388612362565b9052565b6000610120820190506123a082845161234a565b60208301516123b2604084018261234a565b5060408301516080830152606083015160a0830152608083015160c08301526001600160401b0360a08401511660e083015260c08301516123f7610100840182612378565b5092915050565b610120810161240d828a61234a565b61241a604083018961234a565b8660808301528560a08301528460c08301526001600160401b03841660e08301526106e4610100830184612378565b60006080828403121561245b57600080fd5b50919050565b6000806000806060858703121561247757600080fd5b61248085612210565b935060208501356001600160401b038082111561249c57600080fd5b6124a888838901612449565b945060408701359150808211156124be57600080fd5b818701915087601f8301126124d257600080fd5b8135818111156124e157600080fd5b8860208260051b85010111156124f657600080fd5b95989497505060200194505050565b6000806000806060858703121561251b57600080fd5b61252485612210565b935060208501356001600160401b038082111561254057600080fd5b61254c88838901612449565b9450604087013591508082111561256257600080fd5b818701915087601f83011261257657600080fd5b81358181111561258557600080fd5b8860208285010111156124f657600080fd5b600080600080608085870312156125ad57600080fd5b84356125b88161222c565b935060208501356125c88161222c565b925060408501356125d88161222c565b915060608501356125e88161222c565b939692955090935050565b600080600080600060e0868803121561260b57600080fd5b61261486612210565b945060208601356001600160401b0381111561262f57600080fd5b61263b88828901612449565b94505061264b87604088016121ff565b925061265a87608088016121ff565b9497939650919460c0013592915050565b634e487b7160e01b600052604160045260246000fd5b634e487b7160e01b600052603260045260246000fd5b6000602082840312156126a957600080fd5b81356004811061201857600080fd5b604080519081016001600160401b03811182821017156126da576126da61266b565b60405290565b600082601f8301126126f157600080fd5b604051604081018181106001600160401b03821117156127135761271361266b565b806040525080604084018581111561272a57600080fd5b845b8181101561274b5761273d81612210565b83526020928301920161272c565b509195945050505050565b60006080828403121561276857600080fd5b604051604081018181106001600160401b038211171561278a5761278a61266b565b604052601f8301841361279c57600080fd5b6127a46126b8565b8060408501868111156127b657600080fd5b855b818110156127d05780358452602093840193016127b8565b508184526127de87826126e0565b6020850152509195945050505050565b634e487b7160e01b600052601160045260246000fd5b60006001600160401b0380831681811415612821576128216127ee565b6001019392505050565b634e487b7160e01b600052600160045260246000fd5b604081833760006040838101828152908301915b6002811015612884576001600160401b0361286f84612210565b16825260209283019290910190600101612855565b5050505050565b610100810161289a8285612841565b6120186080830184612841565b600060208083528351808285015260005b818110156128d4578581018301518582016040015282016128b8565b818111156128e6576000604083870101525b50601f01601f1916929092016040019392505050565b6020808252602c908201527f46756e6374696f6e206d7573742062652063616c6c6564207468726f7567682060408201526b19195b1959d85d1958d85b1b60a21b606082015260800190565b600481106107bd576107bd612362565b6020810161296583612948565b91905290565b6020808252600b908201526a21a420a62fa9a2a72222a960a91b604082015260600190565b6020808252600d908201526c4348414c5f444541444c494e4560981b604082015260600190565b6020808252600e908201526d4348414c5f4e4f545f424c4f434b60901b604082015260600190565b60208082526012908201527121a420a62fa727aa2fa2ac22a1aaaa24a7a760711b604082015260600190565b6000808335601e19843603018112612a2257600080fd5b8301803591506001600160401b03821115612a3c57600080fd5b6020019150600581901b3603821315612a5457600080fd5b9250929050565b6020808252600990820152684249535f535441544560b81b604082015260600190565b600082821015612a9057612a906127ee565b500390565b6020808252601190820152704241445f4348414c4c454e47455f504f5360781b604082015260600190565b60008219821115612ad357612ad36127ee565b500190565b602080825260089082015267544f4f5f4c4f4e4760c01b604082015260600190565b8551815260018060a01b03602087015116602082015284604082015283606082015260a060808201528160a0820152818360c0830137600081830160c090810191909152601f909201601f19160101949350505050565b600060208284031215612b6357600080fd5b5051919050565b60408101612b7784612948565b9281526020015290565b6000606082018583526020858185015260606040850152818551808452608086019150828701935060005b81811015612bc857845183529383019391830191600101612bac565b509098975050505050505050565b83815260006020848184015260408301845182860160005b82811015612c0a57815184529284019290840190600101612bee565b509198975050505050505050565b634e487b7160e01b600052601260045260246000fd5b600082612c3d57612c3d612c18565b500490565b6000816000190483118215151615612c5c57612c5c6127ee565b500290565b600082612c7057612c70612c18565b50069056fea2646970667358221220d1bac57c40e879ffe5492c445773e1293aadfc210845af4536fc292e062be3e164736f6c63430008090033
Loading...
Loading
Loading...
Loading
Multichain Portfolio | 34 Chains
Chain | Token | Portfolio % | Price | Amount | Value |
---|
Loading...
Loading
Loading...
Loading
A contract address hosts a smart contract, which is a set of code stored on the blockchain that runs when predetermined conditions are met. Learn more about addresses in our Knowledge Base.