Sepolia Testnet

Contract

0xeae835289f34dE789C370929d33458919c106a22
Source Code Source Code

Overview

ETH Balance

0 ETH

More Info

Multichain Info

N/A
Transaction Hash
Method
Block
From
To
Amount
Send Giga Root98455672025-12-15 11:34:0061 days ago1765798440IN
0xeae83528...19c106a22
0.05 ETH0.000000230.00100092
Send Giga Root98455672025-12-15 11:34:0061 days ago1765798440IN
0xeae83528...19c106a22
0.05 ETH0.000000250.00100092
Send Giga Root98455672025-12-15 11:34:0061 days ago1765798440IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100092
Update Giga Root98455642025-12-15 11:33:1261 days ago1765798392IN
0xeae83528...19c106a22
0 ETH0.000000230.00100085
Update Giga Root98455642025-12-15 11:33:1261 days ago1765798392IN
0xeae83528...19c106a22
0 ETH0.000000230.00100085
Update Giga Root98455642025-12-15 11:33:1261 days ago1765798392IN
0xeae83528...19c106a22
0 ETH0.000000240.00100085
Send Giga Root98455172025-12-15 11:23:4861 days ago1765797828IN
0xeae83528...19c106a22
0.05 ETH0.000000230.00100048
Send Giga Root98455172025-12-15 11:23:4861 days ago1765797828IN
0xeae83528...19c106a22
0.05 ETH0.000000250.00100048
Send Giga Root98455172025-12-15 11:23:4861 days ago1765797828IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100048
Update Giga Root98455132025-12-15 11:23:0061 days ago1765797780IN
0xeae83528...19c106a22
0 ETH0.000000230.00100056
Update Giga Root98455132025-12-15 11:23:0061 days ago1765797780IN
0xeae83528...19c106a22
0 ETH0.000000240.00100056
Update Giga Root98455122025-12-15 11:22:4861 days ago1765797768IN
0xeae83528...19c106a22
0 ETH0.000000240.00100057
Send Giga Root98454682025-12-15 11:14:0061 days ago1765797240IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100027
Send Giga Root98454682025-12-15 11:14:0061 days ago1765797240IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100027
Send Giga Root98454662025-12-15 11:13:3661 days ago1765797216IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100029
Update Giga Root98454652025-12-15 11:13:2461 days ago1765797204IN
0xeae83528...19c106a22
0 ETH0.000000230.00099996
Update Giga Root98454652025-12-15 11:13:2461 days ago1765797204IN
0xeae83528...19c106a22
0 ETH0.000000240.00099996
Update Giga Root98454632025-12-15 11:13:0061 days ago1765797180IN
0xeae83528...19c106a22
0 ETH0.000000240.00099997
Send Giga Root98451172025-12-15 10:03:4861 days ago1765793028IN
0xeae83528...19c106a22
0.05 ETH0.000000240.00100014
Send Giga Root98451162025-12-15 10:03:3661 days ago1765793016IN
0xeae83528...19c106a22
0.05 ETH0.000000250.00100014
Send Giga Root98451162025-12-15 10:03:3661 days ago1765793016IN
0xeae83528...19c106a22
0.05 ETH0.000000260.00100014
Update Giga Root98451142025-12-15 10:03:1261 days ago1765792992IN
0xeae83528...19c106a22
0 ETH0.000000240.00100013
Update Giga Root98451132025-12-15 10:03:0061 days ago1765792980IN
0xeae83528...19c106a22
0 ETH0.000000230.00100012
Update Giga Root98451132025-12-15 10:03:0061 days ago1765792980IN
0xeae83528...19c106a22
0 ETH0.000000240.00100012
Send Giga Root98450692025-12-15 9:54:0061 days ago1765792440IN
0xeae83528...19c106a22
0.05 ETH0.000000240.00100001
View all transactions

Latest 25 internal transactions (View All)

Advanced mode:
Parent Transaction Hash Method Block
From
To
Amount
Receive Giga Roo...98455672025-12-15 11:34:0061 days ago1765798440
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98455672025-12-15 11:34:0061 days ago1765798440
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98455672025-12-15 11:34:0061 days ago1765798440
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98455172025-12-15 11:23:4861 days ago1765797828
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98455172025-12-15 11:23:4861 days ago1765797828
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98455172025-12-15 11:23:4861 days ago1765797828
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98454682025-12-15 11:14:0061 days ago1765797240
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98454682025-12-15 11:14:0061 days ago1765797240
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98454662025-12-15 11:13:3661 days ago1765797216
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98451172025-12-15 10:03:4861 days ago1765793028
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98451162025-12-15 10:03:3661 days ago1765793016
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98451162025-12-15 10:03:3661 days ago1765793016
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450692025-12-15 9:54:0061 days ago1765792440
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450662025-12-15 9:53:2461 days ago1765792404
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450662025-12-15 9:53:2461 days ago1765792404
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450162025-12-15 9:43:2461 days ago1765791804
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450162025-12-15 9:43:2461 days ago1765791804
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98450162025-12-15 9:43:2461 days ago1765791804
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98445272025-12-15 8:05:1261 days ago1765785912
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98445272025-12-15 8:05:1261 days ago1765785912
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98445272025-12-15 8:05:1261 days ago1765785912
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98445272025-12-15 8:05:1261 days ago1765785912
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98444692025-12-15 7:53:3661 days ago1765785216
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98444682025-12-15 7:53:2461 days ago1765785204
0xeae83528...19c106a22
0.05 ETH
Receive Giga Roo...98444682025-12-15 7:53:2461 days ago1765785204
0xeae83528...19c106a22
0.05 ETH
View All Internal Transactions
Loading...
Loading
Loading...
Loading

Block Transaction Difficulty Gas Used Reward
View All Blocks Produced

Validator Index Block Amount
View All Withdrawals

Transaction Hash Block Value Eth2 PubKey Valid
View All Deposits
Loading...
Loading

Contract Source Code Verified (Exact Match)

Contract Name:
GigaBridge

Compiler Version
v0.8.29+commit.ab55807c

Optimization Enabled:
Yes with 1000 runs

Other Settings:
cancun EvmVersion
// SPDX-License-Identifier: MIT

pragma solidity 0.8.29;

import {IGigaBridge} from "./interfaces/IGigaBridge.sol";
import {IGigaRootProvider, ILocalRootRecipient, ILocalRootProvider, IGigaRootRecipient} from "./interfaces/IRootMessengers.sol";
import {PoseidonT3} from "poseidon-solidity/PoseidonT3.sol";
import {LazyIMT, LazyIMTData} from "@zk-kit/lazy-imt.sol/LazyIMT.sol";

contract GigaBridge is IGigaBridge, ILocalRootRecipient, IGigaRootProvider  {
    // get gigaRootFrom destination chain. look up at which block that got created at with: ConstructedNewGigaRoot(gigaRoot)
    // get all leaves of giga tree by scanning for all indexes with ReceivedNewLocalRoot. Start at the block number found above ^
    // get allIndexes you need by looking at amountOfLocalRoots
    // work ur way down until you found all indexes.

    uint256 public gigaRoot; // keep this here pls so it's alway at slot 0 for L1SLOAD on scroll

    LazyIMTData public rootTreeData; // does this need to be public? yes? maybe we can sync clients faster somehow?
    uint8 public maxTreeDepth;

    mapping(address => uint40) private localRootProvidersIndexes; // getters are public btw
    mapping(address => uint256) public localRootBlockNumbers; // current blocknumber per root. History is in events. We need this to check that incoming roots are not older than current
    uint256 public amountOfLocalRoots;

    event SentGigaRoot(uint256 indexed gigaRoot);

    /**
     * @notice Initialize the root bridge
     * @param _gigaRootRecipients - the L1 contracts that can receive roots from corresponding locals
     */
    constructor(address[] memory _gigaRootRecipients, uint8 _maxTreeDepth) {
        maxTreeDepth = _maxTreeDepth;
        // init doesn't add any leaves. But the leaves are all 0 by default!
        LazyIMT.init(rootTreeData, _maxTreeDepth);

        // for each L1LocalRootProvider...
        for (uint40 i = 0; i < _gigaRootRecipients.length; i++) {
            _setLocalRootProvidersIndex(_gigaRootRecipients[i], i);
            LazyIMT.insert(rootTreeData,0); // TODO this is kind of expensive way to get around the error from `lazyIMT.update`: `leaf must exist`
        }
        amountOfLocalRoots = _gigaRootRecipients.length; 

        // other wise gigaRoot can be 0. Which i cant see how that would be a issue but it scares so we do this to be safe
        gigaRoot = LazyIMT.root(rootTreeData, maxTreeDepth);
    }

    function _setLocalRootProvidersIndex(address _localRootProvider, uint40 index) private {
        localRootProvidersIndexes[_localRootProvider] = index + 1; //+1 because a mapping defaults to 0. so those don't exist!
    }

    function getLocalRootProvidersIndex(address _localRootProvider) public view returns(uint40) {
        return localRootProvidersIndexes[_localRootProvider] - 1; //-1 because a mapping defaults to 0. so those don't exist!
    }

    function isLocalRootProviders(address _localRootProvider) public view returns(bool) {
        return localRootProvidersIndexes[_localRootProvider] > 0;
    }

    /**
     * @notice updates the current gigaRoot by querying for updates from the supplied
     * list of local root providers.  You can pull updates from a subset of local root providers for gas saving (don't have to update to all local root providers).
     */
    function updateGigaRoot(address[] memory _localRootProvider) external {
        // for each localRootProviders
        for (uint40 i = 0; i < _localRootProvider.length; i++) {
            address localRootProvider = _localRootProvider[i];

            // get the index of this localRootProvider (used in updatedLocalRootBlockNumbers and rootTreeData)
            uint40 localRootIndex = getLocalRootProvidersIndex(localRootProvider);

            // make sure this bridgeAdapterAddress was initialized
            require(
                isLocalRootProviders(localRootProvider),
                "Address is not a registered root bridge address"
            );

            // get the most recent l2 root and the l2 block number it came from from this bridge
            (uint256 newLocalRoot, uint256 localRootBlockNumber) = ILocalRootProvider(localRootProvider).getLocalRootAndBlock();

            require(localRootBlockNumber >= localRootBlockNumbers[localRootProvider], "localRoot has to be newer or the same"); 
            localRootBlockNumbers[localRootProvider] = localRootBlockNumber;

            LazyIMT.update(rootTreeData, newLocalRoot, localRootIndex);
            //TODO can we emit 33 events?
            emit ReceivedNewLocalRoot(
                newLocalRoot,
                localRootIndex,
                localRootBlockNumber
            );
        }
        // compute new giga root
        uint256 newGigaRoot = LazyIMT.root(rootTreeData, maxTreeDepth);
        emit ConstructedNewGigaRoot(newGigaRoot);

        // set new gigaRoot in contract
        gigaRoot = newGigaRoot;
    }   

    // TODO this is very convenient to initiated all bridging txs at once but the problem is that every bridge is different
    // so the might require different parameter handed to them by a eoa like scrolls bridge needs a extra gaslimit
    // so we should pull from the gigaRoot from the L1Adapter instead

    // Made this a second function because the addresses that want the gigaRoot
    // might be different from the addresses that are updating their localRoot.
    // since most of the time everyone wants the latest gigaRoot but not everyone has a localRoot that is new
    // Sends the most recent gigaRoot to an array of localRootProviders
    function sendGigaRoot(address[] memory _gigaRootRecipients, uint256[] memory _amounts) public payable {
        uint256 _gigaRoot = gigaRoot;
        emit SentGigaRoot(_gigaRoot);
        for (uint256 i = 0; i < _gigaRootRecipients.length; i++) {
            address gigaRootRecipient = _gigaRootRecipients[i];

            // send the most recent gigaRoot to this LocalRootProvider address. 
            // They provide local roots but also like something back. A gigaRoot :0!!!
           IGigaRootRecipient(gigaRootRecipient).receiveGigaRoot{value: _amounts[i]}(_gigaRoot);
        }
    }


    // above function is more efficient most of the time. This is here to support the IGigaRootProvider 
    // and IGigaRootProvider doesn't do the for loop because L2 adapters only have one recipient (L2Warptoad).
    function sendGigaRoot(address _gigaRootRecipient) public payable{
        uint256 _gigaRoot = gigaRoot;
        emit SentGigaRoot(_gigaRoot);
        IGigaRootRecipient(_gigaRootRecipient).receiveGigaRoot{value: msg.value}(_gigaRoot);
    }

    // // for scroll who needs eth to make the bridge tx
    // // this is kinda getting messy. Next version of gigaBridge should instead only receive leafValues and have a public getter for gigaRoot (history)
    // // then the adapters can handle all these whacky different bridge apis. 
    // // for loops are also bad in gigaBridge, since it forces gigaBridge to know what the bridge api is like before hand. Instead we should just do multi-call or whatever
    // function sendGigaRootPayable(address _gigaRootRecipient) public payable {
    //     IGigaRootRecipient(_gigaRootRecipient).receiveGigaRoot{value: msg.value}(gigaRoot);
    // }
}

File 2 of 7 : Constants.sol
// SPDX-License-Identifier: UNLICENSED
pragma solidity ^0.8.4;

uint256 constant SNARK_SCALAR_FIELD = 21888242871839275222246405745257275088548364400416034343698204186575808495617;
uint8 constant MAX_DEPTH = 32;

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import {PoseidonT3} from "poseidon-solidity/PoseidonT3.sol";
import {SNARK_SCALAR_FIELD, MAX_DEPTH} from "./Constants.sol";

struct LazyIMTData {
    uint40 maxIndex;
    uint40 numberOfLeaves;
    mapping(uint256 => uint256) elements;
}

library InternalLazyIMT {
    uint40 internal constant MAX_INDEX = (1 << 32) - 1;

    uint256 internal constant Z_0 = 0;
    uint256 internal constant Z_1 = 14744269619966411208579211824598458697587494354926760081771325075741142829156;
    uint256 internal constant Z_2 = 7423237065226347324353380772367382631490014989348495481811164164159255474657;
    uint256 internal constant Z_3 = 11286972368698509976183087595462810875513684078608517520839298933882497716792;
    uint256 internal constant Z_4 = 3607627140608796879659380071776844901612302623152076817094415224584923813162;
    uint256 internal constant Z_5 = 19712377064642672829441595136074946683621277828620209496774504837737984048981;
    uint256 internal constant Z_6 = 20775607673010627194014556968476266066927294572720319469184847051418138353016;
    uint256 internal constant Z_7 = 3396914609616007258851405644437304192397291162432396347162513310381425243293;
    uint256 internal constant Z_8 = 21551820661461729022865262380882070649935529853313286572328683688269863701601;
    uint256 internal constant Z_9 = 6573136701248752079028194407151022595060682063033565181951145966236778420039;
    uint256 internal constant Z_10 = 12413880268183407374852357075976609371175688755676981206018884971008854919922;
    uint256 internal constant Z_11 = 14271763308400718165336499097156975241954733520325982997864342600795471836726;
    uint256 internal constant Z_12 = 20066985985293572387227381049700832219069292839614107140851619262827735677018;
    uint256 internal constant Z_13 = 9394776414966240069580838672673694685292165040808226440647796406499139370960;
    uint256 internal constant Z_14 = 11331146992410411304059858900317123658895005918277453009197229807340014528524;
    uint256 internal constant Z_15 = 15819538789928229930262697811477882737253464456578333862691129291651619515538;
    uint256 internal constant Z_16 = 19217088683336594659449020493828377907203207941212636669271704950158751593251;
    uint256 internal constant Z_17 = 21035245323335827719745544373081896983162834604456827698288649288827293579666;
    uint256 internal constant Z_18 = 6939770416153240137322503476966641397417391950902474480970945462551409848591;
    uint256 internal constant Z_19 = 10941962436777715901943463195175331263348098796018438960955633645115732864202;
    uint256 internal constant Z_20 = 15019797232609675441998260052101280400536945603062888308240081994073687793470;
    uint256 internal constant Z_21 = 11702828337982203149177882813338547876343922920234831094975924378932809409969;
    uint256 internal constant Z_22 = 11217067736778784455593535811108456786943573747466706329920902520905755780395;
    uint256 internal constant Z_23 = 16072238744996205792852194127671441602062027943016727953216607508365787157389;
    uint256 internal constant Z_24 = 17681057402012993898104192736393849603097507831571622013521167331642182653248;
    uint256 internal constant Z_25 = 21694045479371014653083846597424257852691458318143380497809004364947786214945;
    uint256 internal constant Z_26 = 8163447297445169709687354538480474434591144168767135863541048304198280615192;
    uint256 internal constant Z_27 = 14081762237856300239452543304351251708585712948734528663957353575674639038357;
    uint256 internal constant Z_28 = 16619959921569409661790279042024627172199214148318086837362003702249041851090;
    uint256 internal constant Z_29 = 7022159125197495734384997711896547675021391130223237843255817587255104160365;
    uint256 internal constant Z_30 = 4114686047564160449611603615418567457008101555090703535405891656262658644463;
    uint256 internal constant Z_31 = 12549363297364877722388257367377629555213421373705596078299904496781819142130;
    uint256 internal constant Z_32 = 21443572485391568159800782191812935835534334817699172242223315142338162256601;

    function _defaultZero(uint8 index) internal pure returns (uint256) {
        if (index == 0) return Z_0;
        if (index == 1) return Z_1;
        if (index == 2) return Z_2;
        if (index == 3) return Z_3;
        if (index == 4) return Z_4;
        if (index == 5) return Z_5;
        if (index == 6) return Z_6;
        if (index == 7) return Z_7;
        if (index == 8) return Z_8;
        if (index == 9) return Z_9;
        if (index == 10) return Z_10;
        if (index == 11) return Z_11;
        if (index == 12) return Z_12;
        if (index == 13) return Z_13;
        if (index == 14) return Z_14;
        if (index == 15) return Z_15;
        if (index == 16) return Z_16;
        if (index == 17) return Z_17;
        if (index == 18) return Z_18;
        if (index == 19) return Z_19;
        if (index == 20) return Z_20;
        if (index == 21) return Z_21;
        if (index == 22) return Z_22;
        if (index == 23) return Z_23;
        if (index == 24) return Z_24;
        if (index == 25) return Z_25;
        if (index == 26) return Z_26;
        if (index == 27) return Z_27;
        if (index == 28) return Z_28;
        if (index == 29) return Z_29;
        if (index == 30) return Z_30;
        if (index == 31) return Z_31;
        if (index == 32) return Z_32;
        revert("LazyIMT: defaultZero bad index");
    }

    function _init(LazyIMTData storage self, uint8 depth) internal {
        require(depth <= MAX_DEPTH, "LazyIMT: Tree too large");
        self.maxIndex = uint40((1 << depth) - 1);
        self.numberOfLeaves = 0;
    }

    function _reset(LazyIMTData storage self) internal {
        self.numberOfLeaves = 0;
    }

    function _indexForElement(uint8 level, uint40 index) internal pure returns (uint40) {
        // store the elements sparsely
        return MAX_INDEX * level + index;
    }

    function _insert(LazyIMTData storage self, uint256 leaf) internal {
        uint40 index = self.numberOfLeaves;
        require(leaf < SNARK_SCALAR_FIELD, "LazyIMT: leaf must be < SNARK_SCALAR_FIELD");
        require(index < self.maxIndex, "LazyIMT: tree is full");

        self.numberOfLeaves = index + 1;

        uint256 hash = leaf;

        for (uint8 i = 0; ; ) {
            self.elements[_indexForElement(i, index)] = hash;
            // it's a left element so we don't hash until there's a right element
            if (index & 1 == 0) break;
            uint40 elementIndex = _indexForElement(i, index - 1);
            hash = PoseidonT3.hash([self.elements[elementIndex], hash]);
            unchecked {
                index >>= 1;
                i++;
            }
        }
    }

    function _update(LazyIMTData storage self, uint256 leaf, uint40 index) internal {
        require(leaf < SNARK_SCALAR_FIELD, "LazyIMT: leaf must be < SNARK_SCALAR_FIELD");
        uint40 numberOfLeaves = self.numberOfLeaves;
        require(index < numberOfLeaves, "LazyIMT: leaf must exist");

        uint256 hash = leaf;

        for (uint8 i = 0; true; ) {
            self.elements[_indexForElement(i, index)] = hash;
            uint256 levelCount = numberOfLeaves >> (i + 1);
            if (levelCount <= index >> 1) break;
            if (index & 1 == 0) {
                uint40 elementIndex = _indexForElement(i, index + 1);
                hash = PoseidonT3.hash([hash, self.elements[elementIndex]]);
            } else {
                uint40 elementIndex = _indexForElement(i, index - 1);
                hash = PoseidonT3.hash([self.elements[elementIndex], hash]);
            }
            unchecked {
                index >>= 1;
                i++;
            }
        }
    }

    function _root(LazyIMTData storage self) internal view returns (uint256) {
        // this will always short circuit if self.numberOfLeaves == 0
        uint40 numberOfLeaves = self.numberOfLeaves;
        // dynamically determine a depth
        uint8 depth = 1;
        while (uint40(2) ** uint40(depth) < numberOfLeaves) {
            depth++;
        }
        return _root(self, numberOfLeaves, depth);
    }

    function _root(LazyIMTData storage self, uint8 depth) internal view returns (uint256) {
        require(depth > 0, "LazyIMT: depth must be > 0");
        require(depth <= MAX_DEPTH, "LazyIMT: depth must be <= MAX_DEPTH");
        uint40 numberOfLeaves = self.numberOfLeaves;
        require(uint40(2) ** uint40(depth) >= numberOfLeaves, "LazyIMT: ambiguous depth");
        return _root(self, numberOfLeaves, depth);
    }

    // Here it's assumed that the depth value is valid. If it is either 0 or > 2^8-1
    // this function will panic.
    function _root(LazyIMTData storage self, uint40 numberOfLeaves, uint8 depth) internal view returns (uint256) {
        require(depth <= MAX_DEPTH, "LazyIMT: depth must be <= MAX_DEPTH");
        // this should always short circuit if self.numberOfLeaves == 0
        if (numberOfLeaves == 0) return _defaultZero(depth);
        uint256[] memory levels = new uint256[](depth + 1);
        _levels(self, numberOfLeaves, depth, levels);
        return levels[depth];
    }

    function _levels(
        LazyIMTData storage self,
        uint40 numberOfLeaves,
        uint8 depth,
        uint256[] memory levels
    ) internal view {
        require(depth <= MAX_DEPTH, "LazyIMT: depth must be <= MAX_DEPTH");
        require(numberOfLeaves > 0, "LazyIMT: number of leaves must be > 0");
        // this should always short circuit if self.numberOfLeaves == 0
        uint40 index = numberOfLeaves - 1;

        if (index & 1 == 0) {
            levels[0] = self.elements[_indexForElement(0, index)];
        } else {
            levels[0] = _defaultZero(0);
        }

        for (uint8 i = 0; i < depth; ) {
            if (index & 1 == 0) {
                levels[i + 1] = PoseidonT3.hash([levels[i], _defaultZero(i)]);
            } else {
                uint256 levelCount = (numberOfLeaves) >> (i + 1);
                if (levelCount > index >> 1) {
                    uint256 parent = self.elements[_indexForElement(i + 1, index >> 1)];
                    levels[i + 1] = parent;
                } else {
                    uint256 sibling = self.elements[_indexForElement(i, index - 1)];
                    levels[i + 1] = PoseidonT3.hash([sibling, levels[i]]);
                }
            }
            unchecked {
                index >>= 1;
                i++;
            }
        }
    }

    function _merkleProofElements(
        LazyIMTData storage self,
        uint40 index,
        uint8 depth
    ) internal view returns (uint256[] memory) {
        uint40 numberOfLeaves = self.numberOfLeaves;
        require(index < numberOfLeaves, "LazyIMT: leaf must exist");

        uint8 targetDepth = 1;
        while (uint40(2) ** uint40(targetDepth) < numberOfLeaves) {
            targetDepth++;
        }
        require(depth >= targetDepth, "LazyIMT: proof depth");
        // pass depth -1 because we don't need the root value
        uint256[] memory _elements = new uint256[](depth);
        _levels(self, numberOfLeaves, targetDepth - 1, _elements);

        // unroll the bottom entry of the tree because it will never need to
        // be pulled from _levels
        if (index & 1 == 0) {
            if (index + 1 >= numberOfLeaves) {
                _elements[0] = _defaultZero(0);
            } else {
                _elements[0] = self.elements[_indexForElement(0, index + 1)];
            }
        } else {
            _elements[0] = self.elements[_indexForElement(0, index - 1)];
        }
        index >>= 1;

        for (uint8 i = 1; i < depth; ) {
            uint256 currentLevelCount = numberOfLeaves >> i;
            if (index & 1 == 0) {
                // if the element is an uncomputed edge node we'll use the value set
                // from _levels above
                // otherwise set as usual below
                if (index + 1 < currentLevelCount) {
                    _elements[i] = self.elements[_indexForElement(i, index + 1)];
                } else if (((numberOfLeaves - 1) >> i) <= index) {
                    _elements[i] = _defaultZero(i);
                }
            } else {
                _elements[i] = self.elements[_indexForElement(i, index - 1)];
            }
            unchecked {
                index >>= 1;
                i++;
            }
        }
        return _elements;
    }
}

// SPDX-License-Identifier: MIT
pragma solidity ^0.8.4;

import {InternalLazyIMT, LazyIMTData} from "./InternalLazyIMT.sol";

library LazyIMT {
    using InternalLazyIMT for *;

    function init(LazyIMTData storage self, uint8 depth) public {
        InternalLazyIMT._init(self, depth);
    }

    function defaultZero(uint8 index) public pure returns (uint256) {
        return InternalLazyIMT._defaultZero(index);
    }

    function reset(LazyIMTData storage self) public {
        InternalLazyIMT._reset(self);
    }

    function indexForElement(uint8 level, uint40 index) public pure returns (uint40) {
        return InternalLazyIMT._indexForElement(level, index);
    }

    function insert(LazyIMTData storage self, uint256 leaf) public {
        InternalLazyIMT._insert(self, leaf);
    }

    function update(LazyIMTData storage self, uint256 leaf, uint40 index) public {
        InternalLazyIMT._update(self, leaf, index);
    }

    function root(LazyIMTData storage self) public view returns (uint256) {
        return InternalLazyIMT._root(self);
    }

    function root(LazyIMTData storage self, uint8 depth) public view returns (uint256) {
        return InternalLazyIMT._root(self, depth);
    }

    function merkleProofElements(
        LazyIMTData storage self,
        uint40 index,
        uint8 depth
    ) public view returns (uint256[] memory) {
        return InternalLazyIMT._merkleProofElements(self, index, depth);
    }

    function _root(LazyIMTData storage self, uint40 numberOfLeaves, uint8 depth) internal view returns (uint256) {
        return InternalLazyIMT._root(self, numberOfLeaves, depth);
    }
}

// SPDX-License-Identifier: MIT

pragma solidity 0.8.29;

// TODO public state vars?
interface IGigaBridge {
    event ConstructedNewGigaRoot(
        uint256 indexed newGigaRoot
    ); 
    
    event ReceivedNewLocalRoot(
        uint256 indexed newLocalRoot,
        uint40 indexed localRootIndex, 
        uint256 localRootBlockNumber
    );

    function getLocalRootProvidersIndex(address _localRootProvider) external view returns(uint40);

    function isLocalRootProviders(address _localRootProvider) external view returns(bool);

    function updateGigaRoot(address[] memory _localRootProvider) external;

    // Made this a second function because the addresses that want the gigaRoot
    // might be different from the addresses that are updating their localRoot.
    // since most of the time everyone wants the latest gigaRoot but not everyone has a localRoot that is new
    // Sends the most recent gigaRoot to an array of localRootProviders
    function sendGigaRoot(address[] memory _gigaRootRecipients, uint256[] memory _amounts) payable external;

}

// SPDX-License-Identifier: MIT

pragma solidity 0.8.29;

interface IGigaRootProvider {
    function sendGigaRoot(address _gigaRootRecipient) external payable;
    function gigaRoot() external returns(uint256);
}

interface IGigaRootRecipient {
    function receiveGigaRoot(uint256 _gigaRoot) payable external;
    //function receiveGigaRoot(uint256 _gigaRoot, uint256 _gasLimit) payable external;
}


interface ILocalRootProvider {
    function getLocalRootAndBlock() external returns (uint256, uint256);
}

interface ILocalRootRecipient {
    //only gigaBridge does this
    //function updateGigaRoot(address[] memory _localRootProvider) external;
}

/// SPDX-License-Identifier: MIT
pragma solidity >=0.7.0;

library PoseidonT3 {
  uint constant M00 = 0x109b7f411ba0e4c9b2b70caf5c36a7b194be7c11ad24378bfedb68592ba8118b;
  uint constant M01 = 0x2969f27eed31a480b9c36c764379dbca2cc8fdd1415c3dded62940bcde0bd771;
  uint constant M02 = 0x143021ec686a3f330d5f9e654638065ce6cd79e28c5b3753326244ee65a1b1a7;
  uint constant M10 = 0x16ed41e13bb9c0c66ae119424fddbcbc9314dc9fdbdeea55d6c64543dc4903e0;
  uint constant M11 = 0x2e2419f9ec02ec394c9871c832963dc1b89d743c8c7b964029b2311687b1fe23;
  uint constant M12 = 0x176cc029695ad02582a70eff08a6fd99d057e12e58e7d7b6b16cdfabc8ee2911;

  // See here for a simplified implementation: https://github.com/vimwitch/poseidon-solidity/blob/e57becdabb65d99fdc586fe1e1e09e7108202d53/contracts/Poseidon.sol#L40
  // Inspired by: https://github.com/iden3/circomlibjs/blob/v0.0.8/src/poseidon_slow.js
  function hash(uint[2] memory) public pure returns (uint) {
    assembly {
      let F := 21888242871839275222246405745257275088548364400416034343698204186575808495617
      let M20 := 0x2b90bba00fca0589f617e7dcbfe82e0df706ab640ceb247b791a93b74e36736d
      let M21 := 0x101071f0032379b697315876690f053d148d4e109f5fb065c8aacc55a0f89bfa
      let M22 := 0x19a3fc0a56702bf417ba7fee3802593fa644470307043f7773279cd71d25d5e0

      // load the inputs from memory
      let state1 := add(mod(mload(0x80), F), 0x00f1445235f2148c5986587169fc1bcd887b08d4d00868df5696fff40956e864)
      let state2 := add(mod(mload(0xa0), F), 0x08dff3487e8ac99e1f29a058d0fa80b930c728730b7ab36ce879f3890ecf73f5)
      let scratch0 := mulmod(state1, state1, F)
      state1 := mulmod(mulmod(scratch0, scratch0, F), state1, F)
      scratch0 := mulmod(state2, state2, F)
      state2 := mulmod(mulmod(scratch0, scratch0, F), state2, F)
      scratch0 := add(
        0x2f27be690fdaee46c3ce28f7532b13c856c35342c84bda6e20966310fadc01d0,
        add(add(15452833169820924772166449970675545095234312153403844297388521437673434406763, mulmod(state1, M10, F)), mulmod(state2, M20, F))
      )
      let scratch1 := add(
        0x2b2ae1acf68b7b8d2416bebf3d4f6234b763fe04b8043ee48b8327bebca16cf2,
        add(add(18674271267752038776579386132900109523609358935013267566297499497165104279117, mulmod(state1, M11, F)), mulmod(state2, M21, F))
      )
      let scratch2 := add(
        0x0319d062072bef7ecca5eac06f97d4d55952c175ab6b03eae64b44c7dbf11cfa,
        add(add(14817777843080276494683266178512808687156649753153012854386334860566696099579, mulmod(state1, M12, F)), mulmod(state2, M22, F))
      )
      let state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := mulmod(scratch1, scratch1, F)
      scratch1 := mulmod(mulmod(state0, state0, F), scratch1, F)
      state0 := mulmod(scratch2, scratch2, F)
      scratch2 := mulmod(mulmod(state0, state0, F), scratch2, F)
      state0 := add(0x28813dcaebaeaa828a376df87af4a63bc8b7bf27ad49c6298ef7b387bf28526d, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x2727673b2ccbc903f181bf38e1c1d40d2033865200c352bc150928adddf9cb78, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x234ec45ca27727c2e74abd2b2a1494cd6efbd43e340587d6b8fb9e31e65cc632, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := mulmod(state1, state1, F)
      state1 := mulmod(mulmod(scratch0, scratch0, F), state1, F)
      scratch0 := mulmod(state2, state2, F)
      state2 := mulmod(mulmod(scratch0, scratch0, F), state2, F)
      scratch0 := add(0x15b52534031ae18f7f862cb2cf7cf760ab10a8150a337b1ccd99ff6e8797d428, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0dc8fad6d9e4b35f5ed9a3d186b79ce38e0e8a8d1b58b132d701d4eecf68d1f6, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x1bcd95ffc211fbca600f705fad3fb567ea4eb378f62e1fec97805518a47e4d9c, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := mulmod(scratch1, scratch1, F)
      scratch1 := mulmod(mulmod(state0, state0, F), scratch1, F)
      state0 := mulmod(scratch2, scratch2, F)
      scratch2 := mulmod(mulmod(state0, state0, F), scratch2, F)
      state0 := add(0x10520b0ab721cadfe9eff81b016fc34dc76da36c2578937817cb978d069de559, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1f6d48149b8e7f7d9b257d8ed5fbbaf42932498075fed0ace88a9eb81f5627f6, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1d9655f652309014d29e00ef35a2089bfff8dc1c816f0dc9ca34bdb5460c8705, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x04df5a56ff95bcafb051f7b1cd43a99ba731ff67e47032058fe3d4185697cc7d, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0672d995f8fff640151b3d290cedaf148690a10a8c8424a7f6ec282b6e4be828, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x099952b414884454b21200d7ffafdd5f0c9a9dcc06f2708e9fc1d8209b5c75b9, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x052cba2255dfd00c7c483143ba8d469448e43586a9b4cd9183fd0e843a6b9fa6, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0b8badee690adb8eb0bd74712b7999af82de55707251ad7716077cb93c464ddc, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x119b1590f13307af5a1ee651020c07c749c15d60683a8050b963d0a8e4b2bdd1, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x03150b7cd6d5d17b2529d36be0f67b832c4acfc884ef4ee5ce15be0bfb4a8d09, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2cc6182c5e14546e3cf1951f173912355374efb83d80898abe69cb317c9ea565, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x005032551e6378c450cfe129a404b3764218cadedac14e2b92d2cd73111bf0f9, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x233237e3289baa34bb147e972ebcb9516469c399fcc069fb88f9da2cc28276b5, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x05c8f4f4ebd4a6e3c980d31674bfbe6323037f21b34ae5a4e80c2d4c24d60280, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x0a7b1db13042d396ba05d818a319f25252bcf35ef3aeed91ee1f09b2590fc65b, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2a73b71f9b210cf5b14296572c9d32dbf156e2b086ff47dc5df542365a404ec0, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1ac9b0417abcc9a1935107e9ffc91dc3ec18f2c4dbe7f22976a760bb5c50c460, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x12c0339ae08374823fabb076707ef479269f3e4d6cb104349015ee046dc93fc0, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x0b7475b102a165ad7f5b18db4e1e704f52900aa3253baac68246682e56e9a28e, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x037c2849e191ca3edb1c5e49f6e8b8917c843e379366f2ea32ab3aa88d7f8448, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x05a6811f8556f014e92674661e217e9bd5206c5c93a07dc145fdb176a716346f, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x29a795e7d98028946e947b75d54e9f044076e87a7b2883b47b675ef5f38bd66e, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x20439a0c84b322eb45a3857afc18f5826e8c7382c8a1585c507be199981fd22f, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2e0ba8d94d9ecf4a94ec2050c7371ff1bb50f27799a84b6d4a2a6f2a0982c887, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x143fd115ce08fb27ca38eb7cce822b4517822cd2109048d2e6d0ddcca17d71c8, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0c64cbecb1c734b857968dbbdcf813cdf8611659323dbcbfc84323623be9caf1, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x028a305847c683f646fca925c163ff5ae74f348d62c2b670f1426cef9403da53, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2e4ef510ff0b6fda5fa940ab4c4380f26a6bcb64d89427b824d6755b5db9e30c, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0081c95bc43384e663d79270c956ce3b8925b4f6d033b078b96384f50579400e, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2ed5f0c91cbd9749187e2fade687e05ee2491b349c039a0bba8a9f4023a0bb38, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x30509991f88da3504bbf374ed5aae2f03448a22c76234c8c990f01f33a735206, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1c3f20fd55409a53221b7c4d49a356b9f0a1119fb2067b41a7529094424ec6ad, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x10b4e7f3ab5df003049514459b6e18eec46bb2213e8e131e170887b47ddcb96c, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2a1982979c3ff7f43ddd543d891c2abddd80f804c077d775039aa3502e43adef, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1c74ee64f15e1db6feddbead56d6d55dba431ebc396c9af95cad0f1315bd5c91, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x07533ec850ba7f98eab9303cace01b4b9e4f2e8b82708cfa9c2fe45a0ae146a0, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x21576b438e500449a151e4eeaf17b154285c68f42d42c1808a11abf3764c0750, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x2f17c0559b8fe79608ad5ca193d62f10bce8384c815f0906743d6930836d4a9e, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x2d477e3862d07708a79e8aae946170bc9775a4201318474ae665b0b1b7e2730e, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x162f5243967064c390e095577984f291afba2266c38f5abcd89be0f5b2747eab, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2b4cb233ede9ba48264ecd2c8ae50d1ad7a8596a87f29f8a7777a70092393311, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2c8fbcb2dd8573dc1dbaf8f4622854776db2eece6d85c4cf4254e7c35e03b07a, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x1d6f347725e4816af2ff453f0cd56b199e1b61e9f601e9ade5e88db870949da9, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x204b0c397f4ebe71ebc2d8b3df5b913df9e6ac02b68d31324cd49af5c4565529, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x0c4cb9dc3c4fd8174f1149b3c63c3c2f9ecb827cd7dc25534ff8fb75bc79c502, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x174ad61a1448c899a25416474f4930301e5c49475279e0639a616ddc45bc7b54, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1a96177bcf4d8d89f759df4ec2f3cde2eaaa28c177cc0fa13a9816d49a38d2ef, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x066d04b24331d71cd0ef8054bc60c4ff05202c126a233c1a8242ace360b8a30a, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x2a4c4fc6ec0b0cf52195782871c6dd3b381cc65f72e02ad527037a62aa1bd804, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x13ab2d136ccf37d447e9f2e14a7cedc95e727f8446f6d9d7e55afc01219fd649, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1121552fca26061619d24d843dc82769c1b04fcec26f55194c2e3e869acc6a9a, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x00ef653322b13d6c889bc81715c37d77a6cd267d595c4a8909a5546c7c97cff1, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0e25483e45a665208b261d8ba74051e6400c776d652595d9845aca35d8a397d3, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x29f536dcb9dd7682245264659e15d88e395ac3d4dde92d8c46448db979eeba89, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x2a56ef9f2c53febadfda33575dbdbd885a124e2780bbea170e456baace0fa5be, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1c8361c78eb5cf5decfb7a2d17b5c409f2ae2999a46762e8ee416240a8cb9af1, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x151aff5f38b20a0fc0473089aaf0206b83e8e68a764507bfd3d0ab4be74319c5, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x04c6187e41ed881dc1b239c88f7f9d43a9f52fc8c8b6cdd1e76e47615b51f100, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x13b37bd80f4d27fb10d84331f6fb6d534b81c61ed15776449e801b7ddc9c2967, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x01a5c536273c2d9df578bfbd32c17b7a2ce3664c2a52032c9321ceb1c4e8a8e4, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x2ab3561834ca73835ad05f5d7acb950b4a9a2c666b9726da832239065b7c3b02, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1d4d8ec291e720db200fe6d686c0d613acaf6af4e95d3bf69f7ed516a597b646, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x041294d2cc484d228f5784fe7919fd2bb925351240a04b711514c9c80b65af1d, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x154ac98e01708c611c4fa715991f004898f57939d126e392042971dd90e81fc6, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0b339d8acca7d4f83eedd84093aef51050b3684c88f8b0b04524563bc6ea4da4, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x0955e49e6610c94254a4f84cfbab344598f0e71eaff4a7dd81ed95b50839c82e, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x06746a6156eba54426b9e22206f15abca9a6f41e6f535c6f3525401ea0654626, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0f18f5a0ecd1423c496f3820c549c27838e5790e2bd0a196ac917c7ff32077fb, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x04f6eeca1751f7308ac59eff5beb261e4bb563583ede7bc92a738223d6f76e13, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2b56973364c4c4f5c1a3ec4da3cdce038811eb116fb3e45bc1768d26fc0b3758, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x123769dd49d5b054dcd76b89804b1bcb8e1392b385716a5d83feb65d437f29ef, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2147b424fc48c80a88ee52b91169aacea989f6446471150994257b2fb01c63e9, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x0fdc1f58548b85701a6c5505ea332a29647e6f34ad4243c2ea54ad897cebe54d, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x12373a8251fea004df68abcf0f7786d4bceff28c5dbbe0c3944f685cc0a0b1f2, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x21e4f4ea5f35f85bad7ea52ff742c9e8a642756b6af44203dd8a1f35c1a90035, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x16243916d69d2ca3dfb4722224d4c462b57366492f45e90d8a81934f1bc3b147, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1efbe46dd7a578b4f66f9adbc88b4378abc21566e1a0453ca13a4159cac04ac2, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x07ea5e8537cf5dd08886020e23a7f387d468d5525be66f853b672cc96a88969a, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x05a8c4f9968b8aa3b7b478a30f9a5b63650f19a75e7ce11ca9fe16c0b76c00bc, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x20f057712cc21654fbfe59bd345e8dac3f7818c701b9c7882d9d57b72a32e83f, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x04a12ededa9dfd689672f8c67fee31636dcd8e88d01d49019bd90b33eb33db69, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x27e88d8c15f37dcee44f1e5425a51decbd136ce5091a6767e49ec9544ccd101a, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2feed17b84285ed9b8a5c8c5e95a41f66e096619a7703223176c41ee433de4d1, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x1ed7cc76edf45c7c404241420f729cf394e5942911312a0d6972b8bd53aff2b8, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x15742e99b9bfa323157ff8c586f5660eac6783476144cdcadf2874be45466b1a, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1aac285387f65e82c895fc6887ddf40577107454c6ec0317284f033f27d0c785, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x25851c3c845d4790f9ddadbdb6057357832e2e7a49775f71ec75a96554d67c77, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x15a5821565cc2ec2ce78457db197edf353b7ebba2c5523370ddccc3d9f146a67, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2411d57a4813b9980efa7e31a1db5966dcf64f36044277502f15485f28c71727, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x002e6f8d6520cd4713e335b8c0b6d2e647e9a98e12f4cd2558828b5ef6cb4c9b, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x2ff7bc8f4380cde997da00b616b0fcd1af8f0e91e2fe1ed7398834609e0315d2, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x00b9831b948525595ee02724471bcd182e9521f6b7bb68f1e93be4febb0d3cbe, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x0a2f53768b8ebf6a86913b0e57c04e011ca408648a4743a87d77adbf0c9c3512, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x00248156142fd0373a479f91ff239e960f599ff7e94be69b7f2a290305e1198d, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x171d5620b87bfb1328cf8c02ab3f0c9a397196aa6a542c2350eb512a2b2bcda9, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x170a4f55536f7dc970087c7c10d6fad760c952172dd54dd99d1045e4ec34a808, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x29aba33f799fe66c2ef3134aea04336ecc37e38c1cd211ba482eca17e2dbfae1, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1e9bc179a4fdd758fdd1bb1945088d47e70d114a03f6a0e8b5ba650369e64973, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1dd269799b660fad58f7f4892dfb0b5afeaad869a9c4b44f9c9e1c43bdaf8f09, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x22cdbc8b70117ad1401181d02e15459e7ccd426fe869c7c95d1dd2cb0f24af38, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x0ef042e454771c533a9f57a55c503fcefd3150f52ed94a7cd5ba93b9c7dacefd, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x11609e06ad6c8fe2f287f3036037e8851318e8b08a0359a03b304ffca62e8284, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x1166d9e554616dba9e753eea427c17b7fecd58c076dfe42708b08f5b783aa9af, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x2de52989431a859593413026354413db177fbf4cd2ac0b56f855a888357ee466, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x3006eb4ffc7a85819a6da492f3a8ac1df51aee5b17b8e89d74bf01cf5f71e9ad, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2af41fbb61ba8a80fdcf6fff9e3f6f422993fe8f0a4639f962344c8225145086, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x119e684de476155fe5a6b41a8ebc85db8718ab27889e85e781b214bace4827c3, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x1835b786e2e8925e188bea59ae363537b51248c23828f047cff784b97b3fd800, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x28201a34c594dfa34d794996c6433a20d152bac2a7905c926c40e285ab32eeb6, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x083efd7a27d1751094e80fefaf78b000864c82eb571187724a761f88c22cc4e7, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x0b6f88a3577199526158e61ceea27be811c16df7774dd8519e079564f61fd13b, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x0ec868e6d15e51d9644f66e1d6471a94589511ca00d29e1014390e6ee4254f5b, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2af33e3f866771271ac0c9b3ed2e1142ecd3e74b939cd40d00d937ab84c98591, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x0b520211f904b5e7d09b5d961c6ace7734568c547dd6858b364ce5e47951f178, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x0b2d722d0919a1aad8db58f10062a92ea0c56ac4270e822cca228620188a1d40, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x1f790d4d7f8cf094d980ceb37c2453e957b54a9991ca38bbe0061d1ed6e562d4, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x0171eb95dfbf7d1eaea97cd385f780150885c16235a2a6a8da92ceb01e504233, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x0c2d0e3b5fd57549329bf6885da66b9b790b40defd2c8650762305381b168873, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1162fb28689c27154e5a8228b4e72b377cbcafa589e283c35d3803054407a18d, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2f1459b65dee441b64ad386a91e8310f282c5a92a89e19921623ef8249711bc0, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x1e6ff3216b688c3d996d74367d5cd4c1bc489d46754eb712c243f70d1b53cfbb, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x01ca8be73832b8d0681487d27d157802d741a6f36cdc2a0576881f9326478875, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1f7735706ffe9fc586f976d5bdf223dc680286080b10cea00b9b5de315f9650e, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2522b60f4ea3307640a0c2dce041fba921ac10a3d5f096ef4745ca838285f019, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x23f0bee001b1029d5255075ddc957f833418cad4f52b6c3f8ce16c235572575b, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2bc1ae8b8ddbb81fcaac2d44555ed5685d142633e9df905f66d9401093082d59, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x0f9406b8296564a37304507b8dba3ed162371273a07b1fc98011fcd6ad72205f, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x2360a8eb0cc7defa67b72998de90714e17e75b174a52ee4acb126c8cd995f0a8, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x15871a5cddead976804c803cbaef255eb4815a5e96df8b006dcbbc2767f88948, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x193a56766998ee9e0a8652dd2f3b1da0362f4f54f72379544f957ccdeefb420f, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x2a394a43934f86982f9be56ff4fab1703b2e63c8ad334834e4309805e777ae0f, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x1859954cfeb8695f3e8b635dcb345192892cd11223443ba7b4166e8876c0d142, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x04e1181763050e58013444dbcb99f1902b11bc25d90bbdca408d3819f4fed32b, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0fdb253dee83869d40c335ea64de8c5bb10eb82db08b5e8b1f5e5552bfd05f23, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x058cbe8a9a5027bdaa4efb623adead6275f08686f1c08984a9d7c5bae9b4f1c0, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x1382edce9971e186497eadb1aeb1f52b23b4b83bef023ab0d15228b4cceca59a, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x03464990f045c6ee0819ca51fd11b0be7f61b8eb99f14b77e1e6634601d9e8b5, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x23f7bfc8720dc296fff33b41f98ff83c6fcab4605db2eb5aaa5bc137aeb70a58, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x0a59a158e3eec2117e6e94e7f0e9decf18c3ffd5e1531a9219636158bbaf62f2, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x06ec54c80381c052b58bf23b312ffd3ce2c4eba065420af8f4c23ed0075fd07b, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x118872dc832e0eb5476b56648e867ec8b09340f7a7bcb1b4962f0ff9ed1f9d01, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x13d69fa127d834165ad5c7cba7ad59ed52e0b0f0e42d7fea95e1906b520921b1, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x169a177f63ea681270b1c6877a73d21bde143942fb71dc55fd8a49f19f10c77b, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x04ef51591c6ead97ef42f287adce40d93abeb032b922f66ffb7e9a5a7450544d, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x256e175a1dc079390ecd7ca703fb2e3b19ec61805d4f03ced5f45ee6dd0f69ec, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x30102d28636abd5fe5f2af412ff6004f75cc360d3205dd2da002813d3e2ceeb2, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x10998e42dfcd3bbf1c0714bc73eb1bf40443a3fa99bef4a31fd31be182fcc792, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x193edd8e9fcf3d7625fa7d24b598a1d89f3362eaf4d582efecad76f879e36860, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x18168afd34f2d915d0368ce80b7b3347d1c7a561ce611425f2664d7aa51f0b5d, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x29383c01ebd3b6ab0c017656ebe658b6a328ec77bc33626e29e2e95b33ea6111, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x10646d2f2603de39a1f4ae5e7771a64a702db6e86fb76ab600bf573f9010c711, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0beb5e07d1b27145f575f1395a55bf132f90c25b40da7b3864d0242dcb1117fb, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x16d685252078c133dc0d3ecad62b5c8830f95bb2e54b59abdffbf018d96fa336, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x0a6abd1d833938f33c74154e0404b4b40a555bbbec21ddfafd672dd62047f01a, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1a679f5d36eb7b5c8ea12a4c2dedc8feb12dffeec450317270a6f19b34cf1860, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x0980fb233bd456c23974d50e0ebfde4726a423eada4e8f6ffbc7592e3f1b93d6, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x161b42232e61b84cbf1810af93a38fc0cece3d5628c9282003ebacb5c312c72b, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0ada10a90c7f0520950f7d47a60d5e6a493f09787f1564e5d09203db47de1a0b, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1a730d372310ba82320345a29ac4238ed3f07a8a2b4e121bb50ddb9af407f451, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x2c8120f268ef054f817064c369dda7ea908377feaba5c4dffbda10ef58e8c556, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1c7c8824f758753fa57c00789c684217b930e95313bcb73e6e7b8649a4968f70, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x2cd9ed31f5f8691c8e39e4077a74faa0f400ad8b491eb3f7b47b27fa3fd1cf77, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x23ff4f9d46813457cf60d92f57618399a5e022ac321ca550854ae23918a22eea, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x09945a5d147a4f66ceece6405dddd9d0af5a2c5103529407dff1ea58f180426d, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x188d9c528025d4c2b67660c6b771b90f7c7da6eaa29d3f268a6dd223ec6fc630, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x3050e37996596b7f81f68311431d8734dba7d926d3633595e0c0d8ddf4f0f47f, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x15af1169396830a91600ca8102c35c426ceae5461e3f95d89d829518d30afd78, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x1da6d09885432ea9a06d9f37f873d985dae933e351466b2904284da3320d8acc, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := add(0x2796ea90d269af29f5f8acf33921124e4e4fad3dbe658945e546ee411ddaa9cb, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x202d7dd1da0f6b4b0325c8b3307742f01e15612ec8e9304a7cb0319e01d32d60, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x096d6790d05bb759156a952ba263d672a2d7f9c788f4c831a29dace4c0f8be5f, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := add(0x054efa1f65b0fce283808965275d877b438da23ce5b13e1963798cb1447d25a4, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x1b162f83d917e93edb3308c29802deb9d8aa690113b2e14864ccf6e18e4165f1, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x21e5241e12564dd6fd9f1cdd2a0de39eedfefc1466cc568ec5ceb745a0506edc, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := mulmod(scratch1, scratch1, F)
      scratch1 := mulmod(mulmod(state0, state0, F), scratch1, F)
      state0 := mulmod(scratch2, scratch2, F)
      scratch2 := mulmod(mulmod(state0, state0, F), scratch2, F)
      state0 := add(0x1cfb5662e8cf5ac9226a80ee17b36abecb73ab5f87e161927b4349e10e4bdf08, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x0f21177e302a771bbae6d8d1ecb373b62c99af346220ac0129c53f666eb24100, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1671522374606992affb0dd7f71b12bec4236aede6290546bcef7e1f515c2320, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := mulmod(state1, state1, F)
      state1 := mulmod(mulmod(scratch0, scratch0, F), state1, F)
      scratch0 := mulmod(state2, state2, F)
      state2 := mulmod(mulmod(scratch0, scratch0, F), state2, F)
      scratch0 := add(0x0fa3ec5b9488259c2eb4cf24501bfad9be2ec9e42c5cc8ccd419d2a692cad870, add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)))
      scratch1 := add(0x193c0e04e0bd298357cb266c1506080ed36edce85c648cc085e8c57b1ab54bba, add(add(mulmod(state0, M01, F), mulmod(state1, M11, F)), mulmod(state2, M21, F)))
      scratch2 := add(0x102adf8ef74735a27e9128306dcbc3c99f6f7291cd406578ce14ea2adaba68f8, add(add(mulmod(state0, M02, F), mulmod(state1, M12, F)), mulmod(state2, M22, F)))
      state0 := mulmod(scratch0, scratch0, F)
      scratch0 := mulmod(mulmod(state0, state0, F), scratch0, F)
      state0 := mulmod(scratch1, scratch1, F)
      scratch1 := mulmod(mulmod(state0, state0, F), scratch1, F)
      state0 := mulmod(scratch2, scratch2, F)
      scratch2 := mulmod(mulmod(state0, state0, F), scratch2, F)
      state0 := add(0x0fe0af7858e49859e2a54d6f1ad945b1316aa24bfbdd23ae40a6d0cb70c3eab1, add(add(mulmod(scratch0, M00, F), mulmod(scratch1, M10, F)), mulmod(scratch2, M20, F)))
      state1 := add(0x216f6717bbc7dedb08536a2220843f4e2da5f1daa9ebdefde8a5ea7344798d22, add(add(mulmod(scratch0, M01, F), mulmod(scratch1, M11, F)), mulmod(scratch2, M21, F)))
      state2 := add(0x1da55cc900f0d21f4a3e694391918a1b3c23b2ac773c6b3ef88e2e4228325161, add(add(mulmod(scratch0, M02, F), mulmod(scratch1, M12, F)), mulmod(scratch2, M22, F)))
      scratch0 := mulmod(state0, state0, F)
      state0 := mulmod(mulmod(scratch0, scratch0, F), state0, F)
      scratch0 := mulmod(state1, state1, F)
      state1 := mulmod(mulmod(scratch0, scratch0, F), state1, F)
      scratch0 := mulmod(state2, state2, F)
      state2 := mulmod(mulmod(scratch0, scratch0, F), state2, F)

      mstore(0x0, mod(add(add(mulmod(state0, M00, F), mulmod(state1, M10, F)), mulmod(state2, M20, F)), F))

      return(0, 0x20)
    }
  }
}

Settings
{
  "optimizer": {
    "enabled": true,
    "runs": 1000
  },
  "evmVersion": "cancun",
  "outputSelection": {
    "*": {
      "*": [
        "evm.bytecode",
        "evm.deployedBytecode",
        "devdoc",
        "userdoc",
        "metadata",
        "abi"
      ]
    }
  },
  "libraries": {
    "contracts/evm/GigaBridge.sol": {
      "LazyIMT": "0xba7c11d97d4b977908c5182eeb9d130474c2e67f"
    }
  }
}

Contract ABI

API
[{"inputs":[{"internalType":"address[]","name":"_gigaRootRecipients","type":"address[]"},{"internalType":"uint8","name":"_maxTreeDepth","type":"uint8"}],"stateMutability":"nonpayable","type":"constructor"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"newGigaRoot","type":"uint256"}],"name":"ConstructedNewGigaRoot","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"newLocalRoot","type":"uint256"},{"indexed":true,"internalType":"uint40","name":"localRootIndex","type":"uint40"},{"indexed":false,"internalType":"uint256","name":"localRootBlockNumber","type":"uint256"}],"name":"ReceivedNewLocalRoot","type":"event"},{"anonymous":false,"inputs":[{"indexed":true,"internalType":"uint256","name":"gigaRoot","type":"uint256"}],"name":"SentGigaRoot","type":"event"},{"inputs":[],"name":"amountOfLocalRoots","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_localRootProvider","type":"address"}],"name":"getLocalRootProvidersIndex","outputs":[{"internalType":"uint40","name":"","type":"uint40"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"gigaRoot","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_localRootProvider","type":"address"}],"name":"isLocalRootProviders","outputs":[{"internalType":"bool","name":"","type":"bool"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"","type":"address"}],"name":"localRootBlockNumbers","outputs":[{"internalType":"uint256","name":"","type":"uint256"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"maxTreeDepth","outputs":[{"internalType":"uint8","name":"","type":"uint8"}],"stateMutability":"view","type":"function"},{"inputs":[],"name":"rootTreeData","outputs":[{"internalType":"uint40","name":"maxIndex","type":"uint40"},{"internalType":"uint40","name":"numberOfLeaves","type":"uint40"}],"stateMutability":"view","type":"function"},{"inputs":[{"internalType":"address","name":"_gigaRootRecipient","type":"address"}],"name":"sendGigaRoot","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"_gigaRootRecipients","type":"address[]"},{"internalType":"uint256[]","name":"_amounts","type":"uint256[]"}],"name":"sendGigaRoot","outputs":[],"stateMutability":"payable","type":"function"},{"inputs":[{"internalType":"address[]","name":"_localRootProvider","type":"address[]"}],"name":"updateGigaRoot","outputs":[],"stateMutability":"nonpayable","type":"function"}]

608060405234801561000f575f5ffd5b50604051610e6f380380610e6f83398101604081905261002e91610271565b6003805460ff191660ff8316908117909155604051631844db3b60e21b815260016004820152602481019190915273ba7c11d97d4b977908c5182eeb9d130474c2e67f906361136cec906044015f6040518083038186803b158015610091575f5ffd5b505af41580156100a3573d5f5f3e3d5ffd5b505f925050505b82518164ffffffffff161015610162576100ea838264ffffffffff16815181106100d6576100d661034d565b6020026020010151826101f160201b60201c565b60405163011277af60e11b8152600160048201525f602482015273ba7c11d97d4b977908c5182eeb9d130474c2e67f90630224ef5e906044015f6040518083038186803b158015610139575f5ffd5b505af415801561014b573d5f5f3e3d5ffd5b50505050808061015a90610375565b9150506100aa565b5081516006556003546040516339ebe6e360e01b81526001600482015260ff909116602482015273ba7c11d97d4b977908c5182eeb9d130474c2e67f906339ebe6e390604401602060405180830381865af41580156101c3573d5f5f3e3d5ffd5b505050506040513d601f19601f820116820180604052508101906101e7919061039b565b5f55506103d59050565b6101fc8160016103b2565b6001600160a01b03929092165f908152600460205260409020805464ffffffffff191664ffffffffff9093169290921790915550565b634e487b7160e01b5f52604160045260245ffd5b80516001600160a01b038116811461025c575f5ffd5b919050565b805160ff8116811461025c575f5ffd5b5f5f60408385031215610282575f5ffd5b82516001600160401b03811115610297575f5ffd5b8301601f810185136102a7575f5ffd5b80516001600160401b038111156102c0576102c0610232565b604051600582901b90603f8201601f191681016001600160401b03811182821017156102ee576102ee610232565b60405291825260208184018101929081018884111561030b575f5ffd5b6020850194505b838510156103315761032385610246565b815260209485019401610312565b5094506103449250505060208401610261565b90509250929050565b634e487b7160e01b5f52603260045260245ffd5b634e487b7160e01b5f52601160045260245ffd5b5f64ffffffffff821664ffffffffff810361039257610392610361565b60010192915050565b5f602082840312156103ab575f5ffd5b5051919050565b64ffffffffff81811683821601908111156103cf576103cf610361565b92915050565b610a8d806103e25f395ff3fe6080604052600436106100ad575f3560e01c80638e79a15c11610066578063cc9c92e31161004c578063cc9c92e3146101eb578063d3f9fa5114610216578063ed31090b14610241575f5ffd5b80638e79a15c1461017f578063b32a95711461019e575f5ffd5b8063363f1dad11610096578063363f1dad146100ed5780633b7cd9de146101355780633df6effa1461016a575f5ffd5b8063025e2480146100b157806329c50fa9146100d9575b5f5ffd5b3480156100bc575f5ffd5b506100c660065481565b6040519081526020015b60405180910390f35b3480156100e4575f5ffd5b506100c65f5481565b3480156100f8575f5ffd5b506001546101179064ffffffffff808216916501000000000090041682565b6040805164ffffffffff9384168152929091166020830152016100d0565b348015610140575f5ffd5b5061015461014f3660046107c2565b610254565b60405164ffffffffff90911681526020016100d0565b61017d6101783660046107c2565b610285565b005b34801561018a575f5ffd5b5061017d6101993660046108bb565b610328565b3480156101a9575f5ffd5b506101db6101b83660046107c2565b6001600160a01b03165f9081526004602052604090205464ffffffffff16151590565b60405190151581526020016100d0565b3480156101f6575f5ffd5b506100c66102053660046107c2565b60056020525f908152604090205481565b348015610221575f5ffd5b5060035461022f9060ff1681565b60405160ff90911681526020016100d0565b61017d61024f3660046108f5565b6106c8565b6001600160a01b0381165f9081526004602052604081205461027f9060019064ffffffffff166109c7565b92915050565b5f8054604051909182917f5262fb268b6ad97e5b83c2aba6751e21eca0cfbef291e46408cddbaca13cd8f49190a26040517f27e74ca3000000000000000000000000000000000000000000000000000000008152600481018290526001600160a01b038316906327e74ca39034906024015f604051808303818588803b15801561030d575f5ffd5b505af115801561031f573d5f5f3e3d5ffd5b50505050505050565b5f5b81518164ffffffffff1610156105fb575f828264ffffffffff1681518110610354576103546109e4565b602002602001015190505f61036882610254565b9050610391826001600160a01b03165f9081526004602052604090205464ffffffffff16151590565b6104085760405162461bcd60e51b815260206004820152602f60248201527f41646472657373206973206e6f742061207265676973746572656420726f6f7460448201527f206272696467652061646472657373000000000000000000000000000000000060648201526084015b60405180910390fd5b5f5f836001600160a01b031663ae5582fa6040518163ffffffff1660e01b815260040160408051808303815f875af1158015610446573d5f5f3e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061046a91906109f8565b6001600160a01b0386165f9081526005602052604090205491935091508110156104fc5760405162461bcd60e51b815260206004820152602560248201527f6c6f63616c526f6f742068617320746f206265206e65776572206f722074686560448201527f2073616d6500000000000000000000000000000000000000000000000000000060648201526084016103ff565b6001600160a01b0384165f9081526005602052604090819020829055517f09489a3c000000000000000000000000000000000000000000000000000000008152600160048201526024810183905264ffffffffff8416604482015273ba7c11d97d4b977908c5182eeb9d130474c2e67f906309489a3c906064015f6040518083038186803b15801561058c575f5ffd5b505af415801561059e573d5f5f3e3d5ffd5b505050508264ffffffffff16827fd22c20021486e0e86b4af0b379484ed1fb952315fb1e05df3dda5bd6421d936e836040516105dc91815260200190565b60405180910390a35050505080806105f390610a1a565b91505061032a565b506003546040517f39ebe6e30000000000000000000000000000000000000000000000000000000081526001600482015260ff90911660248201525f9073ba7c11d97d4b977908c5182eeb9d130474c2e67f906339ebe6e390604401602060405180830381865af4158015610672573d5f5f3e3d5ffd5b505050506040513d601f19601f820116820180604052508101906106969190610a40565b60405190915081907f8e90d8cfb527d5c92458e67bc378f86769c754f180409b1e5c7ec5e183c91820905f90a25f5550565b5f8054604051909182917f5262fb268b6ad97e5b83c2aba6751e21eca0cfbef291e46408cddbaca13cd8f49190a25f5b83518110156107a1575f848281518110610714576107146109e4565b60200260200101519050806001600160a01b03166327e74ca385848151811061073f5761073f6109e4565b6020026020010151856040518363ffffffff1660e01b815260040161076691815260200190565b5f604051808303818588803b15801561077d575f5ffd5b505af115801561078f573d5f5f3e3d5ffd5b5050600190940193506106f892505050565b50505050565b80356001600160a01b03811681146107bd575f5ffd5b919050565b5f602082840312156107d2575f5ffd5b6107db826107a7565b9392505050565b634e487b7160e01b5f52604160045260245ffd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561081f5761081f6107e2565b604052919050565b5f67ffffffffffffffff821115610840576108406107e2565b5060051b60200190565b5f82601f830112610859575f5ffd5b813561086c61086782610827565b6107f6565b8082825260208201915060208360051b86010192508583111561088d575f5ffd5b602085015b838110156108b1576108a3816107a7565b835260209283019201610892565b5095945050505050565b5f602082840312156108cb575f5ffd5b813567ffffffffffffffff8111156108e1575f5ffd5b6108ed8482850161084a565b949350505050565b5f5f60408385031215610906575f5ffd5b823567ffffffffffffffff81111561091c575f5ffd5b6109288582860161084a565b925050602083013567ffffffffffffffff811115610944575f5ffd5b8301601f81018513610954575f5ffd5b803561096261086782610827565b8082825260208201915060208360051b850101925087831115610983575f5ffd5b6020840193505b828410156109a557833582526020938401939091019061098a565b809450505050509250929050565b634e487b7160e01b5f52601160045260245ffd5b64ffffffffff828116828216039081111561027f5761027f6109b3565b634e487b7160e01b5f52603260045260245ffd5b5f5f60408385031215610a09575f5ffd5b505080516020909101519092909150565b5f64ffffffffff821664ffffffffff8103610a3757610a376109b3565b60010192915050565b5f60208284031215610a50575f5ffd5b505191905056fea26469706673582212209d895b84d612b1101d2de2ddca38c4896a2c1a82f28f425b1a30e46965bb443664736f6c634300081d00330000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000030000000000000000000000005bfa9a4f358470774ec2997623efa97ecbf32263000000000000000000000000056b0485c1a76bf0a158e7dcd3d19e4d31f0cc5b0000000000000000000000001c9b9fdfb57fddf18588e0247f7dc786d9ea3d92

Deployed Bytecode

0x6080604052600436106100ad575f3560e01c80638e79a15c11610066578063cc9c92e31161004c578063cc9c92e3146101eb578063d3f9fa5114610216578063ed31090b14610241575f5ffd5b80638e79a15c1461017f578063b32a95711461019e575f5ffd5b8063363f1dad11610096578063363f1dad146100ed5780633b7cd9de146101355780633df6effa1461016a575f5ffd5b8063025e2480146100b157806329c50fa9146100d9575b5f5ffd5b3480156100bc575f5ffd5b506100c660065481565b6040519081526020015b60405180910390f35b3480156100e4575f5ffd5b506100c65f5481565b3480156100f8575f5ffd5b506001546101179064ffffffffff808216916501000000000090041682565b6040805164ffffffffff9384168152929091166020830152016100d0565b348015610140575f5ffd5b5061015461014f3660046107c2565b610254565b60405164ffffffffff90911681526020016100d0565b61017d6101783660046107c2565b610285565b005b34801561018a575f5ffd5b5061017d6101993660046108bb565b610328565b3480156101a9575f5ffd5b506101db6101b83660046107c2565b6001600160a01b03165f9081526004602052604090205464ffffffffff16151590565b60405190151581526020016100d0565b3480156101f6575f5ffd5b506100c66102053660046107c2565b60056020525f908152604090205481565b348015610221575f5ffd5b5060035461022f9060ff1681565b60405160ff90911681526020016100d0565b61017d61024f3660046108f5565b6106c8565b6001600160a01b0381165f9081526004602052604081205461027f9060019064ffffffffff166109c7565b92915050565b5f8054604051909182917f5262fb268b6ad97e5b83c2aba6751e21eca0cfbef291e46408cddbaca13cd8f49190a26040517f27e74ca3000000000000000000000000000000000000000000000000000000008152600481018290526001600160a01b038316906327e74ca39034906024015f604051808303818588803b15801561030d575f5ffd5b505af115801561031f573d5f5f3e3d5ffd5b50505050505050565b5f5b81518164ffffffffff1610156105fb575f828264ffffffffff1681518110610354576103546109e4565b602002602001015190505f61036882610254565b9050610391826001600160a01b03165f9081526004602052604090205464ffffffffff16151590565b6104085760405162461bcd60e51b815260206004820152602f60248201527f41646472657373206973206e6f742061207265676973746572656420726f6f7460448201527f206272696467652061646472657373000000000000000000000000000000000060648201526084015b60405180910390fd5b5f5f836001600160a01b031663ae5582fa6040518163ffffffff1660e01b815260040160408051808303815f875af1158015610446573d5f5f3e3d5ffd5b505050506040513d601f19601f8201168201806040525081019061046a91906109f8565b6001600160a01b0386165f9081526005602052604090205491935091508110156104fc5760405162461bcd60e51b815260206004820152602560248201527f6c6f63616c526f6f742068617320746f206265206e65776572206f722074686560448201527f2073616d6500000000000000000000000000000000000000000000000000000060648201526084016103ff565b6001600160a01b0384165f9081526005602052604090819020829055517f09489a3c000000000000000000000000000000000000000000000000000000008152600160048201526024810183905264ffffffffff8416604482015273ba7c11d97d4b977908c5182eeb9d130474c2e67f906309489a3c906064015f6040518083038186803b15801561058c575f5ffd5b505af415801561059e573d5f5f3e3d5ffd5b505050508264ffffffffff16827fd22c20021486e0e86b4af0b379484ed1fb952315fb1e05df3dda5bd6421d936e836040516105dc91815260200190565b60405180910390a35050505080806105f390610a1a565b91505061032a565b506003546040517f39ebe6e30000000000000000000000000000000000000000000000000000000081526001600482015260ff90911660248201525f9073ba7c11d97d4b977908c5182eeb9d130474c2e67f906339ebe6e390604401602060405180830381865af4158015610672573d5f5f3e3d5ffd5b505050506040513d601f19601f820116820180604052508101906106969190610a40565b60405190915081907f8e90d8cfb527d5c92458e67bc378f86769c754f180409b1e5c7ec5e183c91820905f90a25f5550565b5f8054604051909182917f5262fb268b6ad97e5b83c2aba6751e21eca0cfbef291e46408cddbaca13cd8f49190a25f5b83518110156107a1575f848281518110610714576107146109e4565b60200260200101519050806001600160a01b03166327e74ca385848151811061073f5761073f6109e4565b6020026020010151856040518363ffffffff1660e01b815260040161076691815260200190565b5f604051808303818588803b15801561077d575f5ffd5b505af115801561078f573d5f5f3e3d5ffd5b5050600190940193506106f892505050565b50505050565b80356001600160a01b03811681146107bd575f5ffd5b919050565b5f602082840312156107d2575f5ffd5b6107db826107a7565b9392505050565b634e487b7160e01b5f52604160045260245ffd5b604051601f8201601f1916810167ffffffffffffffff8111828210171561081f5761081f6107e2565b604052919050565b5f67ffffffffffffffff821115610840576108406107e2565b5060051b60200190565b5f82601f830112610859575f5ffd5b813561086c61086782610827565b6107f6565b8082825260208201915060208360051b86010192508583111561088d575f5ffd5b602085015b838110156108b1576108a3816107a7565b835260209283019201610892565b5095945050505050565b5f602082840312156108cb575f5ffd5b813567ffffffffffffffff8111156108e1575f5ffd5b6108ed8482850161084a565b949350505050565b5f5f60408385031215610906575f5ffd5b823567ffffffffffffffff81111561091c575f5ffd5b6109288582860161084a565b925050602083013567ffffffffffffffff811115610944575f5ffd5b8301601f81018513610954575f5ffd5b803561096261086782610827565b8082825260208201915060208360051b850101925087831115610983575f5ffd5b6020840193505b828410156109a557833582526020938401939091019061098a565b809450505050509250929050565b634e487b7160e01b5f52601160045260245ffd5b64ffffffffff828116828216039081111561027f5761027f6109b3565b634e487b7160e01b5f52603260045260245ffd5b5f5f60408385031215610a09575f5ffd5b505080516020909101519092909150565b5f64ffffffffff821664ffffffffff8103610a3757610a376109b3565b60010192915050565b5f60208284031215610a50575f5ffd5b505191905056fea26469706673582212209d895b84d612b1101d2de2ddca38c4896a2c1a82f28f425b1a30e46965bb443664736f6c634300081d0033

Constructor Arguments (ABI-Encoded and is the last bytes of the Contract Creation Code above)

0000000000000000000000000000000000000000000000000000000000000040000000000000000000000000000000000000000000000000000000000000000500000000000000000000000000000000000000000000000000000000000000030000000000000000000000005bfa9a4f358470774ec2997623efa97ecbf32263000000000000000000000000056b0485c1a76bf0a158e7dcd3d19e4d31f0cc5b0000000000000000000000001c9b9fdfb57fddf18588e0247f7dc786d9ea3d92

-----Decoded View---------------
Arg [0] : _gigaRootRecipients (address[]): 0x5BFA9A4f358470774eC2997623efA97ecbf32263,0x056B0485c1A76bf0A158e7DCd3D19e4d31f0CC5b,0x1c9b9Fdfb57fDdF18588e0247F7Dc786d9eA3D92
Arg [1] : _maxTreeDepth (uint8): 5

-----Encoded View---------------
6 Constructor Arguments found :
Arg [0] : 0000000000000000000000000000000000000000000000000000000000000040
Arg [1] : 0000000000000000000000000000000000000000000000000000000000000005
Arg [2] : 0000000000000000000000000000000000000000000000000000000000000003
Arg [3] : 0000000000000000000000005bfa9a4f358470774ec2997623efa97ecbf32263
Arg [4] : 000000000000000000000000056b0485c1a76bf0a158e7dcd3d19e4d31f0cc5b
Arg [5] : 0000000000000000000000001c9b9fdfb57fddf18588e0247f7dc786d9ea3d92


Block Uncle Number Difficulty Gas Used Reward
View All Uncles
Loading...
Loading
0xeae835289f34dE789C370929d33458919c106a22
Loading...
Loading
Loading...
Loading
[ Download: CSV Export  ]
[ Download: CSV Export  ]

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.