Skip to content

Commit

Permalink
Merge pull request #98 from RealityETH/feature-fork-integration-reapply
Browse files Browse the repository at this point in the history
Integrates adjudication of questions on L2 via the zkEVM bridge
  • Loading branch information
edmundedgar authored Nov 28, 2023
2 parents 8758eb2 + 1ebd8bc commit c6f295c
Show file tree
Hide file tree
Showing 29 changed files with 3,522 additions and 430 deletions.
12 changes: 6 additions & 6 deletions .solhintignore
Original file line number Diff line number Diff line change
@@ -1,12 +1,13 @@
/contracts/RealityETH_ERC20-3.0.sol
/contracts/Arbitrator.sol
/contracts/lib/reality-eth/RealityETH_ERC20-3.0.sol
/contracts/lib/reality-eth/RealityETH-3.0.sol
/contracts/lib/reality-eth/Arbitrator.sol
/contracts/lib/reality-eth/BalanceHolder.sol
/contracts/interfaces/IBalanceHolder.sol
/contracts/interfaces/IBalanceHolder_ERC20.sol
/contracts/interfaces/IArbitrator.sol
/contracts/interfaces/IRealityETH.sol
/contracts/ForkableRealityETH_ERC20.sol
/contracts/ForkableRealityETH_ERC20.sol
/contracts/Auction_ERC20.sol
/contracts/mixin/BalanceHolder.sol
/contracts/mixin/BalanceHolder_ERC20.sol
/contracts/WhitelistArbitrator.sol
/contracts/mixin/Owned.sol
/contracts/interfaces/IZKBridge.sol
Expand All @@ -18,4 +19,3 @@
/contracts/ERC20Mint.sol
/contracts/TokenBridge.sol
/contracts/ERC20.sol
/contracts/AdjudicationFramework.sol
344 changes: 166 additions & 178 deletions contracts/AdjudicationFramework.sol

Large diffs are not rendered by default.

223 changes: 0 additions & 223 deletions contracts/Auction_ERC20.sol

This file was deleted.

2 changes: 1 addition & 1 deletion contracts/ForkableRealityETH_ERC20.sol
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

pragma solidity ^0.8.20;

import "./mixin/BalanceHolder_ERC20.sol";
import "./lib/reality-eth/BalanceHolder_ERC20.sol";

import "./interfaces/IForkableRealityETH.sol";

Expand Down
17 changes: 15 additions & 2 deletions contracts/ForkingManager.sol
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,6 @@ contract ForkingManager is IForkingManager, ForkableStructure {
DisputeData public disputeData;
NewImplementations public proposedImplementations;
uint256 public executionTimeForProposal = 0;

uint256 public immutable forkPreparationTime = 1 weeks;

/// @inheritdoc IForkingManager
Expand All @@ -64,6 +63,19 @@ contract ForkingManager is IForkingManager, ForkableStructure {
ForkableStructure.initialize(address(this), _parentContract);
}

function isForkingInitiated() external view returns (bool) {
return (executionTimeForProposal > 0);
}

function isForkingExecuted() external view returns (bool) {
return (children[0] != address(0) || children[1] != address(0));
}

// TODO: If there is any other reason a fork can be prevented, eg the contract can be frozen by governance, add it here.
function canFork() external view returns (bool) {
return (executionTimeForProposal == 0);
}

/**
* @notice function to initiate and schedule the fork
* @param _disputeData the dispute contract and call to identify the dispute
Expand Down Expand Up @@ -165,7 +177,7 @@ contract ForkingManager is IForkingManager, ForkableStructure {
);
initializePackedParameters.chainID = ChainIdManager(chainIdManager)
.getNextUsableChainId();
initializePackedParameters.forkID = newImplementations.forkID;
initializePackedParameters.forkID = newImplementations.forkID > 0 ? newImplementations.forkID : IPolygonZkEVM(zkEVM).forkID();
IForkableZkEVM(newInstances.zkEVM.two).initialize(
newInstances.forkingManager.two,
zkEVM,
Expand Down Expand Up @@ -260,4 +272,5 @@ contract ForkingManager is IForkingManager, ForkableStructure {
newInstances.bridge.two
);
}

}
80 changes: 80 additions & 0 deletions contracts/L1GlobalChainInfoPublisher.sol
Original file line number Diff line number Diff line change
@@ -0,0 +1,80 @@
// SPDX-License-Identifier: GPL-3.0-only

pragma solidity ^0.8.20;

import {IForkingManager} from "./interfaces/IForkingManager.sol";
import {IForkableStructure} from "./interfaces/IForkableStructure.sol";
import {IPolygonZkEVMBridge} from "@RealityETH/zkevm-contracts/contracts/interfaces/IPolygonZkEVMBridge.sol";
import {IPolygonZkEVM} from "@RealityETH/zkevm-contracts/contracts/interfaces/IPolygonZkEVM.sol";

contract L1GlobalChainInfoPublisher {

/// @notice Function to send the data about a fork to a contract on L2.
/// @param _bridge The bridge to send the data through
/// @param _l2ChainInfo The L2ChainInfo contract on L2 to send the data to
/// @param _ancestorForkingManager The ForkingManager to send data about, if referring to a previous fork (unusual)
/// @param _maxAncestors The number of forks back to look when looking for the _ancestorForkingManager
/// @dev Normally someone would call this right after a fork, _ancestorForkingManager and _maxAncestors should only be used in wierd cases
function updateL2ChainInfo(address _bridge, address _l2ChainInfo, address _ancestorForkingManager, uint256 _maxAncestors) external {

// Ask the bridge its forkmanager
IForkingManager forkingManager = IForkingManager(IForkableStructure(_bridge).forkmanager());

// If we passed an _ancestorForkingManager, crawl up and find that as our ancestor and send data for that over the current bridge.
// We will refuse to send data about a forkingManager that isn't an ancestor of the one used by the bridge.
// Normally we won't need to do this because we'll update L2ChainInfo as soon as there's a fork
// This is here just in case there's some weird availability issue and we couldn't send an update before the next fork.
// NB If we keep forking every week forever you will eventually become unable to get the earliest before running out of gas
if (_ancestorForkingManager != address(0)) {
bool found = false;
for(uint256 i = 0; i < _maxAncestors; i++) {
forkingManager = IForkingManager(forkingManager.parentContract());
if (address(forkingManager) == address(0)) {
break; // No more ancestors
}
if (_ancestorForkingManager == address(forkingManager)) {
found = true;
break;
}
}
require(found, "Ancestor not found");
}

// Dispute results will need to come from the parent ForkingManager
IForkingManager parentForkingManager = IForkingManager(forkingManager.parentContract());

bool isL1;
address disputeContract;
bytes32 disputeContent;

// Fork results: 0 for the genesis, 1 for yes, 2 for no
uint8 forkResult = 0;

// Find out whether we are the "yes" fork or the "no" fork
if (address(parentForkingManager) != address(0)) {
(address child1, address child2) = parentForkingManager.getChildren();
if (child1 == address(forkingManager)) {
forkResult = 1;
} else if (child2 == address(forkingManager)) {
forkResult = 2;
} else {
revert("Unexpected child address");
}
(isL1, disputeContract, disputeContent) = forkingManager.disputeData();
}

uint256 arbitrationFee = forkingManager.arbitrationFee();
address forkonomicToken = forkingManager.forkonomicToken();
uint64 chainId = IPolygonZkEVM(forkingManager.zkEVM()).chainID();

bytes memory data = abi.encode(chainId, forkonomicToken, arbitrationFee, isL1, disputeContract, disputeContent, forkResult);

IPolygonZkEVMBridge(_bridge).bridgeMessage(
uint32(1),
_l2ChainInfo,
true,
data
);
}

}
Loading

0 comments on commit c6f295c

Please sign in to comment.