{"assessments":[],"deployments":[{"attestationHash":"5b25c0db4edd426a06b98b4d7bf2108d974c292b743b85f0c87609c795afb0ae","chainId":1,"contracts":[],"id":"49157b8c-728a-4f12-8c49-ea012783d898","manifestHash":"018e53aa9f629156cd6aa8d3a1d8d5caa3b095ef645a9f1eb9ffb9c29aadf6be","status":"parked"}],"fuzz":[],"identity":{"adapter":"0xde152afb7db5373f34876e1499fbd893a82dd336","chainId":1,"collection":"0x0000ec93127baa929e58e97dd0095a2bfb38ec1d","registry":"0x8004a169fb4a3325136eb29fa0ceb6d2e539a432"},"interpretation":"Records acceptance and evidence. Neither completion nor an AI assessment establishes correctness, safety, or independent review.","jobId":"e657ede5-15ce-4580-95dd-af7c56f3e46a","kind":"shape:chain","nodes":[{"acceptedSubmissionHash":"5df6f4873e942fce0cbbb3c5372d5ca1abdcb9d06ee0a392c8d52687ab519224","dependsOn":["manifest"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"9897597976b0e72440db7ca402d225aea20f3d37205ba53e7df2400ff80f29cc","skillId":"audit-imported-code","tools":[]},"key":"audit_imported_code","kind":"code","role":"review","skillHash":"9897597976b0e72440db7ca402d225aea20f3d37205ba53e7df2400ff80f29cc","skillId":"audit-imported-code","state":"accepted"},{"acceptedSubmissionHash":"9f8bbfaffaabf57677d02686742990d75a4312955a13a0b1d401d365a07a4531","dependsOn":[],"execution":{"network":false,"profile":"foundry","requires":[],"tools":[]},"key":"manifest","kind":"code","role":"integrate","skillHash":null,"skillId":null,"state":"accepted"}],"objective":"Launch the Swarmlings repository on Ethereum mainnet as a univ4_hook launch paired with IMD, exactly as launch.json describes: token Swarmlings (LING) with constructor (), hook SwarmlingsHook with constructor ($poolManager, $token) at an address whose low 14 bits are all set (0x3FFF, all hook flags), pool IMD / LING at fee 12500, tick spacing 60. Do not change the contracts' behaviour; adapt only what the launcher needs, and leave src/ untouched: the hook's bytecode is tuned so the protected floor finds its CREATE2 salt quickly (BUILD_TAG in SwarmlingsHook.sol, guarded by test/HookSalt.t.sol); launch 1954 parked because that search ran setUp out of memory gas. Access: the token and the NFT contract have no owner and cannot change; owner() is a marketplace label with no power. The hook is a router whose fee slices and modules can be changed only by SwarmlingsCouncil, already deployed at 0x4d0b3507D80f678d9e658Fd5482Ca6a96636A032 and owned by the dev wallet 0x92cEf4823119f3332A85A39023eEbA01a06890c4, at once with a logged memo, within limits fixed in code: total hook fee at most 5%, the holders' 1.25% fixed, no module can block a sell or a liquidity removal. At launch there are no slices and no modules. Anyone may call SwarmlingsHook.distribute(), Swarmlings.syncEth(), syncToken(), addRewards() and a sink's poke(); claim(), claimEth() and claimToken() pay only the caller's own rewards; claimDev() pays only the fixed DEV wallet. Numbers: 300,000 LING per NFT, 3,333 NFTs max, 1.25% hook fee in IMD to holders on every LING / IMD pool using the hook, a 60-second launch snipe tax on buys falling from 40% to 0 (to holders), 5% creator fee on NFT sales (half to holders in ETH, half to DEV), rewards that arrive on one UTC day are paid out the next day per second held, poolBps 9000, auto-skip above 800 NFTs minted in one transfer. This job only launches the contracts; the site is built afterwards in a continuation that reads the live addresses.","parentJobId":null,"planHash":"5748b563491ca7e779f6682d037ad43554ad5ff2cf4047c68d829d0c783bec34","previousHash":"13de2691d3fe42ee1278d781bc6c23f77f27b5baabe036b897163285da59efe9","projectId":"e657ede5-15ce-4580-95dd-af7c56f3e46a","publication":{"commit":"28468a08a439d910ed4b0de90807f4924383c225","deliveredAt":"2026-10-18T14:05:03.962Z","repoUrl":"https://github.com/identity-md-launches/launch-2167-launch-swarmlings-repository-ethereum"},"receiptIdentity":{"adapter":"0xde152afb7db5373f34876e1499fbd893a82dd336","chainId":1,"collection":"0x0000ec93127baa929e58e97dd0095a2bfb38ec1d","registry":"0x8004a169fb4a3325136eb29fa0ceb6d2e539a432"},"registry":"0xb6d0a187b050fa5bb0b87033a203f37becf4a775","research":[],"schema":"identitymd-work-v1","signals":[],"site":null,"snapshotHash":"2ea220db8c279d9366a616bfc17155c25bd049c51116be35fdc2f7e2991ee5dc","state":"completed","submissions":[{"artifacts":[],"attempt":1,"bundleHash":null,"device":"776c025db24644e8","findings":[{"citation":"resolved","description":"snipeBps() is 4000 in the block the launch pool is initialized and falls to 0 over 60 s. _quote adds it to every buy on a charged pool regardless of who the swap's sender is. The hook exempts its deployer (`launcher`, the IMD launch factory) from the JIT penalty but not from the snipe tax, so if the factory performs a seed buy of LING with the payer's IMD inside the launch transaction (the same block as afterInitialize), 41.25% of that IMD (1.25% holder fee + 40% snipe) is minted as holder claims to the hook instead of buying LING. At that moment no Swarmling NFT exists, so the amount is queued and paid to whoever holds NFTs the next UTC day; it is not lost to the system, but it is not the payer's LING either. If the factory does not swap inside the launch transaction, this has no effect on the launch and is only the designed sniper deterrent. The adapter should confirm which it is. Nothing to change in src if no seed buy is made.","line":542,"path":"src/SwarmlingsHook.sol","reproduction":"State: launch pool just initialized (block.timestamp == hook.launchedAt()). Call: swapRouter.swap(launchKey, SwapParams(zeroForOne = rewardIsCurrency0, amountSpecified = -1_000e18, limit = MIN/MAX bound)). Observed (test/scratch/Seed.t.sol, ImdFirst pairing): hook.pendingFees() rises by 412_500000000000000000 (412.5 IMD) for a 1,000 IMD exact-in buy; hook.snipeBps() == 4000. Expected if the seed buy were meant to be exempt like the factory's liquidity: 12.5 IMD (holder floor only). 60 seconds later the same buy pays 12.5 IMD.","severity":"low","snippet":"        if (buy) bps += snipeBps();","title":"Launch-block buys, a factory seed buy included, pay the 40% snipe tax to the holders' pot"},{"citation":"resolved","description":"For exact-in buys and exact-out sells (IMD is the specified currency) the fee is taken in beforeSwap on the full specified amount; afterSwap then requires the pool to have swapped exactly amountSpecified + fee and reverts otherwise. Any price limit that stops the swap early therefore reverts the whole transaction (v4 wraps it as WrappedError(hook, afterSwap.selector, PartialFill(), HookCallFailed())). Universal Router and the test routers pass the MIN/MAX bounds, so ordinary users are unaffected, and the behaviour is documented in the source. It matters for this launch only if the factory's launch transaction performs a seed swap with a tight sqrtPriceLimitX96: that swap, and with it the launch transaction, would revert. Informational: accepted design, no change requested.","line":366,"path":"src/SwarmlingsHook.sol","reproduction":"State: launch pool open, 60 s after launch. Call: swapRouter.swap(launchKey, SwapParams(zeroForOne = buy direction, amountSpecified = -100_000e18 IMD, sqrtPriceLimitX96 = current price * 0.995 (or * 1.005 for the other ordering))). Observed (test/scratch/Seed.t.sol): revert WrappedError(0x...3ffF, 0xb47b2fb1 afterSwap, 0xd964f528 PartialFill, 0xa9e35b2f HookCallFailed). Expected by a caller used to v4 semantics: a partial fill up to the limit. With sqrtPriceLimitX96 = TickMath.MIN_SQRT_PRICE + 1 the same swap succeeds.","severity":"info","snippet":"            if (rewardDelta != params.amountSpecified + int256(fee)) revert PartialFill();","title":"A reward-specified swap that hits its sqrtPriceLimit reverts (PartialFill) instead of filling partially"},{"citation":"resolved","description":"The token mints one Swarmling per 300,000 LING received by any address without code (and 7702 wallets) and only switches the receiver to skipNFT when a single transfer would mint more than 800. Measured on this tree: a 100,000,000 LING transfer to a fresh EOA (333 NFTs) costs 4,130,937 gas; 240,000,000 LING (800 NFTs) costs 9,541,938 gas; 240,300,000 LING (801, auto-skip) costs 114,329 gas. Creation of the token with its mirror is about 4.3M and of the hook about 4.6M (creation code 22,432 and 23,469 bytes). The manifest asks for poolBps 9000 so that no allocation reaches an EOA, but the remaining 10% follows the launch policy's split: if any of it is transferred to an address without code inside the launch transaction, the transaction grows by the figures above (a 10% EOA treasury adds 4.13M, bringing the launch to roughly 14M against the 16,777,216 EIP-7825 cap and whatever gasCeilingWei the policy sets). Contract recipients (lock, treasury contract, PoolManager, factory) skip NFTs and are unaffected. No change to src requested; the adapter should check the policy's recipients.","line":430,"path":"src/Swarmlings.sol","reproduction":"vm.chainId(1); factory deploys Swarmlings; factory.transfer(eoa, 100_000_000e18): gas 4,130,937 and mirror.balanceOf(eoa) == 333. factory.transfer(eoa2, 240_000_000e18): gas 9,541,938, 800 NFTs. factory.transfer(eoa3, 240_300_000e18): gas 114,329, 0 NFTs, AutoSkipNFT(eoa3, 801) emitted. (test/scratch/Gas.t.sol on this tree.)","severity":"info","snippet":"            if (mint > have + MAX_MINT_PER_TRANSFER) {","title":"Every EOA or EIP-7702 wallet that receives LING inside the launch transaction mints NFTs at about 12.4k gas each (auto-skip only above 800)"},{"citation":"resolved","description":"The CREATE2 address depends on keccak256(creationCode ++ abi.encode(manager, token)). test/HookSalt.t.sol bounds the search for four (deployer, manager) combinations, all with the probe token 0x70ce. For any other token address the number of salts until the low 14 bits are all set is a fresh geometric draw with mean 16,384 (P(> 57,357) is about 3%), so the tuning holds for the floor only if the floor really substitutes 0x70ce for the token, as the test assumes; a floor that deploys the real token first and mines against its address gets no benefit from BUILD_TAG and could hit the same MemoryOOG as launch 1954. The deployer's own off-chain salt mining is unaffected. The constant itself is behaviour-free (a public constant getter; validated by all 240 tests). Informational: nothing in src to change; the adapter should confirm the floor's probe addresses against the test's constants (0xfac7, 0x900c, 0x70ce, factory 0x12C63b58..., manager 0x0000...8A90).","line":75,"path":"src/SwarmlingsHook.sol","reproduction":"forge test --match-path test/HookSalt.t.sol passes (search ends within 1,000 / 5,000 salts for the four listed combinations). Replace TOKEN_PROBE with any other address, e.g. address(0x70cf), in a scratch copy of _salts: the count is unrelated to BUILD_TAG and is on average 16,384.","severity":"info","snippet":"    bytes32 public constant BUILD_TAG = 0x184d9531afc21a46a0cbb7a9731f40a0966c64069b5c5adc81173f1ef4de7335;","title":"BUILD_TAG keeps the salt search short only for the probe token address the HookSalt test uses"},{"citation":"resolved","description":"Commit 69b2407 moved AddressData.balance to the low 96 bits of its slot and gave totalSupply its own slot so forge-std deal can set LING. The reorder is behaviour-neutral (no assembly reads the struct by offset: grep of sload/sstore in DN404.sol shows only the Uint32Map/Bitmap helpers, and all 240 tests pass), but the balance slot is still packed: bits 96..127 hold ownedLength, 128..159 addressAlias, 160..167 flags (skipNFT, initialized), 168..255 aux. forge-std 1.17's stdstore masks packed fields, so deal(ling, holder, x) on this tree only writes the balance (test_dealWritesLingBalanceAndSupply). A verifier that writes the full slot (older forge-std, or vm.store on the located slot) on an address that already owns NFTs would zero ownedLength and flags, after which that address's NFT count and skipNFT state disagree with its balance. Informational for the verifier and the adapter; nothing to change in src or lib (lib is read-only for this launch).","line":147,"path":"lib/dn404/src/DN404.sol","reproduction":"holder owns 3 NFTs (900,000 LING). vm.store(address(ling), slotOf(addressData[holder]), bytes32(uint256(1_200_000e18))) writes balance = 1.2M but ownedLength = 0 and flags = 0: mirror.balanceOf(holder) still reports 3 through the owned array while ownedLength says 0; the next transfer out reverts or mis-burns. With forge-std deal(address(ling), holder, 1_200_000e18) on this tree the same scenario keeps ownedLength = 3 (packed write is masked).","severity":"info","snippet":"        uint96 balance;","title":"Vendored DN404 field reorder: balance now shares its slot with ownedLength, alias and flags; a whole-slot write by a verifier would corrupt the NFT bookkeeping"},{"citation":"resolved","description":"The launch rules list anything configured after deployment as a medium finding for the adapter to remove. Here the hook is a router by the requester's specification: SwarmlingsCouncil (verified on chain at 0x4d0b3507D80f678d9e658Fd5482Ca6a96636A032 with owner() == DEV 0x92cEf4823119f3332A85A39023eEbA01a06890c4) may set at most 8 slices totalling at most 375 bps on top of the fixed 125 bps holder floor, at most 8 modules, and may hand over or freeze the council. The bounds are constants; the code paths were reviewed: no slice or module can block a sell or a liquidity removal (observers are gas-capped raw calls with no return-data copy; guard reverts are bubbled only on buys, adds and donates), a quoter's answer is clamped before it is added, sinks spend only their own ERC-6909 claims, setSlices rejects the hook and the token as sinks. There is no proxy, initializer, DELEGATECALL, CALLCODE or SELFDESTRUCT in src or the vendored DN404, no mint after construction, no pause, freeze, blacklist or seizure. Recorded as informational because the assignment and the audit report accept this design (C-3 / C-4 accepted); no change requested.","line":860,"path":"src/SwarmlingsHook.sol","reproduction":"Trust assumption, not a failure: as COUNCIL.owner (DEV), council.execute(hook, abi.encodeCall(hook.setSlices, ([Slice(sink, 375, false)])), memo) succeeds at once; Slice(sink, 376, false) reverts FeeTooHigh; setModules with a guard that reverts onBeforeSwap blocks buys only, sells on the launch pool still succeed (test_audit_badQuotersNeverBlockSells and the Hive suite).","severity":"info","snippet":"    function setSlices(Slice[] calldata s) external onlyCouncil {","title":"Post-deployment configuration surface (council: slices, modules, setCouncil) exists by design and is empty at launch"}],"hash":"5df6f4873e942fce0cbbb3c5372d5ca1abdcb9d06ee0a392c8d52687ab519224","nodeId":"42e0851c-d243-4e03-b66c-a19772739158","outcome":"completed","summary":"The review is complete and `.imd-findings.json` holds six findings plus a 55-row coverage record. Nothing I found would stop or break this launch.\n\n**Verdict.** No critical, high or medium defects. All 240 project tests pass on this tree, and the four mainnet fork tests pass against the real OpenSea validator and the real IMD token when run through a public RPC. The manifest is schema-valid: IMD paired, fee 12500, tick spacing 60, two constructor args in order, 14 permissions matching both `getHookPermissions` and the 0x3FFF address mask, notes under the 4,000-character cap.\n\n**What I verified beyond the code.** IMD is verified source (BridgedFP, an OpenZeppelin ERC-20 plus LayerZero OFT) with no pause, blocklist or transfer fee, so the hook's IMD hand-over in `beforeSwap` cannot be blocked by the paired token. The council at its CREATE2 address has code and its on-chain owner is the DEV wallet. The launch factory, PoolManager, validator and renderer all have code on mainnet. No DELEGATECALL, CALLCODE, SELFDESTRUCT, proxy, initializer, post-launch mint, pause or seizure exists in src or the vendored DN404.\n\n**Findings, by severity.**\n- **Low: launch-block buys pay the snipe tax.** The hook exempts the factory from the JIT penalty but not from the 40% snipe tax. A 1,000 IMD exact-in buy in the launch block sends 412.5 IMD to the holders' pot. This only matters if the factory seeds a buy inside the launch transaction.\n- **Info: limit-bounded specified swaps revert.** An exact-in buy whose price limit stops the swap early reverts with PartialFill wrapped by v4. Routers using the MIN/MAX bounds are unaffected. A factory seed swap with a tight limit would revert the launch transaction.\n- **Info: launch-transaction gas.** Any address without code that receives LING in the launch transaction mints NFTs. Measured: 333 NFTs cost 4.13M gas, 800 cost 9.54M, auto-skip starts at 801. With token and hook creation near 9M, a 10% EOA recipient pushes the transaction to about 14M.\n- **Info: BUILD_TAG tuning** holds only for the probe token address the HookSalt test uses. For any other token address the salt count is a fresh draw averaging 16,384.\n- **Info: DN404 field reorder** is behaviour-neutral, but the balance still shares a packed slot with the NFT counters. A verifier writing the whole slot on an address that owns NFTs would corrupt its bookkeeping. forge-std 1.17's deal masks correctly.\n- **Info: post-deployment configuration** through the council exists by the requester's design and is bounded by constants. Recorded for the launch rule list, no change requested.\n\n**Coverage.** I read all four src contracts, all seven modules, the interface file, the vendored DN404 token and mirror, the manifest, and the launch, salt, manifest and fork tests. Every listed entry point has a verdict: 52 hold, 3 point to the findings above, none unreached. I could not read the launch factory's source, which is unverified, so the seed-buy and allocation questions in the first three findings are for the adapter to confirm against the policy.","treeHash":null,"usage":{"cachedInputTokens":1535267,"inputTokens":386,"model":"claude-fable-5-1","outputTokens":56794,"runtime":"claude","turns":31,"wallClockMs":817053}},{"artifacts":[],"attempt":1,"bundleHash":"ffc25a898ba2af72c300a2890cce68025d5292e4456af69eb1898f2d95ec5f20","device":"4f2ce49dc630c86e","findings":[{"description":"stdStorage find(StdStorage): Failed to write value.\n\nRepair: the launch factory collects its zero-liquidity fee from every pool it created, and the hook must not revert, skim or redirect that collect. Check for an `onlyOwner`/role gate on fee callbacks, a revert in `beforeSwap`/`afterSwap` when the caller is the factory, or a transfer hook that steals the factory's take. The factory's fee goes to the network; a hook that blocks it freezes the payer's and the network's economics together.","line":null,"path":null,"reproduction":"The verifier deployed the manifest's contracts as the launch deploys them: from the launch factory (msg.sender), with IMD's launch wallet as tx.origin and $owner set, then read owner(), admin(), getOwner() and the admin role, and for a hook opened, seeded, traded and collected the pool from the factory (test/protected/univ4_hook/Owners.protected.t.sol in the protected floor).","severity":"high","title":"A launch contract blocks the launch factory's fee collect"}],"hash":"9f8bbfaffaabf57677d02686742990d75a4312955a13a0b1d401d365a07a4531","nodeId":"503b37c9-32f3-4458-b92f-840f74d24ff0","outcome":"completed","summary":"`launch.json` was already in the repo and matched the source, so I made one small edit to its notes. `forge build` passed, and `forge test` with the verifier's fuzz seed passed all 244 tests, including `test/Manifest.t.sol`, which checks the manifest against the source.\n\nWhat I confirmed against the code:\n- **Contracts:** the hook is `SwarmlingsHook`, built with `[\"$poolManager\", \"$token\"]`, matching its constructor `(IPoolManager manager, address token)`. The token is `Swarmlings` (LING, 18 decimals), whose constructor takes no arguments.\n- **Permissions:** the manifest lists all 14 hook flags, exactly what `getHookPermissions` returns. That includes both `beforeInitialize` and `afterInitialize`, which only the PoolManager can call and which return the correct selectors. Neither refuses fee 12500, and the hook's `LAUNCH_LP_FEE` is 12500.\n- **Pool:** paired with IMD (`0xd34a99bc0f67ae1bbd63c660e6d0b0dd03e263b7`), fee 12500, tick spacing 60, initial price `79228162514264337593543950336`.\n\nThe notes edit:\n- **Council wording:** the old notes said SwarmlingsCouncil would be \"deployed by us separately\". They now say it is already deployed on mainnet, owned by the dev wallet `0x92cEf4823119f3332A85A39023eEbA01a06890c4`, and limited in code: total hook fee at most 5%, the holders' 1.25% fixed, and no module can block a sell or a liquidity removal.\n- **Initialize callbacks:** I added a sentence on how `beforeInitialize` and `afterInitialize` are restricted.\n\nThe notes are now 3,651 characters, under the 4,000 cap.\n\nNo other file changed, and `src/` is untouched. I haven't committed the change.","treeHash":"25223f730c98d2d973be59a7ccc2f3bfa0a0cd60","usage":{"cachedInputTokens":163871,"inputTokens":12,"model":"claude-opus-5-5","outputTokens":2080,"runtime":"claude","turns":6,"wallClockMs":83169}}],"verification":[{"checks":[{"durationMs":11556,"exitCode":0,"name":"build","output":"Compiling 110 files with Solc 0.8.26\nSolc 0.8.26 finished in 11.45s\nCompiler run successful with warnings:\nWarning (8760): This declaration has the same name as another declaration.\n   --> src/SwarmlingsHook.sol:242:51:\n    |\n242 |     function currentSwap() external view returns (bool buy, uint256 bps, uint256 fee) {\n    |                                                   ^^^^^^^^\nNote: The other declaration is here:\n   --> src/SwarmlingsHook.sol:707:5:\n    |\n707 |     function buy(uint256 budget, uint160 sqrtPriceLimitX96)\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\nWarning (8760): This declaration has the same name as another declaration.\n   --> src/SwarmlingsHook.sol:320:9:\n    |\n320 |         bool buy = _isBuy(params);\n    |         ^^^^^^^^\nNote: The other declaration is here:\n   --> src/SwarmlingsHook.sol:707:5:\n    |\n707 |     function buy(uint256 budget, uint160 sqrtPriceLimitX96)\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\nWarning (8760): This declaration has the same name as another declaration.\n   --> src/SwarmlingsHook.sol:358:9:\n    |\n358 |         bool buy = _isBuy(params);\n    |         ^^^^^^^^\nNote: The other declaration is here:\n   --> src/SwarmlingsHook.sol:707:5:\n    |\n707 |     function buy(uint256 budget, uint160 sqrtPriceLimitX96)\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\nWarning (8760): This declaration has the same name as another declaration.\n   --> src/SwarmlingsHook.sol:520:21:\n    |\n520 |     function _quote(bool buy, uint256 depth) private returns (uint256 bps) {\n    |                     ^^^^^^^^\nNote: The other declaration is here:\n   --> src/SwarmlingsHook.sol:707:5:\n    |\n707 |     function buy(uint256 budget, uint160 sqrtPriceLimitX96)\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\nWarning (8760): This declaration has the same name as another declaration.\n   --> src/SwarmlingsHook.sol:644:49:\n    |\n644 |     function _collect(uint256 fee, uint256 bps, bool buy) private {\n    |                                                 ^^^^^^^^\nNote: The other declaration is here:\n   --> src/SwarmlingsHook.sol:707:5:\n    |\n707 |     function buy(uint256 budget, uint160 sqrtPriceLimitX96)\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:287:30:\n    |\n287 |     function afterInitialize(address sender, PoolKey calldata key, uint160 sqrtPriceX96, int24 tick)\n    |                              ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:287:68:\n    |\n287 |     function afterInitialize(address sender, PoolKey calldata key, uint160 sqrtPriceX96, int24 tick)\n    |                                                                    ^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:287:90:\n    |\n287 |     function afterInitialize(address sender, PoolKey calldata key, uint160 sqrtPriceX96, int24 tick)\n    |                                                                                          ^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:312:9:\n    |\n312 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:315:9:\n    |\n315 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:341:9:\n    |\n341 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:345:9:\n    |\n345 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:392:9:\n    |\n392 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:394:9:\n    |\n394 |         ModifyLiquidityParams calldata params,\n    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:395:9:\n    |\n395 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:409:9:\n    |\n409 |         BalanceDelta delta,\n    |         ^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:411:9:\n    |\n411 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:427:9:\n    |\n427 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:429:9:\n    |\n429 |         ModifyLiquidityParams calldata params,\n    |         ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:430:9:\n    |\n430 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:444:9:\n    |\n444 |         BalanceDelta delta,\n    |         ^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:446:9:\n    |\n446 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:489:9:\n    |\n489 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:491:9:\n    |\n491 |         uint256 amount0,\n    |         ^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:492:9:\n    |\n492 |         uint256 amount1,\n    |         ^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:493:9:\n    |\n493 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:502:9:\n    |\n502 |         address sender,\n    |         ^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:504:9:\n    |\n504 |         uint256 amount0,\n    |         ^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:505:9:\n    |\n505 |         uint256 amount1,\n    |         ^^^^^^^^^^^^^^^\n\nWarning (5667): Unused function parameter. Remove or comment out the variable name to silence this warning.\n   --> src/SwarmlingsHook.sol:506:9:\n    |\n506 |         bytes calldata hookData\n    |         ^^^^^^^^^^^^^^^^^^^^^^^\n\nWarning (2018): Function state mutability can be restricted to view\n  --> test/fork/Validator.t.sol:58:5:\n   |\n58 |     function test_fork_marketplaceView() public {\n   |     ^ (Relevant source part starts here and spans across multiple lines).\n\n","passed":true},{"durationMs":2541,"exitCode":0,"name":"test","output":"No files changed, compilation skipped\n\nRan 4 tests for test/fork/Validator.t.sol:ValidatorForkTest\n[PASS] test_fork_marketplaceView() (gas: 2305)\n[PASS] test_fork_ownersMoveTheirOwnNfts() (gas: 2305)\n[PASS] test_fork_realImdRewards() (gas: 2371)\n[PASS] test_fork_unauthorizedOperatorsAreStopped() (gas: 2306)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 372.76µs (228.35µs CPU time)\n\nRan 1 test for test/Manifest.t.sol:ManifestTest\n[PASS] test_launchJsonPairsWithImdAtTheLaunchTier() (gas: 31202)\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 466.90µs (334.04µs CPU time)\n\nRan 3 tests for test/Launcher.t.sol:LingFirstLauncherTest\n[PASS] test_dealWritesLingBalanceAndSupply() (gas: 567615)\n[PASS] test_launcherCollectsItsWholeFeeInsideTheJitWindow() (gas: 906207)\n[PASS] test_launcherIsTheDeployer() (gas: 5671)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.68ms (1.16ms CPU time)\n\nRan 1 test for test/SwarmlingsHook.t.sol:TokenOnlySeedTest\n[PASS] test_firstBuysWorkWithAnEmptyManager() (gas: 3863709)\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 6.74ms (3.14ms CPU time)\n\nRan 1 test for test/GasCap.t.sol:GasCapTest\n[PASS] test_gasWorstCases() (gas: 28574142)\nLogs:\n  n 800\n  buy exact-out minting n    9750848\n  transfer moving n NFTs     5976267\n  sell burning n NFTs        4031202\n  plain transfer minting n   9550855\n  EIP-7825 cap               16777216\n\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 13.62ms (10.65ms CPU time)\n\nRan 1 test for test/HookSalt.t.sol:HookSaltTest\n[PASS] test_floorFindsTheHookSaltQuickly() (gas: 6498182)\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 17.11ms (16.83ms CPU time)\n\nRan 3 tests for test/Launcher.t.sol:ImdFirstLauncherTest\n[PASS] test_dealWritesLingBalanceAndSupply() (gas: 567615)\n[PASS] test_launcherCollectsItsWholeFeeInsideTheJitWindow() (gas: 906548)\n[PASS] test_launcherIsTheDeployer() (gas: 5671)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 18.11ms (1.59ms CPU time)\n\nRan 3 tests for test/Launcher.t.sol:NativeLauncherTest\n[PASS] test_dealWritesLingBalanceAndSupply() (gas: 567615)\n[PASS] test_launcherCollectsItsWholeFeeInsideTheJitWindow() (gas: 2539376)\n[PASS] test_launcherIsTheDeployer() (gas: 5671)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 22.45ms (2.65ms CPU time)\n\nRan 22 tests for test/SwarmlingsHook.t.sol:LingFirstHookTest\n[PASS] testFuzz_feeModes(uint256,uint8) (runs: 256, μ: 4940851, ~: 4363342)\n[PASS] test_buyExactIn() (gas: 383283)\n[PASS] test_buyExactOut() (gas: 472746)\n[PASS] test_callbacksOnlyFromManager() (gas: 121066)\n[PASS] test_distributeNeedsMinimum() (gas: 1859196)\n[PASS] test_distributeStreamsEverythingToHolders() (gas: 1130755)\n[PASS] test_everyLingRewardPoolPaysTheHolderFee() (gas: 855720)\n[PASS] test_feesWithNoHoldersWaitForTheFirstNft() (gas: 1405786)\n[PASS] test_flashBorrowedNftsEarnNothing() (gas: 9004478)\n[PASS] test_holdersClaim() (gas: 3801285)\n[PASS] test_jitPenaltyOnlyWithinTheWindow() (gas: 897880)\n[PASS] test_launchPoolCannotBeHijacked() (gas: 442285)\n[PASS] test_onlyTheFirstLaunchPairPays() (gas: 90280)\n[PASS] test_partialFillRevertsWhenFeeWasTakenUpFront() (gas: 200713)\n[PASS] test_permissionsAndLaunchPool() (gas: 79828)\n[PASS] test_poolAndRoutersNeverHoldNfts() (gas: 7903002)\n[PASS] test_rewardsFollowTimeHeld() (gas: 1582140)\n[PASS] test_sellExactIn() (gas: 598827)\n[PASS] test_sellExactOut() (gas: 809213)\n[PASS] test_skippedHandOverGivesALateBuyerNoBackPay() (gas: 7882561)\n[PASS] test_unsolicitedUnlockCallbackReverts() (gas: 35256)\n[PASS] test_whaleBuyMintsManyNfts() (gas: 1575529)\nLogs:\n  gas, exact-out buy minting 100 NFTs: 1551942\n\nSuite result: ok. 22 passed; 0 failed; 0 skipped; finished in 133.48ms (152.40ms CPU time)\n\nRan 22 tests for test/SwarmlingsHook.t.sol:ImdFirstHookTest\n[PASS] testFuzz_feeModes(uint256,uint8) (runs: 256, μ: 4904993, ~: 4362527)\n[PASS] test_buyExactIn() (gas: 383646)\n[PASS] test_buyExactOut() (gas: 471931)\n[PASS] test_callbacksOnlyFromManager() (gas: 121066)\n[PASS] test_distributeNeedsMinimum() (gas: 1859492)\n[PASS] test_distributeStreamsEverythingToHolders() (gas: 1130301)\n[PASS] test_everyLingRewardPoolPaysTheHolderFee() (gas: 858568)\n[PASS] test_feesWithNoHoldersWaitForTheFirstNft() (gas: 1405623)\n[PASS] test_flashBorrowedNftsEarnNothing() (gas: 9023791)\n[PASS] test_holdersClaim() (gas: 3800728)\n[PASS] test_jitPenaltyOnlyWithinTheWindow() (gas: 898189)\n[PASS] test_launchPoolCannotBeHijacked() (gas: 442219)\n[PASS] test_onlyTheFirstLaunchPairPays() (gas: 90346)\n[PASS] test_partialFillRevertsWhenFeeWasTakenUpFront() (gas: 201096)\n[PASS] test_permissionsAndLaunchPool() (gas: 79828)\n[PASS] test_poolAndRoutersNeverHoldNfts() (gas: 7903055)\n[PASS] test_rewardsFollowTimeHeld() (gas: 1581744)\n[PASS] test_sellExactIn() (gas: 598521)\n[PASS] test_sellExactOut() (gas: 810319)\n[PASS] test_skippedHandOverGivesALateBuyerNoBackPay() (gas: 7901489)\n[PASS] test_unsolicitedUnlockCallbackReverts() (gas: 35256)\n[PASS] test_whaleBuyMintsManyNfts() (gas: 1574712)\nLogs:\n  gas, exact-out buy minting 100 NFTs: 1551125\n\nSuite result: ok. 22 passed; 0 failed; 0 skipped; finished in 156.22ms (180.14ms CPU time)\n\nRan 22 tests for test/SwarmlingsHook.t.sol:NativeHookTest\n[PASS] testFuzz_feeModes(uint256,uint8) (runs: 256, μ: 6040025, ~: 6756913)\n[PASS] test_buyExactIn() (gas: 2108546)\n[PASS] test_buyExactOut() (gas: 440234)\n[PASS] test_callbacksOnlyFromManager() (gas: 120586)\n[PASS] test_distributeNeedsMinimum() (gas: 560639)\n[PASS] test_distributeStreamsEverythingToHolders() (gas: 2792056)\n[PASS] test_everyLingRewardPoolPaysTheHolderFee() (gas: 746078)\n[PASS] test_feesWithNoHoldersWaitForTheFirstNft() (gas: 1296187)\n[PASS] test_flashBorrowedNftsEarnNothing() (gas: 14823745)\n[PASS] test_holdersClaim() (gas: 13374507)\n[PASS] test_jitPenaltyOnlyWithinTheWindow() (gas: 2590175)\n[PASS] test_launchPoolCannotBeHijacked() (gas: 421407)\n[PASS] test_onlyTheFirstLaunchPairPays() (gas: 89994)\n[PASS] test_partialFillRevertsWhenFeeWasTakenUpFront() (gas: 199485)\n[PASS] test_permissionsAndLaunchPool() (gas: 79818)\n[PASS] test_poolAndRoutersNeverHoldNfts() (gas: 1710598)\n[PASS] test_rewardsFollowTimeHeld() (gas: 9785391)\n[PASS] test_sellExactIn() (gas: 532948)\n[PASS] test_sellExactOut() (gas: 705517)\n[PASS] test_skippedHandOverGivesALateBuyerNoBackPay() (gas: 2418)\n[PASS] test_unsolicitedUnlockCallbackReverts() (gas: 35256)\n[PASS] test_whaleBuyMintsManyNfts() (gas: 1552643)\nLogs:\n  gas, exact-out buy minting 100 NFTs: 1529056\n\nSuite result: ok. 22 passed; 0 failed; 0 skipped; finished in 189.53ms (217.24ms CPU time)\n\nRan 32 tests for test/Hive.t.sol:ImdFirstHiveTest\n[PASS] testFuzz_feeSplitsAcrossModes(uint256,uint8) (runs: 256, μ: 5200109, ~: 4665535)\n[PASS] test_audit_badQuotersNeverBlockSells() (gas: 3198835)\n[PASS] test_audit_dirtySinkNeverBlocksSwaps() (gas: 2712876)\n[PASS] test_audit_dueSinkDoesNotMakeLowGasSwapsRevert() (gas: 1529302)\n[PASS] test_audit_failingSinkDoesNotStarveTheNext() (gas: 909989)\n[PASS] test_audit_jitTopUpIsPenalizedToo() (gas: 5363244)\n[PASS] test_audit_nestedSwapKeepsTheOuterFee() (gas: 1597209)\n[PASS] test_audit_returnDataBombIsNotPaidByTraders() (gas: 6745519)\n[PASS] test_audit_sinkCannotBeTheHook() (gas: 74210)\n[PASS] test_audit_twapHasNoLag() (gas: 8886919)\n[PASS] test_autoLiquidityBuildsAPermanentPosition() (gas: 6923782)\n[PASS] test_buybackBurnsSupply() (gas: 2402851)\n[PASS] test_buybackLeavesTheRestWhenTheBandIsHit() (gas: 2345160)\n[PASS] test_councilExecutesAtOnce() (gas: 216207)\n[PASS] test_councilLivesAtTheConstant() (gas: 54256)\n[PASS] test_frozenCouncil() (gas: 98632)\n[PASS] test_guardsRevertBuysNeverSells() (gas: 2053919)\n[PASS] test_journal() (gas: 63399)\n[PASS] test_lowGasSkipsObserversInsteadOfReverting() (gas: 436128)\n[PASS] test_maxBuyGuard() (gas: 2681238)\n[PASS] test_moduleValidationAndEmergencyDisable() (gas: 4021705)\n[PASS] test_observersNeverBlock() (gas: 2361353)\n[PASS] test_onlyTheCouncilConfigures() (gas: 88290)\n[PASS] test_ownerCanHandTheCouncilOn() (gas: 105133)\n[PASS] test_quotedExtraGoesToHoldersAndIsCapped() (gas: 1563200)\n[PASS] test_servicesOnlyForSinks() (gas: 756460)\n[PASS] test_sliceValidation() (gas: 515839)\n[PASS] test_snipeTaxDecaysOverTheFirstMinute() (gas: 18462551)\n[PASS] test_snipeTaxNeverHitsSells() (gas: 586751)\n[PASS] test_snipeTaxSitsOutsideTheCouncilCap() (gas: 7523534)\n[PASS] test_treasurySinkForwardsToTheRecipient() (gas: 1459829)\n[PASS] test_twapAndVolatilityFee() (gas: 13178895)\nSuite result: ok. 32 passed; 0 failed; 0 skipped; finished in 189.56ms (184.26ms CPU time)\n\nRan 32 tests for test/Hive.t.sol:NativeHiveTest\n[PASS] testFuzz_feeSplitsAcrossModes(uint256,uint8) (runs: 256, μ: 6175647, ~: 6969218)\n[PASS] test_audit_badQuotersNeverBlockSells() (gas: 1764031)\n[PASS] test_audit_dirtySinkNeverBlocksSwaps() (gas: 1397683)\n[PASS] test_audit_dueSinkDoesNotMakeLowGasSwapsRevert() (gas: 3167787)\n[PASS] test_audit_failingSinkDoesNotStarveTheNext() (gas: 2557069)\n[PASS] test_audit_jitTopUpIsPenalizedToo() (gas: 6928938)\n[PASS] test_audit_nestedSwapKeepsTheOuterFee() (gas: 1377814)\n[PASS] test_audit_returnDataBombIsNotPaidByTraders() (gas: 6701497)\n[PASS] test_audit_sinkCannotBeTheHook() (gas: 74210)\n[PASS] test_audit_twapHasNoLag() (gas: 8793337)\n[PASS] test_autoLiquidityBuildsAPermanentPosition() (gas: 5780682)\n[PASS] test_buybackBurnsSupply() (gas: 1094944)\n[PASS] test_buybackLeavesTheRestWhenTheBandIsHit() (gas: 18729333)\n[PASS] test_councilExecutesAtOnce() (gas: 216183)\n[PASS] test_councilLivesAtTheConstant() (gas: 54256)\n[PASS] test_frozenCouncil() (gas: 98620)\n[PASS] test_guardsRevertBuysNeverSells() (gas: 1953347)\n[PASS] test_journal() (gas: 63399)\n[PASS] test_lowGasSkipsObserversInsteadOfReverting() (gas: 435876)\n[PASS] test_maxBuyGuard() (gas: 2572494)\n[PASS] test_moduleValidationAndEmergencyDisable() (gas: 1574520)\n[PASS] test_observersNeverBlock() (gas: 1062488)\n[PASS] test_onlyTheCouncilConfigures() (gas: 88266)\n[PASS] test_ownerCanHandTheCouncilOn() (gas: 105133)\n[PASS] test_quotedExtraGoesToHoldersAndIsCapped() (gas: 5865778)\n[PASS] test_servicesOnlyForSinks() (gas: 2453702)\n[PASS] test_sliceValidation() (gas: 515803)\n[PASS] test_snipeTaxDecaysOverTheFirstMinute() (gas: 5123809)\n[PASS] test_snipeTaxNeverHitsSells() (gas: 523678)\n[PASS] test_snipeTaxSitsOutsideTheCouncilCap() (gas: 1775238)\n[PASS] test_treasurySinkForwardsToTheRecipient() (gas: 4567099)\n[PASS] test_twapAndVolatilityFee() (gas: 11287657)\nSuite result: ok. 32 passed; 0 failed; 0 skipped; finished in 194.23ms (235.84ms CPU time)\n\nRan 32 tests for test/Hive.t.sol:LingFirstHiveTest\n[PASS] testFuzz_feeSplitsAcrossModes(uint256,uint8) (runs: 256, μ: 5324066, ~: 4666350)\n[PASS] test_audit_badQuotersNeverBlockSells() (gas: 3199151)\n[PASS] test_audit_dirtySinkNeverBlocksSwaps() (gas: 2712884)\n[PASS] test_audit_dueSinkDoesNotMakeLowGasSwapsRevert() (gas: 1530016)\n[PASS] test_audit_failingSinkDoesNotStarveTheNext() (gas: 909626)\n[PASS] test_audit_jitTopUpIsPenalizedToo() (gas: 5362959)\n[PASS] test_audit_nestedSwapKeepsTheOuterFee() (gas: 1577559)\n[PASS] test_audit_returnDataBombIsNotPaidByTraders() (gas: 6745825)\n[PASS] test_audit_sinkCannotBeTheHook() (gas: 74210)\n[PASS] test_audit_twapHasNoLag() (gas: 8885518)\n[PASS] test_autoLiquidityBuildsAPermanentPosition() (gas: 6922225)\n[PASS] test_buybackBurnsSupply() (gas: 2401739)\n[PASS] test_buybackLeavesTheRestWhenTheBandIsHit() (gas: 2349472)\n[PASS] test_councilExecutesAtOnce() (gas: 216207)\n[PASS] test_councilLivesAtTheConstant() (gas: 54256)\n[PASS] test_frozenCouncil() (gas: 98632)\n[PASS] test_guardsRevertBuysNeverSells() (gas: 2053558)\n[PASS] test_journal() (gas: 63399)\n[PASS] test_lowGasSkipsObserversInsteadOfReverting() (gas: 436127)\n[PASS] test_maxBuyGuard() (gas: 2684872)\n[PASS] test_moduleValidationAndEmergencyDisable() (gas: 4021113)\n[PASS] test_observersNeverBlock() (gas: 2361057)\n[PASS] test_onlyTheCouncilConfigures() (gas: 88290)\n[PASS] test_ownerCanHandTheCouncilOn() (gas: 105133)\n[PASS] test_quotedExtraGoesToHoldersAndIsCapped() (gas: 1562241)\n[PASS] test_servicesOnlyForSinks() (gas: 756095)\n[PASS] test_sliceValidation() (gas: 515839)\n[PASS] test_snipeTaxDecaysOverTheFirstMinute() (gas: 18462411)\n[PASS] test_snipeTaxNeverHitsSells() (gas: 587057)\n[PASS] test_snipeTaxSitsOutsideTheCouncilCap() (gas: 7523236)\n[PASS] test_treasurySinkForwardsToTheRecipient() (gas: 1459983)\n[PASS] test_twapAndVolatilityFee() (gas: 13174320)\nSuite result: ok. 32 passed; 0 failed; 0 skipped; finished in 194.25ms (201.28ms CPU time)\n\nRan 30 tests for test/Swarmlings.t.sol:SwarmlingsTest\n[PASS] testFuzz_rewardsNeverExceedWhatArrived(uint256,uint256,uint256,uint256,uint256,uint256) (runs: 256, μ: 1530316, ~: 1530183)\n[PASS] test_claimCannotBeReentered() (gas: 769562)\n[PASS] test_claimCountsUnsyncedCreatorFees() (gas: 467127)\n[PASS] test_claimOneAssetAtATime() (gas: 636496)\n[PASS] test_constructor() (gas: 93547)\n[PASS] test_contractsSkipUnlessTheyOptIn() (gas: 699766)\n[PASS] test_creatorFeeSplitsHalfToDev() (gas: 568874)\n[PASS] test_delegatedWalletsGetNftsLikeAnyWallet() (gas: 523636)\n[PASS] test_eachDayPaysWhatArrivedTheDayBefore() (gas: 655516)\n[PASS] test_holdingForAMomentEarnsAMomentsShare() (gas: 831416)\n[PASS] test_hugeBuySwitchesToSkipInsteadOfRunningOutOfGas() (gas: 19567493)\n[PASS] test_keepPutsFavouritesFirst() (gas: 580049)\n[PASS] test_keepRejectsOthersAndDuplicates() (gas: 486754)\n[PASS] test_nextMintIdsFollowTheCycle() (gas: 10790448)\n[PASS] test_nftSaleKeepsEarningsWithSeller() (gas: 934003)\n[PASS] test_quietDaysKeepTheQueueIntact() (gas: 546037)\n[PASS] test_rewardWithNoNftsWaitsForTheFirstOne() (gas: 483319)\n[PASS] test_rewardsStreamOverADay() (gas: 1128490)\n[PASS] test_royaltyInfo() (gas: 43821)\n[PASS] test_selfTransferProtectsAFavourite() (gas: 556892)\n[PASS] test_sellingBelowAUnitBurnsTheNewestAndKeepsEarnings() (gas: 646425)\n[PASS] test_swapFeesNeverGoToDev() (gas: 367260)\n[PASS] test_swarmShareMintsNoNftUntilTopUp() (gas: 340597)\n[PASS] test_tokenURIComesFromRenderer() (gas: 458545)\n[PASS] test_tokenURIPlaceholderWithoutRenderer() (gas: 252145)\n[PASS] test_tokenURISurvivesARevertingRenderer() (gas: 389629)\n[PASS] test_transfersMoveExactAmounts(uint256) (runs: 256, μ: 742701, ~: 171279)\n[PASS] test_unitBoundaries() (gas: 628273)\n[PASS] test_validatorGatesOperatorTransfersOnly() (gas: 1087792)\n[PASS] test_validatorIsFixed() (gas: 8547)\nSuite result: ok. 30 passed; 0 failed; 0 skipped; finished in 194.24ms (208.12ms CPU time)\n\nRan 33 tests for test/Swarmlings.t.sol:SwarmlingsMainnetTest\n[PASS] testFuzz_rewardsNeverExceedWhatArrived(uint256,uint256,uint256,uint256,uint256,uint256) (runs: 256, μ: 1607544, ~: 1598203)\n[PASS] test_claimCannotBeReentered() (gas: 832708)\n[PASS] test_claimCannotReenterSyncToken() (gas: 1536249)\n[PASS] test_claimCountsUnsyncedCreatorFees() (gas: 525771)\n[PASS] test_claimOneAssetAtATime() (gas: 720542)\n[PASS] test_constructor() (gas: 98955)\n[PASS] test_contractsSkipUnlessTheyOptIn() (gas: 750233)\n[PASS] test_creatorFeeSplitsHalfToDev() (gas: 610194)\n[PASS] test_delegatedWalletsGetNftsLikeAnyWallet() (gas: 588508)\n[PASS] test_eachDayPaysWhatArrivedTheDayBefore() (gas: 691552)\n[PASS] test_holdingForAMomentEarnsAMomentsShare() (gas: 904188)\n[PASS] test_hugeBuySwitchesToSkipInsteadOfRunningOutOfGas() (gas: 19661275)\n[PASS] test_keepPutsFavouritesFirst() (gas: 630495)\n[PASS] test_keepRejectsOthersAndDuplicates() (gas: 537199)\n[PASS] test_mainnetEarnsBothCurrencies() (gas: 1142012)\n[PASS] test_nextMintIdsFollowTheCycle() (gas: 10855297)\n[PASS] test_nftSaleKeepsEarningsWithSeller() (gas: 985588)\n[PASS] test_quietDaysKeepTheQueueIntact() (gas: 582185)\n[PASS] test_rewardWithNoNftsWaitsForTheFirstOne() (gas: 519445)\n[PASS] test_rewardsStreamOverADay() (gas: 1201868)\n[PASS] test_royaltyInfo() (gas: 43821)\n[PASS] test_selfTransferProtectsAFavourite() (gas: 636145)\n[PASS] test_sellingBelowAUnitBurnsTheNewestAndKeepsEarnings() (gas: 699692)\n[PASS] test_swapFeesNeverGoToDev() (gas: 405973)\n[PASS] test_swarmShareMintsNoNftUntilTopUp() (gas: 391064)\n[PASS] test_tokenURIComesFromRenderer() (gas: 494629)\n[PASS] test_tokenURIPlaceholderWithoutRenderer() (gas: 288251)\n[PASS] test_tokenURISurvivesARevertingRenderer() (gas: 425735)\n[PASS] test_transfersMoveExactAmounts(uint256) (runs: 256, μ: 778801, ~: 207319)\n[PASS] test_unitBoundaries() (gas: 707550)\n[PASS] test_unsolicitedImdGoesToHoldersToo() (gas: 547211)\n[PASS] test_validatorGatesOperatorTransfersOnly() (gas: 1167114)\n[PASS] test_validatorIsFixed() (gas: 8525)\nSuite result: ok. 33 passed; 0 failed; 0 skipped; finished in 194.34ms (254.18ms CPU time)\n\nRan 2 tests for test/Invariant.t.sol:InvariantTest\n[PASS]\nInvariantTest invariants:\n[PASS] invariant_claimsAreCounted\n[PASS] invariant_hookLedger\n[PASS] invariant_nftsMatchBalances\n[PASS] invariant_rewardsAreSolvent\n InvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------+------------+-------+---------+----------╮\n| Contract | Selector   | Calls | Reverts | Discards |\n+====================================================+\n| Handler  | buy        | 768   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | claim      | 849   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | creatorFee | 805   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | devClaim   | 818   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | distribute | 843   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | donate     | 806   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | sell       | 848   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | sendLing   | 836   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | sendNft    | 799   | 0       | 0        |\n|----------+------------+-------+---------+----------|\n| Handler  | wait       | 820   | 0       | 0        |\n╰----------+------------+-------+---------+----------╯\n\n[PASS] test_handlerTradesForReal() (gas: 34290210)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.44s (2.46s CPU time)\n\nRan 17 test suites in 2.44s (3.96s CPU time): 244 tests passed, 0 failed, 0 skipped (244 total tests)\n","passed":true},{"durationMs":81,"exitCode":0,"name":"source-index","output":"{\"v\":1,\"entryPoints\":[\"AutoLiquidity.collect()\",\"AutoLiquidity.poke()\",\"BuybackBurn.poke()\",\"Swarmlings.addRewards()\",\"Swarmlings.approve(address,uint256)\",\"Swarmlings.burn(uint256)\",\"Swarmlings.claim()\",\"Swarmlings.claimDev()\",\"Swarmlings.claimEth()\",\"Swarmlings.claimToken()\",\"Swarmlings.fallback()\",\"Swarmlings.keep(uint256[])\",\"Swarmlings.receive()\",\"Swarmlings.setSkipNFT(bool)\",\"Swarmlings.syncEth()\",\"Swarmlings.syncToken()\",\"Swarmlings.transfer(address,uint256)\",\"Swarmlings.transferFrom(address,address,uint256)\",\"SwarmlingsCouncil.execute(address,bytes,string)\",\"SwarmlingsCouncil.post(string)\",\"SwarmlingsCouncil.setOwner(address)\",\"SwarmlingsHook.addLiquidity(int24,int24,uint128)\",\"SwarmlingsHook.afterAddLiquidity(address,(address,address,uint24,int24,address),(int24,int24,int256,bytes32),int256,int256,bytes)\",\"SwarmlingsHook.afterDonate(address,(address,address,uint24,int24,address),uint256,uint256,bytes)\",\"SwarmlingsHook.afterInitialize(address,(address,address,uint24,int24,address),uint160,int24)\",\"SwarmlingsHook.afterRemoveLiquidity(address,(address,address,uint24,int24,address),(int24,int24,int256,bytes32),int256,int256,bytes)\",\"SwarmlingsHook.afterSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),int256,bytes)\",\"SwarmlingsHook.beforeAddLiquidity(address,(address,address,uint24,int24,address),(int24,int24,int256,bytes32),bytes)\",\"SwarmlingsHook.beforeDonate(address,(address,address,uint24,int24,address),uint256,uint256,bytes)\",\"SwarmlingsHook.beforeRemoveLiquidity(address,(address,address,uint24,int24,address),(int24,int24,int256,bytes32),bytes)\",\"SwarmlingsHook.beforeSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),bytes)\",\"SwarmlingsHook.buy(uint256,uint160)\",\"SwarmlingsHook.collectFees(int24,int24)\",\"SwarmlingsHook.disableModule(address)\",\"SwarmlingsHook.distribute()\",\"SwarmlingsHook.receive()\",\"SwarmlingsHook.setCouncil(address)\",\"SwarmlingsHook.setModules((address,uint16,bool)[])\",\"SwarmlingsHook.setSlices((address,uint16,bool)[])\",\"SwarmlingsHook.take(address,address,uint256)\",\"SwarmlingsHook.unlockCallback(bytes)\",\"SwarmlingsMirror.approve(address,uint256)\",\"SwarmlingsMirror.fallback()\",\"SwarmlingsMirror.pullOwner()\",\"SwarmlingsMirror.receive()\",\"SwarmlingsMirror.safeTransferFrom(address,address,uint256)\",\"SwarmlingsMirror.safeTransferFrom(address,address,uint256,bytes)\",\"SwarmlingsMirror.setApprovalForAll(address,bool)\",\"SwarmlingsMirror.transferFrom(address,address,uint256)\",\"TreasurySink.poke()\",\"TwapOracle.onBeforeSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),bytes)\",\"TwapOracle.record()\"],\"files\":{\".gitignore\":8,\"LICENSE\":21,\"README.md\":156,\"docs/DEPENDENCIES.md\":26,\"docs/HIVE.md\":133,\"docs/OPERATIONS.md\":99,\"docs/SECURITY.md\":126,\"docs/abi/AutoLiquidity.json\":276,\"docs/abi/BuybackBurn.json\":224,\"docs/abi/MaxBuy.json\":204,\"docs/abi/Swarmlings.json\":964,\"docs/abi/SwarmlingsCouncil.json\":137,\"docs/abi/SwarmlingsHook.json\":2085,\"docs/abi/SwarmlingsMirror.json\":607,\"docs/abi/SwarmlingsRenderer.json\":152,\"docs/abi/TreasurySink.json\":223,\"docs/abi/TwapOracle.json\":259,\"docs/abi/VolatilityFee.json\":228,\"docs/audit/2026-10-10/AUDIT-REPORT.md\":57,\"docs/audit/2026-10-10/CROPS.md\":152,\"docs/audit/2026-10-10/findings-access-control.md\":201,\"docs/audit/2026-10-10/findings-defi-amm.md\":91,\"docs/audit/2026-10-10/findings-dos.md\":93,\"docs/audit/2026-10-10/findings-erc20.md\":63,\"docs/audit/2026-10-10/findings-erc721.md\":143,\"docs/audit/2026-10-10/findings-flashloans.md\":112,\"docs/audit/2026-10-10/findings-general.md\":204,\"docs/audit/2026-10-10/findings-precision-math.md\":111,\"docs/audit/2026-10-10/poc/AccessControlAudit.t.sol\":283,\"docs/audit/2026-10-10/poc/AmmAudit.t.sol\":470,\"docs/audit/2026-10-10/poc/Dos.t.sol\":638,\"docs/audit/2026-10-10/poc/ERC20Audit.t.sol\":640,\"docs/audit/2026-10-10/poc/Erc721Audit.t.sol\":490,\"docs/audit/2026-10-10/poc/Erc721AuditFork.t.sol\":186,\"docs/audit/2026-10-10/poc/FlashAtomic.t.sol\":297,\"docs/audit/2026-10-10/poc/FlashJit.t.sol\":88,\"docs/audit/2026-10-10/poc/FlashOracle.t.sol\":120,\"docs/audit/2026-10-10/poc/FlashSinks.t.sol\":256,\"docs/audit/2026-10-10/poc/FlashSkip.t.sol\":32,\"docs/audit/2026-10-10/poc/GeneralAudit.t.sol\":176,\"docs/audit/2026-10-10/poc/PrecisionMath.t.sol\":204,\"docs/audit/2026-10-10/poc/RendererCode.sol\":4,\"docs/audit/2026-10-10/poc/RendererGas.t.sol\":30,\"foundry.toml\":23,\"launch.json\":39,\"remappings.txt\":4,\"renderer/README.md\":17,\"renderer/foundry.toml\":16,\"renderer/lib/solady/LICENSE.txt\":21,\"renderer/lib/solady/src/utils/Base64.sol\":171,\"renderer/lib/solady/src/utils/DynamicBufferLib.sol\":1318,\"renderer/lib/solady/src/utils/LibBytes.sol\":882,\"renderer/lib/solady/src/utils/LibString.sol\":979,\"renderer/script/Deploy.s.sol\":32,\"renderer/src/SwarmlingsData.sol\":35,\"renderer/src/SwarmlingsRenderer.sol\":566,\"renderer/test/Renderer.t.sol\":86,\"renderer/test/data/expected-riso2.bin\":467,\"renderer/test/data/logo.svg\":1,\"renderer/test/data/riso2-1.svg\":1,\"renderer/test/data/riso2-1697.svg\":1,\"renderer/test/data/riso2-32.svg\":1,\"script/Day1Modules.s.sol\":72,\"script/DeployCouncil.s.sol\":30,\"src/Swarmlings.sol\":482,\"src/SwarmlingsCouncil.sol\":54,\"src/SwarmlingsHook.sol\":946,\"src/SwarmlingsMirror.sol\":147,\"src/interfaces/IHive.sol\":151,\"src/modules/AutoLiquidity.sol\":71,\"src/modules/BuybackBurn.sol\":47,\"src/modules/HiveSink.sol\":64,\"src/modules/MaxBuy.sol\":54,\"src/modules/TreasurySink.sol\":34,\"src/modules/TwapOracle.sol\":122,\"src/modules/VolatilityFee.sol\":72,\"test/GasCap.t.sol\":38,\"test/Hive.t.sol\":847,\"test/HookSalt.t.sol\":34,\"test/Invariant.t.sol\":248,\"test/Launcher.t.sol\":81,\"test/Manifest.t.sol\":33,\"test/Swarmlings.t.sol\":626,\"test/SwarmlingsHook.t.sol\":463,\"test/fork/Validator.t.sol\":78,\"test/utils/SwarmlingsBase.sol\":204},\"excluded\":[\"lib/\",\"node_modules/\"],\"truncated\":false}","passed":true}],"detail":"all checks passed; 1 finding(s) for the step that wrote the contracts","evaluation":"checks","profile":"foundry","status":"accepted","submissionHash":"9f8bbfaffaabf57677d02686742990d75a4312955a13a0b1d401d365a07a4531","verifiedTreeHash":"25223f730c98d2d973be59a7ccc2f3bfa0a0cd60","verifierVersion":"0.1.0+745c1db4"}]}