// SPDX-License-Identifier: MIT pragma solidity 0.8.24; import "../ServiceFundedUsdtLotteryRound.sol"; import "./DirectFundingVrfAdapter.sol"; /// @notice Constructor-only deployment with immutable adapter/round binding and native prefunding. contract ServiceFundedRoundBootstrapper { address public immutable adapter; address public immutable round; error InvalidConfig(); error NativeFundingFailed(); constructor(ServiceFundedUsdtLotteryRound.Config memory c, DirectFundingVrfAdapter.Config memory oracle) payable { if (c.randomness != address(0)) revert InvalidConfig(); // This contract's first CREATE is the adapter; its second CREATE is the round. address expectedRound = address(uint160(uint256(keccak256(abi.encodePacked(hex"d694", address(this), hex"02"))))); address deployedAdapter = address(new DirectFundingVrfAdapter(expectedRound, c.treasury, oracle)); c.randomness = deployedAdapter; address deployedRound = address(new ServiceFundedUsdtLotteryRound(c)); if (deployedRound != expectedRound) revert InvalidConfig(); adapter = deployedAdapter; round = deployedRound; if (msg.value != 0) { (bool success,) = payable(deployedAdapter).call{value: msg.value}(""); if (!success) revert NativeFundingFailed(); } } }