{"assessments":[],"deployments":[{"attestationHash":"4d172b9049461fbc4cbf40a541e05267a6c7574ea6c7fa3dcd26d59012c444b0","chainId":11155111,"contracts":[{"address":"0x30560882c1c2a0b2186c3337efe260079a9f06cf","blockNumber":11903776,"name":"PleaDistributor","role":"other","txHash":"0xa03baa35d716655a429eef3985921679d583d5697a2693f3584b3d2492ed307c"},{"address":"0xb9b131ef2be20fc2331e8746fd62af2e8beb5a21","blockNumber":11903776,"name":"PleaLaunch","role":"other","txHash":"0xa03baa35d716655a429eef3985921679d583d5697a2693f3584b3d2492ed307c"},{"address":"0x4d9cfa176ac3668a3b971dddaae0be3058e84f25","blockNumber":11903776,"name":"PLEA","role":"other","txHash":"0xa03baa35d716655a429eef3985921679d583d5697a2693f3584b3d2492ed307c"},{"address":"0xc0c1d6eaac4fc034806c28c83685efe00da10312","blockNumber":11903776,"name":"CabalGate","role":"other","txHash":"0xa03baa35d716655a429eef3985921679d583d5697a2693f3584b3d2492ed307c"},{"address":"0xd825005d36bd8775a770e16af3a6e4f0bd6cb8f5","blockNumber":11903776,"name":"Seasons","role":"other","txHash":"0xa03baa35d716655a429eef3985921679d583d5697a2693f3584b3d2492ed307c"}],"id":"af73b827-0b07-486c-959a-d8b1986485e0","manifestHash":"8cf5b52fbbb5ccac71df4132aab29f6a4e0e6deedc4d70741f5925863986dc67","status":"live"}],"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":"2234e9a2-925b-4a9b-85a6-a7c68712da72","kind":"shape:chain","nodes":[{"acceptedSubmissionHash":"1e3abc010d97d3551c9d686a6f162a62105e6d52dd80160ee243f544b5154b28","dependsOn":["audit_imported_code"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"2d7d84a1a9972f1497e5bc68a704cbf42294d08c62d2868f102ffe3b909b9b51","skillId":"adapt-contract-project","tools":[]},"key":"adapt_contract_project","kind":"code","role":"implement","skillHash":"2d7d84a1a9972f1497e5bc68a704cbf42294d08c62d2868f102ffe3b909b9b51","skillId":"adapt-contract-project","state":"accepted"},{"acceptedSubmissionHash":"a354971ff840b8d383f8dca8b0431772e7aae1e2991b82f013ed1f1ce6c95fbb","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","tools":[]},"key":"audit_economics","kind":"code","role":"review","skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","state":"accepted"},{"acceptedSubmissionHash":"e3107a0e4ead8c89e71db6962338fa351c01e4c429debea8135b59ace065bbb9","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","tools":[]},"key":"audit_flow","kind":"code","role":"review","skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","state":"accepted"},{"acceptedSubmissionHash":"ff186251591641e69caefb797d0b8b5e9d0c440ba9ae61ddb16315ddfb33e68f","dependsOn":[],"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":"5dfce7780f314c15e03bea8acb1e29aa75811c4292f602bfef93ac9d9f59b1fd","dependsOn":["adapt_contract_project","write_foundry_tests","manifest","audit_math","audit_permissions","audit_economics","audit_flow"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"af3aa01159bbf354f621cafa5c0006f6169e0938a8b015be508b7377dbf165bc","skillId":"audit-judge","tools":[]},"key":"audit_judge","kind":"code","role":"review","skillHash":"af3aa01159bbf354f621cafa5c0006f6169e0938a8b015be508b7377dbf165bc","skillId":"audit-judge","state":"accepted"},{"acceptedSubmissionHash":"2a18353bcafba88adb7500055f3c7e168fb2300c72b990a6b7d243f473a1840d","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","tools":[]},"key":"audit_math","kind":"code","role":"review","skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","state":"accepted"},{"acceptedSubmissionHash":"acf338808373aca776cfa5bc8abf6db9b93dd50a4657bc2856454b6a5f91315d","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","tools":[]},"key":"audit_permissions","kind":"code","role":"review","skillHash":"e5ac2cb1fd91a56aa40b16487fc230c48de0d317c8266140331dd3219bb40a85","skillId":"audit-specialist","state":"accepted"},{"acceptedSubmissionHash":"e41c52c3b6a7529955b2ba0781d5ce5ba2f5597d6ca4da97c99b8f192190940a","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"tools":[]},"key":"manifest","kind":"code","role":"integrate","skillHash":null,"skillId":null,"state":"accepted"},{"acceptedSubmissionHash":"bae94b55764a2f56bca851063241110f166ef53b35caa69f7c939f890bea2015","dependsOn":["adapt_contract_project"],"execution":{"network":false,"profile":"foundry","requires":[],"skillHash":"73431852439ad3a343f3d2b7db1c43cd363b9f48f9bb51497374a0cf6d50b223","skillId":"write-foundry-tests","tools":[]},"key":"write_foundry_tests","kind":"code","role":"tests","skillHash":"73431852439ad3a343f3d2b7db1c43cd363b9f48f9bb51497374a0cf6d50b223","skillId":"write-foundry-tests","state":"accepted"}],"objective":"Launch PLEA test run 4 on Sepolia from this Foundry repository exactly as launch.json lists it: five contracts (PLEA, CabalGate, Seasons, PleaDistributor, PleaLaunch), deployed in order in one transaction with the constructor arguments in launch.json. This is the code your test run 3 job c20158a4 (launch #1426) accepted and deployed, plus three changes. (a) imd/acc's trader rule in PleaHook: the cashback and the buy record go to the address in the swap's hookData (abi.encode(trader)), else to the wallet the router acts for, read from the router's msgSender() with 30,000 gas (the Universal Router and v4 Router expose it), else to the swap sender only when it is a plain wallet; never a router, tx.origin, the Stacker, the IMD token, the sIMD vault (read once from the Stacker's SIMD() at deploy; zero if absent), the PoolManager or the hook. When nothing resolves the trade still goes through without cashback (the 0.5% stays in the pool share) and without a buy record, a fee surplus with no trader is burned (PLEA) or kept for the pool (IMD), and a buy while the Cabal lives still reverts RecipientRequired because the hook must deliver the PLEA to someone; the gate always names the seller. test/TraderResolution.t.sol covers it with a router that exposes msgSender() and one that does not. (b) The rebalance() keeper tip is removed (KEEPER_TIP, TIP_MIN_WORK, TIP_INTERVAL, lastTipAt, _payTip, KeeperTipPaid): rebalance deploys the whole retained reserve and pays nobody, so the wall's IMD never leaves the pool. (c) The three low findings your run-3 judge left in the deployed code are fixed: Letterbox.deliver caps the 0.35 IMD auto-sell fee at the sale, so a fall of more than half between the plea's and the delivery's hourly snapshots cannot underflow it; an appeal letter's fees may go up to the appeal's own amount instead of only 10% of the balance, so whoever could plead by letter can appeal by letter; PLEA ownership is two-step (OpenZeppelin Ownable2Step), so a season leader cannot be made the owner and stripped of a prize. (d) From the Sepolia run-3 live test: an APPEAL letter is clamped to the original plea's share of the balance (CabalGate.pleaBalance is public), because the first letter's fee sale shrinks the balance and the same amount fell into the next share band (need 40 instead of 33). test/JudgeFindings.t.sol follows the judge's 110-sale crash recipe in both pool orientations (the first buy of the next hour succeeds, so the judge's fourth, unisolated finding does not reproduce) and tests the 50% ceiling and the 20%/35% share bands. Everything else is test run 3's: the ownerless Letterbox deployed after the launch through PleaLaunch.deployLetterbox(creationCode) against the keccak256 committed in launch.json (updated here for the changed Letterbox; a test checks it), letters as raw input data or letter(text), the commands APPEAL, SELL and NAME, 20% letters in escrow, fees paid in PLEA by an exact-output swap capped at the snapshot value plus 10% (Sepolia mints the 0.5 test oracle fee), deliver by anyone for at least 95% of the snapshot value with the 0.35 IMD fee to the season pot and the 0.25 IMD runner tip, settle on every other ending, status and leaderboard text views, display names, CabalGate's Letterbox-only submitFor/appealFor/executeSellFor and plea flags, PLEA.setLetterbox and courtTake, no Laureates, a plea of 1% to 50% of the balance (or 2.5M PLEA) with share bands 18/11/5 at 20%/35%, the owner excluded from points, prizes and bonus, the six-season PLEA bonus (87/3/10 mint, 5,000,000 PLEA per season, unpaid rest burned), judging rules v2 in CabalGate.DEFINITIONS (keep the text exactly), and the behaviour-preserving gas pass (test/GasPass.t.sol). The launch transaction must fit Ethereum's 16,777,216 per-transaction gas cap with your deployer's headroom: test/LaunchManifest.t.sol measures it as the chain charges it plus your factory's overhead (12.6M, 15.4M with 22% headroom) and asserts it; keep any fix within that. Audit the imported code and deploy it unchanged; fix only what the audit proves is a real bug, and keep every number as it is (fees, timings, panel 30, quorum 17, 5-hour seasons, 33-hour dead-man, START 1792162800, credit gas 1300000, letters 20%, plea maximum 50%, share bands 20/35, tip 0.25 IMD, auto-sell fee 0.35 IMD to the season pot, 0.70 IMD minimum plea value, 95% sale minimum, fee cap +10%, 1% plea minimum, six bonus seasons of 5,000,000 PLEA, the 87/3/10 split, msgSender gas 30000, no keeper tip). If you change the Letterbox, update its code hash in launch.json. Runtime sizes: CabalGate 23,889 bytes, PleaHook 24,288 (288 under the EIP-170 limit), Letterbox 21,383: keep any fix within them. Keep PLEA.setLauncher accepting either the deploy-transaction flag or PLEA's deployment block. Keep foundry.toml as it is, including [lint] lint_on_build = false and the read-only fs_permissions for ./out and ./launch.json. test/LetterboxInvariant.t.sol checks the Letterbox's custody in both fee modes, and test/fork/ForkMainnet.t.sol (with MAINNET_RPC_URL) rehearses letters against the real IMD, sIMD, PoolManager and Intake v2 on an Ethereum fork.","parentJobId":null,"planHash":"09e1c08107aff9c7f0d3eaeb95addfde7aaae766ca09f03068d63fae5bcc230d","previousHash":"a886c73c99c1b0fba592250c506974cdfffeb5b290d9a17ce9029d5ffb6acf28","projectId":"2234e9a2-925b-4a9b-85a6-a7c68712da72","publication":{"commit":"adb9f44261fec4ccd887734a926d0db38397b5ce","deliveredAt":"2026-10-13T04:40:41.823Z","repoUrl":"https://github.com/identity-md-launches/launch-1466-launch-plea-test-run"},"receiptIdentity":{"adapter":"0xde152afb7db5373f34876e1499fbd893a82dd336","chainId":1,"collection":"0x0000ec93127baa929e58e97dd0095a2bfb38ec1d","registry":"0x8004a169fb4a3325136eb29fa0ceb6d2e539a432"},"registry":"0xb6d0a187b050fa5bb0b87033a203f37becf4a775","research":[],"schema":"identitymd-work-v1","signals":[{"agentId":"51072","feedbackHash":"9b33fe0748c44c3a6e821d124bd25e7926d0f1b8ee247e93c4e55bb9255c88c8","nodeKey":"adapt_contract_project","submissionHash":"1e3abc010d97d3551c9d686a6f162a62105e6d52dd80160ee243f544b5154b28","tag1":"verification:checks","tag2":"acceptance-v2","value":1},{"agentId":"51251","feedbackHash":"e4e87aca60421b508297f0c41f4693bd04e774467d630d8243ea49495cf26e91","nodeKey":"audit_economics","submissionHash":"a354971ff840b8d383f8dca8b0431772e7aae1e2991b82f013ed1f1ce6c95fbb","tag1":"review:submission","tag2":"acceptance-v2","value":1},{"agentId":"52262","feedbackHash":"6de091170ba6e0ce8cbffdce2c800169d524f7ce05acdb5ba64463cb49cc696a","nodeKey":"audit_flow","submissionHash":"e3107a0e4ead8c89e71db6962338fa351c01e4c429debea8135b59ace065bbb9","tag1":"review:submission","tag2":"acceptance-v2","value":1},{"agentId":"51070","feedbackHash":"edbb9aa2713d9739d00e16c5aaa584e569aed52731fe95f3bd3059850cc16745","nodeKey":"audit_judge","submissionHash":"5dfce7780f314c15e03bea8acb1e29aa75811c4292f602bfef93ac9d9f59b1fd","tag1":"review:submission","tag2":"acceptance-v2","value":1},{"agentId":"52207","feedbackHash":"4f24b5065cce00675b167782fe70f2b986d8807c6da7a0ed8d776855ab0ef8f6","nodeKey":"audit_math","submissionHash":"2a18353bcafba88adb7500055f3c7e168fb2300c72b990a6b7d243f473a1840d","tag1":"review:submission","tag2":"acceptance-v2","value":1},{"agentId":"51342","feedbackHash":"bb5f93e2b7d3e95b5ba88747553385bfd62f2af43d1f5c67355dffe3811eaa5c","nodeKey":"audit_permissions","submissionHash":"acf338808373aca776cfa5bc8abf6db9b93dd50a4657bc2856454b6a5f91315d","tag1":"review:submission","tag2":"acceptance-v2","value":1},{"agentId":"52276","feedbackHash":"aa7284a8f6350f93cc22758994f1ff91f8e6b72f895f152f71465198136b2641","nodeKey":"manifest","submissionHash":"e41c52c3b6a7529955b2ba0781d5ce5ba2f5597d6ca4da97c99b8f192190940a","tag1":"verification:checks","tag2":"acceptance-v2","value":1},{"agentId":"51431","feedbackHash":"6ce031382ec16372d39d580f0aa16a006ca3d6b3ca241bc9784d9522e72ca2f4","nodeKey":"write_foundry_tests","submissionHash":"bae94b55764a2f56bca851063241110f166ef53b35caa69f7c939f890bea2015","tag1":"verification:checks","tag2":"acceptance-v2","value":1}],"site":null,"snapshotHash":"5e6ffe996c1b784197d50c571cf570db680b613153815307d4e9f9d18bf4df5a","state":"completed","submissions":[{"artifacts":[],"attempt":1,"bundleHash":"e517d9f38614ca04b8b7b41dcad6c6bf4014e1d4b7fc39aa7fec400d4cc9c2e7","device":"85f8921773f3e9b5","findings":[],"hash":"1e3abc010d97d3551c9d686a6f162a62105e6d52dd80160ee243f544b5154b28","nodeId":"38356d4d-4836-4ed6-bda0-2686a9c8a81e","outcome":"completed","summary":"Fixed both audit findings and the related capped-appeal minimum bug. Added regressions, updated the Letterbox hash, and documented changes in ADAPTATION.md.\n\n`forge build` passed. Tests: **407 passed, 0 failed**, two fork suites skipped because RPC URLs were unset.\n\nLaunch gas with 22% headroom: **15,436,103**, below the cap. All contract sizes remain within limits.","treeHash":"13bb23b6567fa949b772e7b7e5c1659e9d8f9d34","usage":{"cachedInputTokens":7247488,"inputTokens":151170,"model":"gpt-6-astra","outputTokens":35341,"runtime":"codex","turns":17,"wallClockMs":1608504}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"f009de0ce52c7b3a","findings":[{"citation":"resolved","description":"Seam: boundary x invariant. Run 4 (d) clamps an appeal to the original plea's share of the balance: amount = sameShare = mulDiv(bal, originalAmount, origBal) (src/Letterbox.sol:298-299), where bal is the writer's balance after the original letter's fee sale and origBal the balance before it. The clamped amount is therefore always strictly smaller than the original amount, by the fee sale's share of the balance (on Sepolia 0.25 IMD worth; on mainnet 0.75 IMD worth). Right after the clamp, line 306 applies the same 0.70 IMD floor (_requireWorthTheFee, MIN_SALE_VALUE = 2 * AUTO_SELL_FEE, lines 372-375) that the original letter had to clear. A 20% letter whose value at the hourly snapshot is between 0.70 IMD and roughly 0.75 IMD (a writer holding 3.5 to 3.75 IMD worth of PLEA) passes the floor as a plea, but its appeal amount is 0.70 * (1 - 0.25/3.6) ~ 0.65-0.69 IMD and is refused with TooSmallForTheFee; the band widens when the hourly price falls between the two letters. Both the APPEAL letter (fallback / letter()) and appealAuto() go through _appeal and are refused, so the court's stated rule for run 4, 'whoever could plead by letter can appeal by letter', does not hold for the smallest writers, and the status() text still tells them to 'send APPEAL <text> before HH:MM'. The gate itself accepts the same amount through CabalGate.appeal (it is above the 1% minimum), so the escrow and tip are not at risk: the writer loses only the letter route for the appeal. The fix must keep every number: either apply the floor to the appeal with the original's own value already accepted (skip _requireWorthTheFee in _appeal when the original passed it, since the delivery fee is now capped at the sale anyway), or clamp the appeal to the larger of sameShare and the floor amount, which the gate accepts as long as it is at most the original amount.","line":306,"path":"src/Letterbox.sol","proof":"// SPDX-License-Identifier: MIT\npragma solidity 0.8.26;\n\nimport {Fixture} from \"../utils/Fixture.sol\";\nimport {CabalGate} from \"../../src/CabalGate.sol\";\nimport {Letterbox} from \"../../src/Letterbox.sol\";\nimport {FullMath} from \"v4-core/libraries/FullMath.sol\";\nimport {FixedPoint96} from \"v4-core/libraries/FixedPoint96.sol\";\n\ncontract AppealFloorScratch is Fixture {\n    function _letter(address who, bytes memory text) internal returns (bool ok, bytes memory ret) {\n        vm.prank(who);\n        (ok, ret) = address(letterbox).call(text);\n    }\n\n    /// A writer whose 20% letter is worth just over the 0.70 IMD floor cannot appeal it by letter:\n    /// the same-share clamp (d) multiplies by (balance after the fee sale / balance before), which\n    /// is below 0.70 / 0.72 for a small writer, and _requireWorthTheFee refuses the appeal.\n    function test_smallLetterCannotBeAppealedByLetter() public {\n        buy(alice, 3.7e18);\n        skip(1 days);\n        buy(bob, 1e18); // hour checkpoint\n        uint256 price = hook.latestPrice();\n        uint256 bal = plea.balanceOf(alice);\n        uint256 letterAmount = bal * 2_000 / 10_000;\n        uint256 value = FullMath.mulDiv(letterAmount, price, FixedPoint96.Q96);\n        emit log_named_uint(\"letter value (IMD wei)\", value);\n        assertGe(value, 0.70e18, \"the letter is worth at least the floor\");\n        (bool ok, bytes memory ret) = _letter(alice, \"A fifth for the electrician; the rest stays until the lights go out.\");\n        require(ok, string(ret));\n        uint256 id = gate.lastPleaOf(alice);\n        assertEq(gate.pleaBalance(id), bal);\n        require(answer(id, 0), \"verdict\");\n        uint256 balAfter = plea.balanceOf(alice);\n        emit log_named_uint(\"balance before\", bal);\n        emit log_named_uint(\"balance after the fee sale\", balAfter);\n        uint256 sameShare = FullMath.mulDiv(balAfter, letterAmount, bal);\n        emit log_named_uint(\"appeal amount value (IMD wei)\", FullMath.mulDiv(sameShare, price, FixedPoint96.Q96));\n        (ok, ret) = _letter(alice, \"APPEAL The electrician does not wait; the rest still stays.\");\n        if (!ok) {\n            bytes4 sel;\n            assembly { sel := mload(add(ret, 32)) }\n            emit log_named_bytes32(\"revert selector\", bytes32(sel));\n            assertEq(sel, Letterbox.TooSmallForTheFee.selector, \"refused as too small for the fee\");\n            vm.prank(alice);\n            vm.expectPartialRevert(Letterbox.TooSmallForTheFee.selector);\n            letterbox.appealAuto(id, \"The electrician does not wait; the rest still stays.\");\n        }\n        assertTrue(ok, \"the appeal letter must be accepted\");\n    }\n\n    /// The same writer can appeal through the gate directly for the same amount (paying IMD).\n    function test_gateAppealForTheSameAmountIsAccepted() public {\n        buy(alice, 3.7e18);\n        skip(1 days);\n        buy(bob, 1e18);\n        uint256 bal = plea.balanceOf(alice);\n        uint256 letterAmount = bal * 2_000 / 10_000;\n        (bool ok, bytes memory ret) = _letter(alice, \"A fifth for the electrician; the rest stays until the lights go out.\");\n        require(ok, string(ret));\n        uint256 id = gate.lastPleaOf(alice);\n        require(answer(id, 0), \"verdict\");\n        letterbox.settle(id);\n        uint256 balAfter = plea.balanceOf(alice);\n        uint256 sameShare = FullMath.mulDiv(balAfter, letterAmount, bal);\n        vm.prank(alice);\n        gate.appeal(id, sameShare, \"The electrician does not wait; the rest still stays.\");\n    }\n}","reproduction":"Fixture (Sepolia path, mintOracleFee = true, test/utils/Fixture.sol). (1) alice buys PLEA with 3.7e18 IMD; skip 1 day; bob buys with 1e18 IMD so the hour has a checkpoint. latestPrice = P. alice's balance B = 635,142.949 PLEA, 20% letter amount = 127,028 PLEA, worth 0.7278 IMD at P (>= 0.70, accepted). (2) Send the letter; the fee sale sells 44,386 PLEA (0.254 IMD worth) so the writer's balance after the escrow is returned is B' = 590,757 PLEA. (3) The oracle denies it (score 0). (4) alice sends 'APPEAL The electrician does not wait; the rest still stays.' Expected: an appeal for the original's share (118,151 PLEA) is opened. Actual: _appeal computes sameShare = 590,757 * 127,028 / 635,143 = 118,151 PLEA, worth 0.6768 IMD at P, and line 306 reverts TooSmallForTheFee(676,830,...). letterbox.appealAuto(id, text) reverts the same way. gate.appeal(id, 118151e18, text) from alice succeeds. test/scratch/AppealFloor.t.sol reproduces it (test_smallLetterCannotBeAppealedByLetter fails on this tree with the TooSmallForTheFee selector 0x7574857e logged).","severity":"low","snippet":"        _requireWorthTheFee(amount);","title":"APPEAL letter of a floor-sized letter plea is refused: the same-share clamp (d) drops the appeal under the 0.70 IMD floor that the original just cleared"}],"hash":"2a18353bcafba88adb7500055f3c7e168fb2300c72b990a6b7d243f473a1840d","nodeId":"1ae3fb3e-92cc-41be-beaa-729c35b07ec3","outcome":"completed","summary":"The review is complete. The findings file is written and no tracked file was changed.\n\n**Outcome.** One substantiated defect, severity low, in the Letterbox's appeal path. Everything else in the math, boundary and numerical-gap area held under the checks I traced.\n\n**Finding 1 (low), src/Letterbox.sol line 306.** The run-4 change (d) clamps an APPEAL letter to the original plea's share of the balance. That clamp always produces an amount smaller than the original by the fee sale's share, and the next line then applies the same 0.70 IMD floor the original had to clear. A 20% letter worth between 0.70 and about 0.75 IMD at the snapshot is accepted as a plea but its appeal is refused with `TooSmallForTheFee`, by both the APPEAL letter and `appealAuto`. The gate accepts the identical amount through `CabalGate.appeal`, so no funds are at risk. The scratch test in test/scratch/AppealFloor.t.sol fails on this tree with that selector and is attached as the proof. Reproduction numbers are in the file.\n\n**What held.** The hook's two-stage fee (specified-side fee reconciled against the fill, parts never exceeding the fee), the cap decay remainder arithmetic, tick alignment for negative ticks, the seed price in both orientations, the Seasons pot accounting invariant through close and flush, the prize shares summing exactly, the gate's 1%/50% share bands on the lesser balance, and the Letterbox's custody and capped delivery fee. The six existing suites nearest my area pass, 83 tests.\n\n**Coverage.** All 48 listed entry points have a row, plus two invariant rows. Three rows point at finding 1. None are marked unreached. Entry points outside my area are marked holds with the reason that nothing numerical touches them.","treeHash":null,"usage":{"cachedInputTokens":2195643,"inputTokens":482,"model":"claude-fable-5-1","outputTokens":41928,"runtime":"claude","turns":25,"wallClockMs":1292745}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"89214b73ec1e0b7b","findings":[{"citation":"resolved","description":"Run 4 (d) clamps an appeal to the original plea's share of the balance: sameShare = mulDiv(bal, originalAmount, origBal) (src/Letterbox.sol:298-299), where bal is the writer's balance after the original letter's fee sale and origBal the balance before it, so the clamped amount is always smaller than the original by the fee sale's share (on Sepolia about 0.25-0.275 IMD worth of PLEA out of a balance worth at least 3.5 IMD). Line 306 then applies the same 0.70 IMD floor (_requireWorthTheFee, MIN_SALE_VALUE = 2 * AUTO_SELL_FEE, lines 372-375) the original had to clear. A 20% letter worth between 0.70 and roughly 0.75 IMD at the hourly snapshot (a writer holding 3.5 to 3.75 IMD worth of PLEA) is accepted as a plea, but its appeal amount is worth 0.70 * (1 - 0.275/3.6) ~ 0.65-0.69 IMD and both the APPEAL letter (fallback / letter()) and appealAuto() revert TooSmallForTheFee; the band widens when the hourly price falls between the two letters. The run-4 rule 'whoever could plead by letter can appeal by letter' does not hold for the smallest writers, and status() still tells them to 'send APPEAL <text> before HH:MM'. The gate accepts the same amount through CabalGate.appeal (above the 1% minimum), so escrow and tip are not at risk: the writer loses only the letter route. Merged from audit_math; reproduced with the specialist's proof on this tree (the APPEAL letter reverts with selector 0x7574857e TooSmallForTheFee; appealAuto reverts the same way; gate.appeal for the same amount succeeds). A fix keeping every number: skip _requireWorthTheFee for an appeal whose original already passed it (the delivery fee is capped at the sale since run 4 (c)), or clamp the appeal to max(sameShare, floor amount), which the gate accepts as long as it is at most the original amount.","line":306,"path":"src/Letterbox.sol","proof":"// SPDX-License-Identifier: MIT\npragma solidity 0.8.26;\n\nimport {Fixture} from \"../utils/Fixture.sol\";\nimport {CabalGate} from \"../../src/CabalGate.sol\";\nimport {Letterbox} from \"../../src/Letterbox.sol\";\nimport {FullMath} from \"v4-core/libraries/FullMath.sol\";\nimport {FixedPoint96} from \"v4-core/libraries/FixedPoint96.sol\";\n\ncontract AppealFloorScratch is Fixture {\n    function _letter(address who, bytes memory text) internal returns (bool ok, bytes memory ret) {\n        vm.prank(who);\n        (ok, ret) = address(letterbox).call(text);\n    }\n\n    /// A writer whose 20% letter is worth just over the 0.70 IMD floor cannot appeal it by letter:\n    /// the same-share clamp (d) multiplies by (balance after the fee sale / balance before), which\n    /// is below 0.70 / 0.72 for a small writer, and _requireWorthTheFee refuses the appeal.\n    function test_smallLetterCannotBeAppealedByLetter() public {\n        buy(alice, 3.7e18);\n        skip(1 days);\n        buy(bob, 1e18); // hour checkpoint\n        uint256 price = hook.latestPrice();\n        uint256 bal = plea.balanceOf(alice);\n        uint256 letterAmount = bal * 2_000 / 10_000;\n        uint256 value = FullMath.mulDiv(letterAmount, price, FixedPoint96.Q96);\n        emit log_named_uint(\"letter value (IMD wei)\", value);\n        assertGe(value, 0.70e18, \"the letter is worth at least the floor\");\n        (bool ok, bytes memory ret) = _letter(alice, \"A fifth for the electrician; the rest stays until the lights go out.\");\n        require(ok, string(ret));\n        uint256 id = gate.lastPleaOf(alice);\n        assertEq(gate.pleaBalance(id), bal);\n        require(answer(id, 0), \"verdict\");\n        uint256 balAfter = plea.balanceOf(alice);\n        emit log_named_uint(\"balance before\", bal);\n        emit log_named_uint(\"balance after the fee sale\", balAfter);\n        uint256 sameShare = FullMath.mulDiv(balAfter, letterAmount, bal);\n        emit log_named_uint(\"appeal amount value (IMD wei)\", FullMath.mulDiv(sameShare, price, FixedPoint96.Q96));\n        (ok, ret) = _letter(alice, \"APPEAL The electrician does not wait; the rest still stays.\");\n        if (!ok) {\n            bytes4 sel;\n            assembly { sel := mload(add(ret, 32)) }\n            emit log_named_bytes32(\"revert selector\", bytes32(sel));\n            assertEq(sel, Letterbox.TooSmallForTheFee.selector, \"refused as too small for the fee\");\n            vm.prank(alice);\n            vm.expectPartialRevert(Letterbox.TooSmallForTheFee.selector);\n            letterbox.appealAuto(id, \"The electrician does not wait; the rest still stays.\");\n        }\n        assertTrue(ok, \"the appeal letter must be accepted\");\n    }\n\n    /// The same writer can appeal through the gate directly for the same amount (paying IMD).\n    function test_gateAppealForTheSameAmountIsAccepted() public {\n        buy(alice, 3.7e18);\n        skip(1 days);\n        buy(bob, 1e18);\n        uint256 bal = plea.balanceOf(alice);\n        uint256 letterAmount = bal * 2_000 / 10_000;\n        (bool ok, bytes memory ret) = _letter(alice, \"A fifth for the electrician; the rest stays until the lights go out.\");\n        require(ok, string(ret));\n        uint256 id = gate.lastPleaOf(alice);\n        require(answer(id, 0), \"verdict\");\n        letterbox.settle(id);\n        uint256 balAfter = plea.balanceOf(alice);\n        uint256 sameShare = FullMath.mulDiv(balAfter, letterAmount, bal);\n        vm.prank(alice);\n        gate.appeal(id, sameShare, \"The electrician does not wait; the rest still stays.\");\n    }\n}","reproduction":"Fixture (Sepolia path, mintOracleFee = true, test/utils/Fixture.sol). (1) alice buys PLEA with 3.7e18 IMD; skip 1 day; bob buys with 1e18 IMD so the hour has a checkpoint; P = hook.latestPrice(). alice's balance B = 635,142.949 PLEA; the 20% letter amount 127,028 PLEA is worth 0.7278 IMD at P (>= 0.70, accepted). (2) alice sends the letter 'A fifth for the electrician; the rest stays until the lights go out.' as raw input data (gate.pleaBalance(id) == B); the fee sale sells about 44,386 PLEA. (3) The oracle denies it (answer(id, 0)). (4) alice sends 'APPEAL The electrician does not wait; the rest still stays.'. Inside _appeal, _settleOpen first returns the 127,028 escrow, so bal = 590,757 PLEA and sameShare = 590,757 * 127,028 / 635,143 = 118,151 PLEA, worth 0.677 IMD at P. Expected: an appeal for that amount opens (the gate accepts it: above 1% of the lesser balance and at most the original). Actual: line 306 reverts TooSmallForTheFee; the raw letter call fails with selector 0x7574857e and letterbox.appealAuto(id, text) reverts the same way, while vm.prank(alice) gate.appeal(id, sameShare, text) succeeds. Run: forge test --match-path test/scratch/AppealFloor.t.sol -vv; test_smallLetterCannotBeAppealedByLetter fails on this tree ('the appeal letter must be accepted', revert selector 0x7574857e logged; the test's own 'appeal amount value' log is computed on the pre-settle balance 463,728 and is only indicative) and test_gateAppealForTheSameAmountIsAccepted passes.","severity":"low","snippet":"        _requireWorthTheFee(amount);","title":"APPEAL letter of a floor-sized 20% letter is refused: the same-share clamp (d) drops the appeal under the 0.70 IMD floor the original just cleared"},{"citation":"resolved","description":"Seasons.record (line 154), _tryRecord (line 300) and _dropOwner (lines 309-311) exclude whoever plea.owner() returns when they run. PleaHook.owner (src/PleaHook.sol:117) and PleaLaunch.owner are immutable copies of PLEA.owner() taken at launch, so the wallet that receives the 0.5% owner fee forever stops being excluded the moment PLEA ownership is handed to any other wallet; Ownable2Step (run 4 (c)) only requires the receiving wallet to accept, which a second team wallet does. Nothing ties a plea to the owner it was submitted by: the owner wallet buys PLEA, pleads through the gate (submitSell has no owner check), is approved, then transferOwnership + acceptOwnership moves the title; from that block record() accepts its pleas and closeSeason pays it the IMD share and the 5,000,000-PLEA bonus share; the title can be handed back afterwards. The brief says 'the owner excluded from points, prizes and bonus' and Seasons' own notice says 'the prize fee always leaves the team for good', and the code comment at line 306 shows only the opposite direction (points recorded before a transfer, the new owner not paid) was considered. Only the privileged owner can do this, so it is a trust assumption that the code claims to enforce but does not, not a third-party bypass. Merged from audit_permissions and audit_economics (same root cause). Minimal fix that keeps the design: also exclude the immutable fee beneficiary (IPleaHook(plea.hook()).owner() and PleaLaunch.owner) in record/_tryRecord/_dropOwner, or snapshot the owner into the Plea at _open and exclude the owner-at-submission.","line":154,"path":"src/Seasons.sol","proof":"// SPDX-License-Identifier: MIT\npragma solidity 0.8.26;\n\nimport {Fixture} from \"../utils/Fixture.sol\";\nimport {Seasons} from \"../../src/Seasons.sol\";\n\n/// The season exclusion follows the PLEA owner of the moment, while the hook's fee beneficiary\n/// (PleaHook.owner) is immutable: after a two-step handover the former owner, still paid 0.5% of\n/// every trade, records points and is paid IMD and the PLEA bonus. This test fails on the current\n/// code (record succeeds, the prize and bonus are paid) and passes once the launch owner / fee\n/// beneficiary stays excluded.\ncontract OwnerRotationScratch is Fixture {\n    function test_formerOwnerStaysExcludedAfterHandover() public {\n        fund(OWNER);\n        buy(OWNER, 50e18);\n        skip(1 days);\n        // OWNER pleads 10% of its balance and is approved with 45.\n        uint256 id1 = plead(OWNER, plea.balanceOf(OWNER) / 10);\n        require(answer(id1, 45), \"verdict 1\");\n        vm.expectRevert(Seasons.OwnerExcluded.selector);\n        seasons.record(id1);\n\n        // Two-step handover inside the team.\n        vm.prank(OWNER);\n        plea.transferOwnership(bob);\n        vm.prank(bob);\n        plea.acceptOwnership();\n        assertEq(plea.owner(), bob);\n        assertEq(hook.owner(), OWNER, \"the fee beneficiary does not change\");\n        assertEq(launch.owner(), OWNER);\n\n        // The former owner is still paid the 0.5% owner fee on alice's trade.\n        uint256 feesBefore = hook.totalOwnerFees();\n        buy(alice, 1_000e18);\n        assertGt(hook.totalOwnerFees(), feesBefore);\n\n        // Expected: the launch owner / fee beneficiary stays excluded from points.\n        (bool ok,) = address(seasons).call(abi.encodeCall(Seasons.record, (id1)));\n        assertFalse(ok, \"the former owner must not record points\");\n\n        // ...and from prizes: the season ends when the Cabal dies; close it after the grace.\n        vm.warp(uint256(gate.lastVerdictAt()) + DEADMAN + 1 hours + 1);\n        uint256 imdBefore = imd.balanceOf(OWNER);\n        uint256 pleaBefore = plea.balanceOf(OWNER);\n        uint256[] memory ids = new uint256[](1);\n        ids[0] = id1;\n        seasons.closeSeason(ids);\n        assertEq(imd.balanceOf(OWNER), imdBefore, \"the former owner must not be paid an IMD prize\");\n        assertEq(plea.balanceOf(OWNER), pleaBefore, \"the former owner must not be paid the PLEA bonus\");\n    }\n}","reproduction":"Fixture (test/utils/Fixture.sol, chain 11155111, OWNER = PLEA owner): fund(OWNER); buy(OWNER, 50e18); skip(1 days); id1 = plead(OWNER, bal/10); answer(id1, 45); seasons.record(id1) reverts OwnerExcluded (expected). vm.prank(OWNER) plea.transferOwnership(bob); vm.prank(bob) plea.acceptOwnership(); now plea.owner() == bob while hook.owner() == OWNER and launch.owner() == OWNER. alice buys 1,000 IMD: hook.totalOwnerFees() rises, i.e. OWNER is still the fee beneficiary. Expected per the brief and Seasons' notice: OWNER's plea still earns no points and OWNER is paid no prize or bonus. Actual: seasons.record(id1) succeeds; after vm.warp(lastVerdictAt + DEADMAN + 1 hours + 1), seasons.closeSeason([id1]) pays OWNER 25% of the season pot in IMD and 1,250,000 PLEA (verified in a first version of the scratch test that asserted the payout: topOf(0)[0].wallet == OWNER with 90 points after a second approved plea, IMD balance up, PLEA balance up by exactly 1,250,000e18). Run: forge test --match-path test/scratch/OwnerRotation.t.sol -vv; test_formerOwnerStaysExcludedAfterHandover fails on this tree at 'the former owner must not record points' and passes once the launch owner / fee beneficiary stays excluded (whether by also excluding IPleaHook(plea.hook()).owner() or by excluding the owner at submission).","severity":"low","snippet":"        if (seller == plea.owner()) revert OwnerExcluded();","title":"Owner exclusion follows PLEA.owner() of the moment while the hook's fee beneficiary is immutable: after a two-step handover the former owner, still paid 0.5% of every trade, records points and is paid"},{"citation":"resolved","description":"The attestation carries questionHash, documented in OracleAttestation.sol (line 30-31) as the field 'a consumer that pins its question compares, so an answer to a different question cannot be presented as its own'. The gate checks msg.sender == intake, maps intakeId -> plea, verifies the signature, consumes a.requestId and takes the score; it never compares a.questionHash with keccak256 of the body it paid for, nor a.requestId with intakeId. The signature therefore proves only that the signer scored some request; a dishonest or buggy Intake writer can deliver plea A's signed 45 to plea B's intakeId. The Intake and the oracle signer are IdentityMD's own contracts and the design already trusts them, so this is a documented trust assumption rather than a bypass; it is recorded so the author can decide whether to pin the question (the canonical document hash the oracle signs must then be known on chain) within the 200k callback stipend. Merged from audit_permissions.","line":507,"path":"src/CabalGate.sol","reproduction":"Fixture: alice and bob each buy 1,000 IMD of PLEA; skip 1 day. a = plead(alice, small(alice)); b = plead(bob, small(bob)) (both Pending). att = attestation(45, keccak256(abi.encode('oracle', a))) with att.questionHash = keccak256(bytes(gate.question(a))), signed by the oracle signer; deliver it through the Intake for plea b's intakeId: intake.complete(intakeIdOf(b), 0, abi.encode(intakeIdOf(b), att, sign(att))). Actual: delivered == true, gate.getPlea(b).status == Approved with score 45 and plea a stays Pending, although the signed document is plea a's. Expected under a pinned question: the gate rejects an attestation whose questionHash is not plea b's. test/scratch/AccessReview.t.sol::test_intakeCanRouteAnotherRequestsAnswerToADifferentPlea passes on this tree (the behaviour happens); every existing test in the repository also passes with the Fixture's dummy questionHash keccak256('question'), the same observation.","severity":"info","snippet":"        _verifyAttestation(a, signature);\n        _consume(a.requestId);","title":"CabalGate.onOracleResult never binds the signed attestation to the plea: questionHash is not compared with the plea's question and requestId is not tied to intakeId, so which plea a signed score lands"},{"citation":"resolved","description":"By the agreed trader rule the hookData address is the trader: the hook writes that wallet's Basis (imdSpent, pleaHeld, avgBuyTime), delivers it the PLEA and stacks its cashback, with no consent from the named wallet. CabalGate._factScore reads avgBuyTime for the holding-time band (14/9/5 points at 7/3/1 days); a buy naming a victim moves avgBuyTime toward now, weighted by the PLEA bought, and can push a plea that needed 33 to need 40 or more. The attacker pays the IMD and gifts the PLEA and the cashback, so it is a costly grief, and it is the rule the brief asks for; recorded as a trust/asymmetry note so the author can decide whether the buy record should follow hookData only when the swapper (or the router's msgSender()) equals the named trader. Merged from audit_permissions.","line":537,"path":"src/PleaHook.sol","reproduction":"Fixture: alice buys 1,000 IMD; skip 1 day (Cabal alive). (,, avgBefore) = hook.basisOf(alice); gate.factScore(alice, bal/10) == 42. vm.prank(bob); router.buyExactIn(1_000e18, abi.encode(alice)). Actual: hook.basisOf(alice).avgBuyTime > avgBefore (alice's holding time reset toward now by bob's trade), alice's PLEA balance grows by the bought amount, alice's cashback is stacked for alice, and gate.factScore(alice, newBal/10) falls to 36 (the one-day holding band is lost until a day passes again), so a plea that needed 28 now needs 34. Expected under a consent model: a wallet's scored buy record changes only through its own trades. test/scratch/AccessReview.t.sol::test_hookDataWritesAnotherWalletsBasis passes on this tree (logs 'fact score before: 42', 'fact score after: 36').","severity":"info","snippet":"            _updateBasis(trader, buy, imdBasis + imdFee, buy ? pleaAmt - pleaFee : pleaAmt + pleaFee);","title":"hookData lets any swapper write another wallet's buy record: a stranger's buy naming a holder moves that holder's buy-weighted holding time toward now, a fact-score input"},{"citation":"resolved","description":"Intended owner power, documented as the guide asks rather than as a bypass. An allowed sender still cannot send to the PoolManager or the gate, so it cannot sell into the pool, but it can transfer PLEA to any buyer while the Cabal lives (an off-chain-settled sale) and the exemption can never be revoked (there is no un-allow). Together with finding 2 the owner's circle is the only class that can exit without a plea. No code change is required by the brief; if wanted, list allowed senders in the launch notes and keep the set empty on Sepolia run 4. Merged from audit_permissions.","line":111,"path":"src/PLEA.sol","reproduction":"Fixture, Cabal alive: vm.prank(OWNER) plea.allow(alice); alice buys 1,000 IMD of PLEA; vm.prank(alice) plea.transfer(bob, 1_000_000e18) succeeds (test/Token.t.sol covers it), while vm.prank(carol) plea.transfer(bob, 1) after carol's buy reverts CabalIsWatching. Expected (as designed): only allowed senders move PLEA freely; there is no un-allow.","severity":"info","snippet":"    function allow(address account) external onlyOwner {","title":"Trust assumption: PLEA.allow lets the owner exempt any sender from the Cabal's transfer rule for good (add-only), so an allowed wallet can sell PLEA outside the court while every other holder must ple"},{"citation":"resolved","description":"The brief states the runtime sizes as CabalGate 23,889, PleaHook 24,288 (288 under the EIP-170 limit) and Letterbox 21,383 and asks that any fix stay within them. With the repository's foundry.toml (solc 0.8.26, via-IR, 200 runs) `forge build --sizes` gives CabalGate 23,889 exactly, PleaHook 24,296 (280 under 24,576) and Letterbox 21,397; ADAPTATION.md records the same figures (the trader-resolution and appeal-minimum fixes added 8 and 14 runtime bytes). Both are still under the limit and test/LaunchManifest.t.sol asserts every deployed runtime is at most 24,576 bytes, so nothing on chain is affected; the note records that the brief's size budget was exceeded by the accepted fixes and that the real margin for any further PleaHook change is 280 bytes, so an author sizing a fix against the brief's figure could cross the limit and have PleaLaunch.deployHook's CREATE2 fail. Merged from audit_flow; the companion audit_flow note about launch.json's gas figures does not reproduce on this tree (the notes already state 12652544 and 15436103).","line":35,"path":"src/PleaHook.sol","reproduction":"Compile with the repository's foundry.toml (solc 0.8.26, cancun, via-IR, optimizer 200) and read out/<Name>.sol/<Name>.json deployedBytecode.object, or run `forge build --sizes`. Expected (per the brief): PleaHook 24,288 and Letterbox 21,383. Actual on this tree: PleaHook runtime 24,296 bytes (creation 25,992; 280 under 24,576), Letterbox runtime 21,397 (creation 22,423; margin 3,179), CabalGate 23,889 as stated. ADAPTATION.md records the same figures. keccak256 of the Letterbox creation code is 0xa1604691bfd2bc1d35ab8e48d88a4403f4a20cd0f165988d6ecd16936ef2552a and matches launch.json (test/LaunchManifest.t.sol::test_launchJsonCommitsToThisLetterbox passes), and the manifest suite logs 12652544 launch gas / 15436103 with headroom, the figures the notes already state.","severity":"info","snippet":"contract PleaHook {","title":"Runtime sizes on this toolchain are PleaHook 24,296 and Letterbox 21,397 bytes, 8 and 14 bytes over the budget the brief fixes (24,288 / 21,383); the hook's EIP-170 margin is 280 bytes, not 288"}],"hash":"5dfce7780f314c15e03bea8acb1e29aa75811c4292f602bfef93ac9d9f59b1fd","nodeId":"4db94aaa-2c6e-452b-bf6e-2bf42f0ad714","outcome":"completed","summary":"The review is complete and `.imd-findings.json` holds six findings plus a 48-row coverage record with no `unreached` rows. No repository file was changed; only the findings file and three scratch tests under `test/scratch/` were written.\n\n**What I kept, all reproduced on this tree**\n\n- **Low, Letterbox line 306.** An APPEAL letter of a floor-sized 20% letter is refused. The run-4 same-share clamp always makes the appeal smaller than the original by the fee sale's share, then the same 0.70 IMD floor is applied again. A writer holding 3.5 to 3.75 IMD worth of PLEA can plead by letter but not appeal by letter, while the gate route accepts the same amount. The specialist's proof fails here with `TooSmallForTheFee`, and it is attached as the proof.\n- **Low, Seasons line 154.** The owner exclusion follows the PLEA owner of the moment, while the hook's fee beneficiary is immutable. After a two-step handover inside the team, the former owner still earns the 0.5% fee and now records points and is paid the IMD prize and the 1,250,000 PLEA bonus. I merged the permissions and economics reports into one finding and attached a scratch proof that fails on this code.\n- **Info, three trust notes.** The gate never binds a signed attestation to its plea (the Intake's routing decides), hookData lets a stranger rewrite another wallet's buy record (fact score 42 to 36 in the test), and the owner's add-only `allow` exemption. All three reproduce in scratch tests but rest on the agreed design or trusted IdentityMD contracts.\n- **Info, sizes.** PleaHook is 24,296 bytes and Letterbox 21,397, 8 and 14 bytes over the brief's budget. Both are under EIP-170, with 280 bytes of hook margin.\n\n**What I dropped.** The gas-figure note on launch.json does not reproduce: the notes already state 12,652,544 and 15,436,103, and the manifest suite logs exactly those numbers.\n\n**Other checks that passed.** The Letterbox creation-code hash in launch.json matches this build, the manifest suite passes on an empty Sepolia chain, and the manifest's shape, argument counts and constructor dependency order are valid. The full `forge build --sizes` was killed at the 20-minute limit on this 4-core machine, so sizes were read from the sparse-compiled artifacts instead; this is the one verification that was not done the way the brief names it.","treeHash":null,"usage":{"cachedInputTokens":3044550,"inputTokens":516,"model":"claude-fable-5-1","outputTokens":65995,"runtime":"claude","turns":37,"wallClockMs":1829531}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"723b11f958c65250","findings":[{"citation":"resolved","description":"The brief says the owner is excluded from points, prizes and the PLEA bonus so that the 0.25% prize fee 'always leaves the team for good'. Seasons enforces that only by comparing the plea's seller with plea.owner() at the moment record() runs (src/Seasons.sol:154, and again _tryRecord at :300) and by dropping whoever is the owner when closeSeason runs (_dropOwner, src/Seasons.sol:309-311). Nothing ties a plea to the owner it was submitted by. Ownable2Step (run 4 change c) stops a leader from being stripped, but it does not stop the opposite flow: the owner wallet buys PLEA, pleads through the gate (submitSell has no owner check), is approved, then calls transferOwnership to a second team wallet which calls acceptOwnership; from that block the old owner is an ordinary seller, record() accepts the plea, and closeSeason pays it the IMD share and the 5,000,000-PLEA bonus share. The new owner can hand ownership back afterwards. Since this is only reachable by the privileged owner it is a trust assumption on the team, not a bypass by a third party; it is reported so the judge can decide whether 'leaves the team for good' needs to be enforced (e.g. by snapshotting the owner into the Plea at _open and excluding the recorded owner-at-submission as well) or documented.","line":154,"path":"src/Seasons.sol","reproduction":"Fixture (test/utils/Fixture.sol): fund(OWNER); buy(OWNER, 50e18); skip(1 days); id = plead(OWNER, bal/10); answer(id, 45); seasons.record(id) reverts OwnerExcluded (expected). Then vm.prank(OWNER) plea.transferOwnership(bob); vm.prank(bob) plea.acceptOwnership(); seasons.record(id) now succeeds and topOf(0)[0].wallet == OWNER. After a second approved plea 4h8m later and vm.warp(lastVerdictAt + DEADMAN + 1h + 1), closeSeason(new uint256[](0)) transfers 25% of the pot in IMD and 1,250,000 PLEA to OWNER (the former owner). Expected per the brief: no prize or bonus ever reaches the team's wallet; actual: it does, after a two-step ownership rotation inside the team. Verified with a Foundry test on this tree (test/scratch/OwnerRotation.t.sol, Fixture-based: record(id1) reverts OwnerExcluded while OWNER owns PLEA; after transferOwnership(bob) + bob.acceptOwnership(), record(id1) and record(id2) succeed, topOf(0)[0].wallet == OWNER, and closeSeason pays OWNER IMD plus exactly 1,250,000 PLEA; the test passes, i.e. the payout happens).","severity":"low","snippet":"        if (seller == plea.owner()) revert OwnerExcluded();","title":"Owner exclusion from points and prizes is checked against the owner of the moment, so the team keeps a prize by pleading and then handing ownership on (trust assumption, not enforced)"}],"hash":"a354971ff840b8d383f8dca8b0431772e7aae1e2991b82f013ed1f1ce6c95fbb","nodeId":"62344619-9d04-4c9f-96cf-ab3392976d93","outcome":"completed","summary":"The review is complete and the findings file is in place. Nothing else is pending.\n\n**Outcome.** The economics of PLEA run 4 hold up under the Economic Security, Invariant and Flow Gap checklists. I found one low-severity gap, verified it with a Foundry test, and recorded coverage for all 52 listed entry points plus four invariants and the manifest. The findings file is at `.imd-findings.json`; the working tree has no other changes (the scratch test lives under `test/scratch/`, which is discarded).\n\n**Finding (low, verified).** The owner exclusion from points, prizes and the PLEA bonus is checked only against whoever owns PLEA at the moment of `record` or `closeSeason`. The owner wallet can plead, get approved, rotate ownership to a second team wallet with the two-step transfer, and then be recorded and paid the IMD share plus the 1,250,000 PLEA bonus share. The scratch test reproduces exactly that payout on this tree. This is reachable only by the privileged owner, so it is reported as an unenforced trust assumption against the brief's \"leaves the team for good\" promise, not as a third-party bypass.\n\n**What held.** I traced the Letterbox escrow and tip custody in both fee modes, the exact-output fee swap and its cap, the appeal clamps added in run 4, the deliver fee cap, Seasons pot accounting and rollover, the hook's fee allocation, claims, wall reserve and the new trader rule, and PLEA's transfer gate. The removed keeper tip is gone from the source. The manifest has the right shape and argument counts, and the manifest test suite passes on this tree, including the committed Letterbox hash and the gas cap.\n\n**Not reported.** Two leads were dropped as accepted design: attestations are not bound to the plea's intake id in the gate (the repo's own replay test states the Intake owns that binding), and hookData lets a buyer name any non-excluded address as trader, which only costs the buyer.\n\n**Limits.** The full build took most of the budget, so I did not re-run the whole suite or the fork test. Static-analysis leads in my area (strict equalities, reentrancy flags) were checked by reading and did not reproduce as defects.","treeHash":null,"usage":{"cachedInputTokens":3437568,"inputTokens":646,"model":"claude-fable-5-1","outputTokens":51097,"runtime":"claude","turns":39,"wallClockMs":1733707}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"cbc83f8151b8340d","findings":[{"citation":"resolved","description":"Seasons.record (line 154) and _dropOwner (line 309) exclude whoever plea.owner() returns at that moment. PleaHook.owner (src/PleaHook.sol:117) and PleaLaunch.owner are immutable copies of PLEA.owner() taken at launch, so the wallet that keeps receiving the 0.5% owner fee forever (and may seed before START) stops being excluded the moment PLEA ownership is handed to any other wallet, including the team's own second wallet. Ownable2Step only requires the receiving wallet to accept, which the same team trivially does. The brief says 'the owner excluded from points, prizes and bonus' and 'the prize fee always leaves the team for good'; after a handover the fee beneficiary competes for the IMD pot it feeds and for the 5,000,000 PLEA bonus. Access x asymmetry seam: the privileged wallet is excluded by one identity (PLEA.owner) and paid by another (hook.owner) that cannot change. Minimal fix that keeps the design: also exclude hook.owner() (and pendingOwner) in record/_tryRecord/_dropOwner, or store the launch owner in Seasons from PleaLaunch and exclude both.","line":154,"path":"src/Seasons.sol","reproduction":"Foundry fixture (test/utils/Fixture.sol state, chain 11155111, OWNER = PLEA owner): 1) fund(OWNER); OWNER buys 10 IMD of PLEA; skip 1 day. 2) vm.prank(OWNER) plea.transferOwnership(second); vm.prank(second) plea.acceptOwnership(). Now plea.owner()==second but hook.owner()==OWNER and launch.owner()==OWNER. 3) alice buys 1,000 IMD: hook.totalOwnerFees() rises and pm.balanceOf(OWNER, imdId) rises, i.e. OWNER is still the fee beneficiary. 4) OWNER pleads 10% of its balance, answered 45 -> Approved; seasons.record(id) succeeds (expected: OwnerExcluded). Repeat after 4h8m; seasons.topOf(0)[0].wallet == OWNER. 5) warp past DEADMAN + 1h; seasons.closeSeason([]): OWNER's IMD rises (25% of the season pot) and OWNER receives 1,250,000 PLEA bonus. Expected: the launch owner / fee beneficiary earns no points, prize or bonus. Scratch test test/scratch/AccessReview.t.sol::test_formerOwnerStillPaidHookFeesCanWinPrizesAfterHandover passes on this code, demonstrating the behaviour.","severity":"low","snippet":"        if (seller == plea.owner()) revert OwnerExcluded();","title":"The season exclusion follows the mutable PLEA.owner() while the hook's owner-fee beneficiary and PleaLaunch.owner are immutable: after a handover the former owner (still paid 0.5% of every trade) earn"},{"citation":"resolved","description":"The attestation carries questionHash, documented in OracleAttestation.sol as the field 'a consumer that pins its question compares, so an answer to a different question cannot be presented as its own'. CabalGate pins nothing: it checks msg.sender == intake, maps intakeId -> plea, verifies the signature, consumes a.requestId and takes the score. The signature therefore proves only that the signer scored *some* request; which plea the score lands on is decided by the Intake caller alone. Trust gap (access x asymmetry): the design's stated protection is the oracle signer's signature, but a dishonest or compromised Intake writer (or any bug in the Intake's completion routing) can take the signed 45 of plea A and approve plea B, or approve a plea whose text the panel never read. The gate already builds body(id) with the exact question, so the fix is one cheap check inside the 200k callback stipend: require a.questionHash == keccak256(bytes(_question(id, ...)))/the canonical document hash the oracle signs, or at least require pleaOfIntake routing to match a.requestId when the Intake exposes it. The consequence is bounded by the Intake being an IdentityMD contract, so severity is low.","line":507,"path":"src/CabalGate.sol","reproduction":"Fixture state: alice and bob each buy 1,000 IMD of PLEA; skip 1 day. a = gate.submitSell(small) by alice; b = gate.submitSell(small) by bob (both Pending). Build attestation(45, requestId = keccak('oracle', a)) with questionHash = keccak256(bytes(gate.question(a))), signed by the oracle signer, and deliver it through the Intake for plea b's intakeId: intake.complete(intakeIdOf(b), 0, abi.encode(intakeIdOf(b), a, sig)). Actual: delivered == true and gate.getPlea(b).status == Approved (2) with score 45, though the signed document is plea a's. Expected: the gate rejects an attestation whose questionHash is not plea b's question. Scratch test test/scratch/AccessReview.t.sol::test_intakeCanRouteAnotherRequestsAnswerToADifferentPlea passes on this code.","severity":"low","snippet":"        _verifyAttestation(a, signature);\n        _consume(a.requestId);","title":"CabalGate.onOracleResult never compares the signed questionHash with the plea's own question, so the gate's verdict binding rests entirely on the Intake's routing of intakeId, not on the oracle signat"},{"citation":"resolved","description":"By imd/acc's trader rule the hookData address is the trader, and the hook writes that wallet's Basis (imdSpent, pleaHeld, avgBuyTime) and delivers it the PLEA. There is no consent from the named wallet. CabalGate._factScore reads avgBuyTime for the holding-time band (14/9/5 points at 7/3/1 days); a buy naming a victim moves avgBuyTime toward now, weighted by the PLEA bought. The attacker pays the IMD and gifts the PLEA, so this is a costly grief rather than an extraction, and it is the agreed rule: recorded as a trust/asymmetry note so the author can decide whether the buy record should only follow hookData when the swapper equals the named trader (or the named trader is the router's msgSender()).","line":537,"path":"src/PleaHook.sol","reproduction":"Fixture: alice buys 1,000 IMD; skip 1 day (Cabal alive). Read (,,avgBefore) = hook.basisOf(alice). bob calls router.buyExactIn(1,000e18, abi.encode(alice)). Actual: hook.basisOf(alice).avgBuyTime > avgBefore (alice's holding time reset toward now by bob's trade) and alice's PLEA balance grows by the bought amount; alice's cashback is stacked for alice. Expected under a consent model: a wallet's scored buy record changes only through its own trades. Scratch test test/scratch/AccessReview.t.sol::test_hookDataWritesAnotherWalletsBasis passes on this code.","severity":"info","snippet":"            _updateBasis(trader, buy, imdBasis + imdFee, buy ? pleaAmt - pleaFee : pleaAmt + pleaFee);","title":"hookData lets any swapper write another wallet's buy record (basisOf): a stranger's buy naming a holder shortens that holder's buy-weighted holding time, a fact-score input"},{"citation":"resolved","description":"Intended owner power, documented here as the guide asks rather than as a bypass. An allowed sender still cannot send to the PoolManager or the gate, so it cannot sell into the pool, but it can transfer PLEA to any buyer while the Cabal lives, i.e. sell outside the court, and the exemption can never be revoked. Combined with finding 1 (the owner can hand PLEA ownership to a second wallet and keep the hook fee), the owner's circle is the only class that can exit without a plea. No code change is required by the brief; the fix, if wanted, is to list allowed senders in the launch notes and keep the set empty on Sepolia run 4.","line":111,"path":"src/PLEA.sol","reproduction":"Fixture, Cabal alive: vm.prank(OWNER) plea.allow(alice); alice buys 1,000 IMD of PLEA; vm.prank(alice) plea.transfer(bob, 1_000_000e18) succeeds (Token.t.sol:39 covers it), while vm.prank(carol) plea.transfer(bob, 1) after carol's buy reverts CabalIsWatching. Expected (as designed): only allowed senders move PLEA freely; there is no un-allow.","severity":"info","snippet":"    function allow(address account) external onlyOwner {","title":"Trust assumption: PLEA.allow lets the owner exempt any sender from the Cabal's transfer rule for good (add-only), so an allowed wallet can move PLEA off-chain-settled (OTC) while every other holder mu"}],"hash":"acf338808373aca776cfa5bc8abf6db9b93dd50a4657bc2856454b6a5f91315d","nodeId":"5685dd63-cea3-425a-9d88-e447d2a56333","outcome":"completed","summary":"The review is complete and recorded in `.imd-findings.json` with 4 findings and 50 coverage rows, one for every listed entry point.\n\n**What I found in the permissions area**\n\n- **Low. Season exclusion follows the mutable owner, the fee beneficiary does not.** Seasons excludes `plea.owner()` at record and close time, while the hook's 0.5% fee recipient and PleaLaunch's owner are immutable copies taken at launch. After a two-step handover to the team's second wallet, the original wallet keeps every owner fee and also earns points, the IMD prize and the 1,250,000 PLEA bonus. A fixture test reproduced the full sequence.\n- **Low. The gate never pins the signed questionHash.** `onOracleResult` trusts the Intake's intakeId routing and checks only signer, replay, panel and range. A valid attestation signed for plea A's question, delivered under plea B's intake id, approved plea B with score 45. The attacker here is a dishonest or buggy Intake, so the severity stays low.\n- **Info. hookData writes a stranger's buy record.** A buy that names another wallet moves that wallet's buy-weighted holding time toward now, which is a fact-score input. It costs the attacker the IMD and gifts the PLEA, so it is a documented asymmetry, not an extraction.\n- **Info. Owner allowlist as a trust assumption.** Allowed senders can move PLEA off-court for good while everyone else must plead. Recorded as the intended power the brief asks for.\n\n**What held** after tracing the guards, state changes and failure paths: launcher-only wiring and one-shot initialisation in PLEA and PleaLaunch, the Letterbox-only gate paths and `courtTake`, the PoolManager-plus-flag callback guards in all four unlock callbacks, sells only through the gate while the Cabal lives, the no-tip `rebalance`, and the Merkle distributor. The manifest test confirms the committed Letterbox hash and the registration window.\n\n**Not reached:** the mainnet fork rehearsal (no RPC in this sandbox) and a candidate about contracts under construction posing as plain wallets, which I dropped because such a contract cannot receive the PoolManager's unlock callback. Scratch tests live in `test/scratch/AccessReview.t.sol` and all three pass on the current code.","treeHash":null,"usage":{"cachedInputTokens":2181980,"inputTokens":482,"model":"claude-fable-5-1","outputTokens":41280,"runtime":"claude","turns":29,"wallClockMs":862264}},{"artifacts":[],"attempt":1,"bundleHash":"2e8ba8d2ccce15ba434a006f2d3eeb28e8e2a56681b31f69e7247b8e39eb4996","device":"74f6c6912a376f27","findings":[],"hash":"bae94b55764a2f56bca851063241110f166ef53b35caa69f7c939f890bea2015","nodeId":"51d1ef10-d48f-4dcc-b61f-c7f1fb6073d5","outcome":"completed","summary":"Added failure-path tests and stateful custody invariants for trader resolution, gas limits, fee surplus, vault discovery, and ownership transitions. Changes are limited to `test/`.\n\nValidation: `forge build` passed; `forge test` reported **441 passed, 0 failed, 2 skipped**. Fork tests lacked RPC URLs.\n\nNo new defects reproduced.","treeHash":"41bc41c55610f193c66d18640ebcbbe30ddd6af0","usage":{"cachedInputTokens":4436608,"inputTokens":162559,"model":"gpt-6-astra","outputTokens":31589,"runtime":"codex","turns":12,"wallClockMs":1299277}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"28e346843ec15530","findings":[{"citation":"resolved","description":"The manifest's explanatory notes say the five-contract launch transaction costs 11.6M gas as the chain charges it and 14.1M with the deployer's 22% headroom. test/LaunchManifest.t.sol (test_factoryDeploysExactManifestOnAnEmptySepoliaChain) measures the same transaction on this tree and logs 12,652,544 gas and a 15,436,103 gas limit, which is what the assignment brief also states (12.6M / 15.4M). The launch still fits Ethereum's 16,777,216 cap (margin 1,341,113 with headroom), and notes are not deployment authority, so nothing on chain is affected. The notes were evidently written against an earlier, smaller tree (the run-4 Letterbox and hook changes grew the init code) and were not refreshed when the hash was. A reviewer reading the notes alone would believe the margin to the cap is twice what it is.","line":55,"path":"launch.json","reproduction":"Read launch.json notes: '11.6M gas measured as the chain charges it, 14.1M with a 22% gas-limit headroom'. Run `forge test --match-path test/LaunchManifest.t.sol --match-test test_factoryDeploysExactManifestOnAnEmptySepoliaChain -vv`. Expected: the notes' figures equal the test's log. Actual: the test logs 'five-contract launch transaction gas through IMD's factory: 12652544' and 'gas limit with IMD's headroom: 15436103'. Fix: update the two numbers in the notes to 12.7M and 15.4M (or drop them, since the test asserts the cap).","severity":"info","snippet":"11.6M gas measured as the chain charges it, 14.1M with a 22% gas-limit headroom","title":"launch.json notes under-state the measured launch gas by about 1M (11.6M/14.1M written, 12.65M/15.44M measured by the repository's own test)"},{"citation":"resolved","description":"The assignment states the runtime sizes as CabalGate 23,889, PleaHook 24,288 (288 under the EIP-170 limit) and Letterbox 21,383 and asks that any fix stay within them. On this tree with the repository's foundry.toml (`forge build --sizes`), CabalGate is exactly 23,889 but PleaHook is 24,296 (280 under 24,576) and Letterbox is 21,397. Both are still under the limit and test/LaunchManifest.t.sol asserts every deployed runtime is at most 24,576 bytes, so this is not a defect in the code; it records that the real margin for any PleaHook fix is 280 bytes, 8 fewer than the brief says, so an author sizing a fix against the brief's figure could exceed the limit and have the hook's CREATE2 deployment (PleaLaunch.deployHook) fail.","line":35,"path":"src/PleaHook.sol","reproduction":"Run `forge build --sizes` in the repository root. Expected (per the brief): PleaHook 24,288, Letterbox 21,383. Actual: `| PleaHook | 24,296 | 25,992 | 280 | 23,160 |` and `| Letterbox | 21,397 | 22,423 | 3,179 | 26,729 |`; CabalGate matches at 23,889. No code change needed; the budget figures should be refreshed from this build.","severity":"info","snippet":"contract PleaHook {","title":"Runtime sizes on this toolchain are PleaHook 24,296 and Letterbox 21,397 bytes, not the 24,288 / 21,383 the brief fixes as the budget; the hook's EIP-170 margin is 280 bytes"}],"hash":"e3107a0e4ead8c89e71db6962338fa351c01e4c429debea8135b59ace065bbb9","nodeId":"84cdeccf-c576-4df3-98cb-ae14a04d6793","outcome":"completed","summary":"Findings file written and validated. The working tree shows no tracked changes, and the scratch directory is removed.\n\n**Outcome.** I traced the control flow of all 54 listed entry points across CabalGate, Letterbox, PLEA, PleaDistributor, PleaHook, PleaLaunch and Seasons, plus the launch manifest, against the Execution Trace, Periphery and First Principles checklists. I found no exploitable defect. The full non-fork test suite passes on this tree. The Letterbox creation-code hash compiled here matches the value in launch.json, the manifest schema and constructor argument counts are correct, and the launch fits the gas cap.\n\n**Reported in `.imd-findings.json`** (both info severity, with concrete reproductions):\n\n- **Stale gas figures in the manifest notes.** The notes say 11.6M gas and 14.1M with headroom. The repository's own LaunchManifest test measures 12,652,544 and 15,436,103 on this tree. Still under the cap, but the stated margin is roughly double the real one.\n- **Runtime size budget drift.** The brief fixes PleaHook at 24,288 bytes and Letterbox at 21,383. This build gives 24,296 and 21,397, so the hook's EIP-170 margin is 280 bytes, not 288. CabalGate matches exactly.\n\n**Leads checked and rejected.** The trader rule's \"plain wallet\" test could in principle match a contract still in its constructor, but the PoolManager cannot call back into an address without code, so the path is unreachable and I did not report it. The run-4 changes (trader resolution, keeper tip removal, the capped delivery fee, the appeal fee and share-band clamp, Ownable2Step) all behave as specified along every path I traced, including the boundary between the 7-minute sale window and settle, and the consistency of the three staleness checks between the gate and the Letterbox.\n\n**Not covered.** The fork tests (test/fork) need MAINNET_RPC_URL and were not run. The Sepolia addresses in launch.json (Intake, oracle fee asset, TestIMD, signer, PoolManager, Stacker) were not verified against the live chain.","treeHash":null,"usage":{"cachedInputTokens":1751453,"inputTokens":386,"model":"claude-fable-5-1","outputTokens":49283,"runtime":"claude","turns":29,"wallClockMs":1154663}},{"artifacts":[],"attempt":1,"bundleHash":"850f730dc7add99324861a6a1c217768e487b604b8f762fb071b21015e0ccc71","device":"41822d343cdb63ba","findings":[],"hash":"e41c52c3b6a7529955b2ba0781d5ce5ba2f5597d6ca4da97c99b8f192190940a","nodeId":"8f8349c9-3122-4b17-b8a3-a151063e3e2c","outcome":"completed","summary":"Updated [launch.json](/home/imd4/.identitymd/work/2234e9a2-925b-4a9b-85a6-a7c68712da72/8f8349c9-3122-4b17-b8a3-a151063e3e2c/launch.json) with run-4 notes and verified gas figures. Constructor arguments and Letterbox hash match the accepted build.\n\n`forge build` passed. `forge test`: 407 passed, 0 failed; 2 fork checks skipped without RPC URLs. Only `launch.json` changed.","treeHash":"663a7b7e9b4defdadc76939aadcbaef6c70d6056","usage":{"cachedInputTokens":1117659,"inputTokens":54986,"model":"gpt-6.1-sol","outputTokens":6805,"runtime":"codex","turns":9,"wallClockMs":389451}},{"artifacts":[],"attempt":1,"bundleHash":null,"device":"918f8261a6fd589c","findings":[{"citation":"resolved","description":"imd/acc's trader rule (change a) says a trade whose trader cannot be resolved still goes through without cashback (after the Cabal dies) or falls back to the router's msgSender() (while it lives). _resolveTrader decodes any 32-byte hookData with abi.decode(hookData, (address)); Solidity 0.8 validates the address type and reverts with empty data when the word has bits above 160 set. The revert escapes beforeSwap and the PoolManager wraps it, so the swap reverts (WrappedError from the hook with empty inner data) instead of continuing down the resolution chain. A router that forwards user-supplied hookData, or a front end that encodes the trader with a packed or mis-padded word, makes every such swap fail even though a valid fallback (msgSender(), or 'no trader' after death) exists. Fix: decode the word as uint256 and treat word > type(uint160).max like the msgSender() path already does (return zero / fall through), so the stated rule holds for every 32-byte hookData.","line":655,"path":"src/PleaHook.sol","reproduction":"State: launch fixture (test/utils/Fixture.sol), Cabal dead (warp past lastVerdictAt + DEADMAN). Call: alice -> BuyRouter.buyExactIn(5e18, abi.encode(uint256(uint160(alice)) | (1 << 200))) (BuyRouter has no msgSender()). Expected per the trader rule: the buy goes through with plain v4 accounting, trader zero, no cashback, no buy record (as test_noTraderAfterDeathBuyGoesThroughWithoutCashback shows for empty hookData). Actual: the swap reverts (WrappedError(hook, 0x575e24b4 beforeSwap, 0x, 0xa9e35b2f HookCallFailed)). While the Cabal lives the same word through MsgSenderRouter.swap(true, 5e18, dirty) also reverts instead of falling back to the router's caller. Scratch test test/scratch/Leads.t.sol: test_dirtyHookDataWordRevertsAfterDeath and test_dirtyHookDataWordRevertsWhileAliveEvenWithMsgSender both fail on this code.","severity":"low","snippet":"            trader = abi.decode(hookData, (address));","title":"A 32-byte hookData word with dirty upper bits reverts the whole swap instead of resolving to no trader"},{"citation":"resolved","description":"Change (d) clamps an appeal to the original plea's share of the balance: sameShare = floor(bal * origAmount / origBal). CabalGate._appeal then checks the amount against its 1% minimum computed on min(bal, originalBalance): least = floor(bal * 100 / 10000). When the original site plea (Letterbox.plead with an explicit amount) was exactly the gate's minimum, origAmount = floor(origBal / 100), and the fee sale shrank the balance so bal < origBal, the clamp evaluates floor(bal/100 - bal*r/(100*origBal)) with r = origBal mod 100. Whenever origBal is not a multiple of 100 and bal is, that is floor(bal/100) - 1, one wei under the gate's least, and appealFor reverts AmountTooSmall. Balances at 18 decimals are essentially uniformly distributed mod 100, so about 1 in 100 such appeals fails for no reason the writer can see or fix (the Letterbox chooses the amount; the writer can only fall back to CabalGate.appeal and pay the fees in IMD by hand). Fix: compute sameShare with FullMath.mulDivRoundingUp, or raise it to the gate's minimum for min(bal, origBal) before calling appealFor.","line":297,"path":"src/Letterbox.sol","reproduction":"State: launch fixture, whale buys 2,000 IMD of PLEA, 1 day later holds B PLEA with B mod 100 != 0 (the test sets B = b0 - b0%100 - 1 with deal; a natural balance is equally likely to satisfy it). Calls: whale -> Letterbox.plead(B/100, text) (exactly the gate's 1% minimum; pleaBalance[id] == B), oracle answers 0 (Denied), Letterbox.settle(id) returns the escrow so the balance is bal = B - feePlea < B; with bal a multiple of 100 (the test rounds it down with deal; naturally about 1 in 100 cases), whale -> Letterbox.appealAuto(id, text). Expected: the appeal opens for the same 1% share as the original. Actual: revert CabalGate.AmountTooSmall() because sameShare = bal/100 - 1 < least = bal/100. Scratch test test/scratch/Leads.t.sol: test_appealAutoOfOnePercentPleaRoundsUnderTheGateMinimum fails with AmountTooSmall() on this code.","severity":"low","snippet":"            uint256 sameShare = FullMath.mulDiv(bal, gate.getPlea(originalId).amount, origBal);","title":"The Letterbox's same-share appeal clamp floors one wei below the gate's 1% minimum, refusing appealAuto of a minimum-size site plea"}],"hash":"ff186251591641e69caefb797d0b8b5e9d0c440ba9ae61ddb16315ddfb33e68f","nodeId":"34cccda1-a8ce-4076-bd81-6bb71818ab82","outcome":"completed","summary":"The review is complete. The findings file holds two substantiated defects, both low severity, and the working tree is otherwise untouched apart from the scratch test.\n\n**Contracts read in full:** PLEA, CabalGate, Seasons, PleaDistributor, PleaLaunch, PleaHook, Letterbox, OracleAttestation, and both interfaces. Everything in `src/` was reached. Not exercised: the fork rehearsals in `test/fork/` (no RPC in this environment) and the live Sepolia Intake, Stacker, sIMD and TestIMD contracts, which remain trusted dependencies. The non-fork suite passes (387 tests, 0 failures), the manifest has only the three schema keys with the right argument counts, and the runtime sizes match the task's figures (CabalGate 23,889, PleaHook 24,288, Letterbox 21,383).\n\n**Findings, both reproduced by `test/scratch/Leads.t.sol`:**\n\n- **Low, PleaHook.sol:655.** A 32-byte hookData word with bits above 160 set makes `abi.decode(hookData, (address))` revert, so the swap fails instead of falling through to the router's `msgSender()` or to \"no trader\" after death. Repro: a buy through a router with hookData `abi.encode(uint256(uint160(alice)) | 1 << 200)` reverts in both states where the rule says it should go through.\n- **Low, Letterbox.sol:297.** The same-share appeal clamp floors, and the gate's 1% minimum floors from a larger number, so an appeal of a site plea placed at exactly the 1% minimum lands one wei under the minimum whenever the original balance is not a multiple of 100 and the shrunk balance is. `appealAuto` then reverts `AmountTooSmall`, about 1 in 100 such appeals; the writer can only fall back to a hand appeal paying IMD. Rounding up or raising the clamp to the gate's minimum fixes it.\n\n**Nothing critical or high was found.** The new trader rule, keeper-tip removal, fee cap at delivery, Ownable2Step, and appeal-share clamp behave as specified in every other path I traced: custody of escrows and tips, exact-output fee swaps, PLEA transfer gating, Seasons accounting with ERC-6909 claims, and the hook's delta settlement in both pool orientations.\n\n**Trust assumptions to carry forward:** the oracle signer and Intake (the gate binds neither `a.requestId` to the Intake id nor `questionHash` to the body, so a misrouted callback from the Intake would be accepted), the Stacker's `credit`, the PLEA owner's add-only allowlist, the distributor owner's one-time Merkle root, and the immutable hook fee beneficiary.","treeHash":null,"usage":{"cachedInputTokens":1804658,"inputTokens":386,"model":"claude-fable-5-1","outputTokens":58031,"runtime":"claude","turns":25,"wallClockMs":1225594}}],"verification":[{"checks":[{"durationMs":397429,"exitCode":0,"name":"build","output":"Compiling 147 files with Solc 0.8.26\nSolc 0.8.26 finished in 397.23s\nCompiler run successful with warnings:\nWarning (2018): Function state mutability can be restricted to pure\n   --> src/CabalGate.sol:706:5:\n    |\n706 |     function _text(string storage t, bool json) internal view returns (string memory) {\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\n","passed":true},{"durationMs":9830,"exitCode":0,"name":"test","output":"No files changed, compilation skipped\n\nRan 1 test for test/fork/ForkMainnet.t.sol:ForkMainnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 645.39µs (0.00ns CPU time)\n\nRan 1 test for test/fork/ForkTestnet.t.sol:ForkTestnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 617.29µs (0.00ns CPU time)\n\nRan 4 tests for test/Token.t.sol:TokenTest\n[PASS] test_distributorAndAllowlistMaySend() (gas: 213606)\n[PASS] test_freeForeverOnceTheCabalDies() (gas: 184114)\n[PASS] test_launcherAndInitAreOneShot() (gas: 127121)\n[PASS] test_walletsCannotSendWhileTheCabalWatches() (gas: 331572)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 42.37ms (490.12µs CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:LetterboxMainnetPathTest\n[PASS] test_letterBuysTheOracleFeeAndTheTipWithPlea() (gas: 9213648)\n[PASS] test_mintingTheFeeIsRefusedOnMainnet() (gas: 733988)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 59.96ms (2.93ms CPU time)\n\nRan 6 tests for test/DistributorAdversarial.t.sol:DistributorAdversarialTest\n[PASS] testFuzz_modifiedLeafOrProofCannotRedirectFunds(uint8,uint8,uint256) (runs: 256, μ: 259302, ~: 259286)\n[PASS] test_claimsCrossBitmapWordsAndCannotBeClaimedTwice() (gas: 1724610)\n[PASS] test_failedTokenTransferRollsBackBitmapAndCanBeRetried() (gas: 317232)\n[PASS] test_fullAllocationAndZeroAmountLeavesDoNotCorruptAdjacentBits() (gas: 260500)\n[PASS] test_rootCannotChangeAfterCommitmentEvenBeforeFirstClaim() (gas: 115955)\n[PASS] test_unsetRootAndUnauthorizedRootDoNotConsumeClaims() (gas: 276001)\nSuite result: ok. 6 passed; 0 failed; 0 skipped; finished in 60.52ms (57.06ms CPU time)\n\nRan 29 tests for test/Gate.t.sol:GateTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340238)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886515)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803827)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826287)\n[PASS] test_callbackFitsTheStipend() (gas: 7822839)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096040)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277015)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791432)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762349)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614957)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684709)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730745)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465765)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754199)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817153)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 29 passed; 0 failed; 0 skipped; finished in 66.06ms (22.27ms CPU time)\n\nRan 30 tests for test/Orientation.t.sol:GatePleaIsZeroTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340260)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886537)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803849)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826309)\n[PASS] test_callbackFitsTheStipend() (gas: 7822861)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096062)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277037)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791454)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762371)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_orientationIsPleaZero() (gas: 15922)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614979)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684731)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730767)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465787)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754221)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817175)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 30 passed; 0 failed; 0 skipped; finished in 72.00ms (28.50ms CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:OwnerExclusionTest\n[PASS] test_nobodyGetsAKeeperTip() (gas: 486471)\n[PASS] test_ownerPleasEarnNoPoints() (gas: 4972130)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 24.12ms (1.12ms CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedPaidFeeTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12726109)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12659407)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9283912)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8527902)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9309902)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8171246)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8430882)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 93.69ms (20.61ms CPU time)\n\nRan 2 tests for test/LaunchManifest.t.sol:PostLaunchTest\n[PASS] test_committedHookDeploysLaterAndMintsOnlyTheFixedSplit() (gas: 135922104)\n[PASS] test_committedLetterboxDeploysLater() (gas: 9913801)\nLogs:\n  deployLetterbox transaction gas: 5136020\n\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 103.07ms (98.67ms CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:RehearsalManifestTest\n[PASS] test_laterBlockCannotRegisterLauncher() (gas: 13266059)\n[PASS] test_separateConstructorCallsInDeploymentBlockStillWork() (gas: 14183820)\n[PASS] test_separateTransactionsLeaveTheAcceptedDeploymentBlockWindow() (gas: 13400445)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 6.98ms (4.73ms CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:AtomicManifestTest\n[PASS] test_factoryDeploysExactManifestOnAnEmptySepoliaChain() (gas: 50242067)\nLogs:\n  five-contract launch transaction gas through IMD's factory: 12652544\n  gas limit with IMD's headroom: 15436103\n  margin to the 16,777,216 cap: 1341113\n\n[PASS] test_launchJsonCommitsToThisLetterbox() (gas: 31298)\n[PASS] test_launchJsonEncodesOracleMintFlagAsStaticWord() (gas: 10484)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 115.27ms (112.72ms CPU time)\n\nRan 12 tests for test/TraderResolution.t.sol:TraderResolutionTest\n[PASS] testFuzz_dirtyHookDataFallsBackToRouterCaller(uint96,bool) (runs: 32, μ: 707000, ~: 707001)\n[PASS] test_dirtyHookDataAfterDeathBuyHasNoTrader() (gas: 482078)\n[PASS] test_dirtyHookDataFallsBackToRouterCallerWhileAlive() (gas: 718951)\n[PASS] test_dirtyHookDataWithoutFallbackWhileAliveRequiresRecipient() (gas: 82148)\n[PASS] test_feeSurplusWithoutATraderIsBurnedOrKeptForThePool() (gas: 520853)\n[PASS] test_hookDataNamesTheTrader() (gas: 673932)\n[PASS] test_invalidHookDataFallsBackToTheRouterCaller() (gas: 2690957)\n[PASS] test_noTraderAfterDeathBuyGoesThroughWithoutCashback() (gas: 440515)\n[PASS] test_noTraderAfterDeathSellGoesThroughWithoutCashback() (gas: 522336)\n[PASS] test_routerCallerIsTheTraderWithoutHookData() (gas: 696907)\n[PASS] test_routerCallerStillCreditedAfterDeath() (gas: 629432)\n[PASS] test_routerWithoutMsgSenderNeedsHookDataWhileTheCabalLives() (gas: 149373)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 78.97ms (44.35ms CPU time)\n\nRan 11 tests for test/Orientation.t.sol:SeasonsPleaIsZeroTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793343)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236802)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471961)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905035)\n[PASS] test_orientationIsPleaZero() (gas: 15724)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814485)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816570)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 136.18ms (81.93ms CPU time)\n\nRan 16 tests for test/SeasonFunds.t.sol:SeasonFundsTest\n[PASS] testFuzz_lateCloseConservesAssets(uint96,uint96,bool) (runs: 32, μ: 1035350, ~: 1073492)\n[PASS] test_bonusIsMintedToSeasonsAndCannotBeWithdrawn() (gas: 24077)\n[PASS] test_bonusPaysTheTopTenAndBurnsTheUnpaidShares() (gas: 1265441)\n[PASS] test_claimRedemptionCallbackCannotBeInvokedOutsideUnlock() (gas: 75348)\n[PASS] test_deathAtBoundaryFlushesClaimsAndLateDonationsOnce() (gas: 1582716)\n[PASS] test_deathBeforeTheSixthSeasonBurnsTheRest() (gas: 909477)\n[PASS] test_deathMidSeasonPreservesEarlierSeasonFees() (gas: 1364594)\n[PASS] test_emptySeasonBurnsItsWholeBonus() (gas: 210361)\n[PASS] test_failedBonusTransferIsBurnedNotStuck() (gas: 584544)\n[PASS] test_failedPayoutRollsForwardWithoutBlockingOtherWinners() (gas: 1302002)\n[PASS] test_feeAtBoundaryBelongsToNextSeason() (gas: 985296)\n[PASS] test_flushBeforeTheEndCannotTouchTheBonus() (gas: 43338)\n[PASS] test_lateClosesOnlyRollUnpaidSharesForward() (gas: 2057793)\n[PASS] test_onlyTheFirstSixSeasonsPayABonus() (gas: 3725664)\n[PASS] test_prizePleaStaysGatedWhileTheCabalWatches() (gas: 650344)\n[PASS] test_unobservedDonationCannotFlowBackwards() (gas: 895448)\nSuite result: ok. 16 passed; 0 failed; 0 skipped; finished in 23.73ms (22.75ms CPU time)\n\nRan 10 tests for test/Seasons.t.sol:SeasonsTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793321)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236691)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471939)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905013)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814463)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816548)\nSuite result: ok. 10 passed; 0 failed; 0 skipped; finished in 82.39ms (54.52ms CPU time)\n\nRan 4 tests for test/OracleConformance.t.sol:OracleConformanceTest\n[PASS] test_callbackSelectorHasTheProtocolStruct() (gas: 748)\n[PASS] test_digestMatchesTheProtocol() (gas: 10527)\n[PASS] test_liveAttestationRecoversToOracleSigner() (gas: 146604)\n[PASS] test_protocolSignatureRecoversToVectorSigner() (gas: 13943)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 930.92µs (438.72µs CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9296247, ~: 9301936)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 87.54ms (86.76ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9296735, ~: 9301936)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 187.78ms (153.07ms CPU time)\n\nRan 20 tests for test/Orientation.t.sol:HookPleaIsZeroTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697464)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294775)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571830)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103593)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_orientationIsPleaZero() (gas: 15910)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819724)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764243)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249381)\nSuite result: ok. 20 passed; 0 failed; 0 skipped; finished in 190.51ms (215.99ms CPU time)\n\nRan 19 tests for test/Hook.t.sol:HookTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697442)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294753)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571808)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103571)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819702)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764200)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249359)\nSuite result: ok. 19 passed; 0 failed; 0 skipped; finished in 191.40ms (124.76ms CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12782094)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12715392)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9320559)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8539202)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9346550)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8182546)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8442182)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 224.92ms (85.74ms CPU time)\n\nRan 3 tests for test/OracleReplay.t.sol:OracleReplayTest\n[PASS] testFuzz_oneSignedRequestCannotSettleTwoPleas(bool,bool) (runs: 32, μ: 7931890, ~: 7921324)\n[PASS] test_deniedRequestCannotBeResignedToApproveItsAppeal() (gas: 8285757)\n[PASS] test_invalidCallbackDoesNotConsumeTheRequest() (gas: 7780529)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 72.78ms (55.65ms CPU time)\n\nRan 5 tests for test/Launch.t.sol:LaunchTest\n[PASS] test_deployHookChecksTheInitCodeAndFlags() (gas: 84639443)\n[PASS] test_eachStepFitsAMainnetTransaction() (gas: 88788260)\nLogs:\n  launch (5 contracts + intake mock): 1248530\n  deployLetterbox: 4774223\n  deployHook: 5607943\n  seed: 598464\n\n[PASS] test_launchWiresEverythingWithoutCallingOutside() (gas: 1320309)\n[PASS] test_ownerMaySeedEarly() (gas: 83866858)\n[PASS] test_seedByOwnerAnyTimeByAnyoneAfterStart() (gas: 83965685)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 228.13ms (449.31ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4122830, ~: 4119959)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11955070)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2078725)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046909)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12106289)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576732)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2173128)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13474309)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1053405)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10100131)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240662)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8792122)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 248.89ms (214.88ms CPU time)\n\nRan 26 tests for test/Letterbox.t.sol:LetterboxTest\n[PASS] testFuzz_namesAreUniqueIdempotentAndReleasedOnClear(uint256,uint8) (runs: 32, μ: 320135, ~: 315948)\n[PASS] test_aBareCommandWordIsNotAPlea() (gas: 5966436)\n[PASS] test_aLapsedApprovalSettlesAndStillCounts() (gas: 5501137)\n[PASS] test_anyoneDeliversAnApprovalForTheTip() (gas: 6123174)\n[PASS] test_appealByLetterKeepsTheOriginalShareAndPaysTheWall() (gas: 10183024)\n[PASS] test_appealLetterRetriesAnAppealTheOracleNeverAnswered() (gas: 21400328)\n[PASS] test_autoSellFeeOnlyOnASaleAndNeverMoreThanHalfOfIt() (gas: 9745542)\n[PASS] test_deadCabalRefusesLettersButSettles() (gas: 5338963)\n[PASS] test_deliverNeedsAnApprovalInsideTheWindowAndTheMinimum() (gas: 6096229)\n[PASS] test_deployLetterboxRefusesOtherCode() (gas: 5287739)\n[PASS] test_expiredPendingPleaSettlesAfterTwentyMinutes() (gas: 5206752)\n[PASS] test_explorerLetterIsTheSameAsARawLetter() (gas: 13547986)\n[PASS] test_invalidNamesAndFailedRenamesPreserveTheOldReservation() (gas: 1334827)\n[PASS] test_leaderboardListsTheSeason() (gas: 6192745)\n[PASS] test_letterCommandsParse() (gas: 8817636)\n[PASS] test_letterPleadsTenPercentPaysFeesInPleaAndEscrows() (gas: 5289498)\n[PASS] test_letterRefusesEthTinyBalancesAndBadText() (gas: 1387704)\n[PASS] test_letterboxIsDeployedOnceFromTheCommittedCode() (gas: 482774)\n[PASS] test_noFunctionIdCanStartALetter() (gas: 835480)\n[PASS] test_noVerdictSettlesAtOnceAndTheNextLetterSettlesTheOldOne() (gas: 8643144)\n[PASS] test_settleReturnsEscrowAndTipAfterADenial() (gas: 5561375)\n[PASS] test_siteAutoSellPleadsAnyValidAmount() (gas: 10121890)\n[PASS] test_statusTellsEachState() (gas: 10135603)\n[PASS] test_strangersCannotUseTheCourtEntryPoints() (gas: 210957)\n[PASS] test_theGateRefusesAManualSaleOfAnEscrowedPlea() (gas: 5296061)\n[PASS] test_theSellLetterIsTheWritersOwnSale() (gas: 6016985)\nSuite result: ok. 26 passed; 0 failed; 0 skipped; finished in 285.00ms (171.23ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionPleaZeroTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4122366, ~: 4117717)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11954633)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2079681)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046221)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12105852)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576295)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2172992)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13472092)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1052581)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10098966)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240213)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8791685)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 296.31ms (264.94ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsPleaZeroTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 301.43ms (178.51ms CPU time)\n\nRan 3 tests for test/HookAdversarial.t.sol:LaunchFeeBoundaryTest\n[PASS] testFuzz_launchFeeOnlyFallsWithTime(uint256,uint256) (runs: 256, μ: 24027, ~: 24152)\n[PASS] test_largeLaunchBuyRollsBackAndSucceedsAtWindowEnd() (gas: 730740)\n[PASS] test_launchFeeHasExactStartMidpointAndEndValues() (gas: 43067)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 21.80ms (7.00ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeeTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9261225, ~: 9267761)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 359.45ms (251.94ms CPU time)\n\nRan 5 tests for test/SeasonRanking.t.sol:SeasonRankingTest\n[PASS] testFuzz_rankingsMatchSortedResultsInAnyRecordOrder(uint256) (runs: 32, μ: 10507728, ~: 10524861)\n[PASS] test_closeSeasonUsesTheSameTiesForPrizes() (gas: 948987)\n[PASS] test_earlierEqualScoreCanReplaceACountedPleaWithoutChangingPoints() (gas: 737882)\n[PASS] test_replacingALowerScoreRemovesItsIdFromTheTieKey() (gas: 738576)\n[PASS] test_walletTieUsesNewestCountedPleaNotLastRecordedPlea() (gas: 775525)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 386.25ms (385.50ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeePleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9262758, ~: 9267938)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 421.54ms (404.42ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1147627, ~: 1142623)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196572)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653721)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 134604)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64100)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309863)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2555263)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 462551)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290623)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601944)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 442.31ms (407.00ms CPU time)\n\nRan 7 tests for test/SeasonAdversarial.t.sol:SeasonAdversarialTest\n[PASS] testFuzz_failedPrizeDoesNotBlockOthersAndUnpaidShareReachesWall(bool) (runs: 256, μ: 1821807, ~: 1821807)\n[PASS] testFuzz_prizeRoundingConservesAnOddSizedPot(uint256) (runs: 256, μ: 4904627, ~: 4925839)\n[PASS] test_batchIgnoresUnknownDeniedAndRepeatedIdsButCannotReopenASeason() (gas: 1061724)\n[PASS] test_closeBeforeGraceRollsBackItsBatchRecording() (gas: 634562)\n[PASS] test_flushBeforeFinalCloseCannotMoveAnyFunds() (gas: 553044)\n[PASS] test_prizesRequireSixtyPoints() (gas: 1262699)\n[PASS] test_recordRejectsDenialsDuplicatesAndLateApprovals() (gas: 813836)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 527.99ms (528.49ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 555.87ms (325.47ms CPU time)\n\nRan 12 tests for test/HookRevision.t.sol:HookRevisionPleaIsZeroTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 32, μ: 1314209, ~: 1313971)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 32, μ: 2432292, ~: 2362579)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 32, μ: 5206336, ~: 5206394)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 32, μ: 2706149, ~: 2703938)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 32, μ: 3884650, ~: 3661467)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 32, μ: 2142054, ~: 2133439)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 32, μ: 3059602, ~: 3174924)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 32, μ: 2245197, ~: 2236342)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594904)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848319)\n[PASS] test_orientationIsPleaZero() (gas: 15668)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117392)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 399.56ms (920.87ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialPleaZeroTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1148149, ~: 1145342)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196880)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653449)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 135432)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64040)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309347)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2554435)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 466981)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290599)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601256)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 495.94ms (477.16ms CPU time)\n\nRan 18 tests for test/GateAdversarial.t.sol:GateAdversarialTest\n[PASS] testFuzz_panelAndAnswerValidationCannotConsumeRequests(uint8) (runs: 256, μ: 4954358, ~: 4957679)\n[PASS] testFuzz_printablePleaRoundTripsThroughQuestionJson(uint256,uint16) (runs: 256, μ: 4996408, ~: 4902758)\n[PASS] testFuzz_signedQuorumMustBeReached(uint16,bool) (runs: 256, μ: 5044315, ~: 5055058)\n[PASS] test_aWhaleCanStillPleadTheMaximum() (gas: 5227666)\n[PASS] test_amountLimitsFailBeforeChargingAndOnePercentIsTheMinimum() (gas: 4977182)\n[PASS] test_appealIsAcceptedAtItsLastSecondAndCannotBeStolen() (gas: 8193866)\n[PASS] test_appealOracleFeeFailureRollsBackWallFundingAndOriginalFlag() (gas: 8695669)\n[PASS] test_approvedWindowOnlyClearsAfterTheLastSecond() (gas: 7922615)\n[PASS] test_changingSignedAnswerOrConsumerChainInvalidatesSignature() (gas: 4978232)\n[PASS] test_deadManExpiresAtTheExactSecondAndNeverAcceptsANewVerdict() (gas: 4874288)\n[PASS] test_denialCooldownEndsExactlyAtFourHours() (gas: 7699273)\n[PASS] test_futureIssuanceAndExpiredAttestationsRejectAtExactBoundaries() (gas: 7892452)\n[PASS] test_gateUnlockCallbackCannotBeInvokedOutsideItsOwnSale() (gas: 88179)\n[PASS] test_latePendingCannotConsumeSignatureOrExtendHeartbeat() (gas: 4863973)\n[PASS] test_malformedUtf8AndHiddenControlsFailWithoutCharging() (gas: 958224)\n[PASS] test_missingSellAllowanceDoesNotConsumeTheApprovedPlea() (gas: 4979060)\n[PASS] test_pendingAndExecutionDeadlinesAreInclusive() (gas: 5395699)\n[PASS] test_slippageRevertRestoresApprovalSupplyAndAllFeeState() (gas: 6050183)\nSuite result: ok. 18 passed; 0 failed; 0 skipped; finished in 732.78ms (616.54ms CPU time)\n\nRan 11 tests for test/HookRevision.t.sol:HookRevisionTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 64, μ: 1314110, ~: 1313900)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 64, μ: 2469695, ~: 2413386)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 64, μ: 5206299, ~: 5206340)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 64, μ: 2706039, ~: 2703908)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 64, μ: 3884194, ~: 3661445)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 64, μ: 2144446, ~: 2133516)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 64, μ: 2788043, ~: 2739775)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 64, μ: 2244220, ~: 2236320)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594882)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848297)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117370)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 419.08ms (1.50s CPU time)\n\nRan 11 tests for test/BonusInvariant.t.sol:BonusEdgeTest\n[PASS] testFuzz_anyRankingPaysPlusBurnsExactlyTheBonus(uint256) (runs: 512, μ: 3145836, ~: 2987455)\n[PASS] test_bonusPaidAfterDeathIsFreelyTransferable() (gas: 694020)\n[PASS] test_closeWithinTheGraceHourIsRefused() (gas: 656998)\n[PASS] test_closingTwiceCannotPayASeasonsBonusTwice() (gas: 648680)\n[PASS] test_deathBeforeTradingSeasonZeroEndsBurnsEverythingButSeasonZero() (gas: 817416)\n[PASS] test_eleventhWalletIsNotPaidAndCannotDisplaceRankTen() (gas: 4437034)\n[PASS] test_gateAsSellerForfeitsWhileWatchedButIsPaidAfterDeath() (gas: 1187960)\n[PASS] test_lateApprovalListedAtCloseStillEarnsTheBonus() (gas: 616880)\n[PASS] test_onlyTheBestThreePleasCount() (gas: 1540529)\n[PASS] test_sixtyPointsQualifiesFiftyNineDoesNot() (gas: 1286951)\n[PASS] test_tenQualifiersReceiveTheWholeBonusAndNothingBurns() (gas: 4183387)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 804.93ms (811.90ms CPU time)\n\nRan 3 tests for test/GateFailureInvariant.t.sol:GateFailureInvariantTest\n[PASS]\nGateFailureInvariantTest invariants:\n[PASS] invariant_gateHoldsNothing\n[PASS] invariant_onlyVerdictsMoveTheClock\n[PASS] invariant_pendingBookkeepingIsConsistent\n GateFailureInvariantTest invariants (runs: 64, calls: 4096, reverts: 0)\n\n╭--------------------+---------------+-------+---------+----------╮\n| Contract           | Selector      | Calls | Reverts | Discards |\n+=================================================================+\n| GateFailureHandler | advance       | 498   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | answer        | 415   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | appeal        | 471   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | directFailure | 458   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | execute       | 452   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | expire        | 474   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | fail          | 430   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | plead         | 431   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | strangerFails | 467   | 0       | 0        |\n╰--------------------+---------------+-------+---------+----------╯\n\n[PASS] test_failureAfterDeathDoesNotReviveTheCabal() (gas: 4763614)\n[PASS] test_handlerReachesFailuresVerdictsAndAppeals() (gas: 18558972)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 1.12s (1.06s CPU time)\n\nRan 2 tests for test/BonusInvariant.t.sol:BonusInvariantTest\n[PASS]\nBonusInvariantTest invariants:\n[PASS] invariant_bonusIsHeldPaidOrBurned\n[PASS] invariant_flushedSeasonsStayFinished\n[PASS] invariant_openBonusSeasonsStayFunded\n[PASS] invariant_supplyFallsOnlyByTheBurnedBonus\n BonusInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭--------------+----------+-------+---------+----------╮\n| Contract     | Selector | Calls | Reverts | Discards |\n+======================================================+\n| BonusHandler | advance  | 1226  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | approve  | 1178  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | close    | 1154  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | die      | 1208  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | donate   | 1124  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | flush    | 1199  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | pull     | 1103  | 0       | 0        |\n╰--------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesPaidClosesDeathAndFlush() (gas: 2140371)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 1.97s (1.96s CPU time)\n\nRan 1 test for test/DistributorAdversarial.t.sol:DistributionInvariantTest\n[PASS]\nDistributionInvariantTest invariants:\n[PASS] invariant_deathAndSystemWiringArePermanent\n[PASS] invariant_distributorPaysEachCommittedLeafAtMostOnce\n[PASS] invariant_supplyEqualsAllBalancesAndOnlyBurnsReduceIt\n DistributionInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------------+----------------------------+-------+---------+----------╮\n| Contract            | Selector                   | Calls | Reverts | Discards |\n+===============================================================================+\n| DistributionHandler | advance                    | 1009  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | allowSender                | 1040  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | approveAndSpend            | 1035  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | burnTokens                 | 994   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | claimAllocation            | 1026  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | donate                     | 967   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | transferTokens             | 1069  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | unauthorizedAdministration | 1052  | 0       | 0        |\n╰---------------------+----------------------------+-------+---------+----------╯\n\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 1.78s (1.77s CPU time)\n\nRan 5 tests for test/GasPass.t.sol:GasPassTest\n[PASS] testFuzz_bodyEqualsEscapingTheWholeQuestion(uint256) (runs: 500, μ: 5582012, ~: 5592706)\n[PASS] testFuzz_textCheckMatchesTheOldRules(uint256) (runs: 5000, μ: 929582, ~: 84141)\n[PASS] test_bodyEqualsEscapingTheWholeQuestion() (gas: 12832911)\n[PASS] test_priceViewsMatchAFullScan() (gas: 128851660)\n[PASS] test_textCheckEdgeCases() (gas: 53621558)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 2.16s (4.21s CPU time)\n\nRan 12 tests for test/AuditRun3.t.sol:AuditRun3Test\n[PASS] test_F1_appealLetterCannotRetryAnAppealTheOracleNeverAnswered() (gas: 16420906)\n[PASS] test_F2_aCapSizedAutoSellPleaCannotBeAppealedThroughTheLetterbox() (gas: 33480907)\n[PASS] test_F3_aBareCommandWordBecomesAPaidPlea() (gas: 112574)\n[PASS] test_aLetterboxDeployedByAnyoneElseHasNoPowers() (gas: 5737587)\n[PASS] test_autoSellCannotAcceptASpotPriceUnderTheSnapshotFloor() (gas: 6742997)\n[PASS] test_escrowsAfterTheCabalDies() (gas: 12786705)\n[PASS] test_feeSaleIsBoundedAndTheTipReturns() (gas: 5225357)\n[PASS] test_letterParsingEdgeCases() (gas: 21094806)\n[PASS] test_markerRuleUnchanged() (gas: 6340228)\n[PASS] test_oneCapSizedSaleMovesSpotUnderOnePercent() (gas: 26980332)\nLogs:\n  price impact of a 2.5M PLEA sale, bps: 80\n\n[PASS] test_oracleBodyIsValidJsonForHostileTexts() (gas: 26155768)\n[PASS] test_priceViewsEqualAFullRingScan() (gas: 47483779)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 2.16s (197.69ms CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxInvariantTest\n[PASS]\nLetterboxInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 588   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 573   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 541   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 562   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 605   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 562   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 579   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 549   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 561   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26112427)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.70s (2.63s CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxMainnetInvariantTest\n[PASS]\nLetterboxMainnetInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxMainnetInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 588   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 573   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 541   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 562   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 605   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 562   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 579   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 549   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 561   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26017407)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.79s (2.67s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingInvariantTest\n[PASS]\nTradingInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 742   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 716   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 746   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 741   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 765   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 731   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 789   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 712   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 766   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 737   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 747   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2943640, ~: 2956067)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9136901)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.92s (3.99s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingPleaZeroInvariantTest\n[PASS]\nTradingPleaZeroInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingPleaZeroInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 742   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 716   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 746   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 741   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 765   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 731   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 789   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 712   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 766   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 737   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 747   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2942824, ~: 2955251)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9141711)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 4.46s (4.51s CPU time)\n\nRan 3 tests for test/SeasonInvariant.t.sol:SeasonInvariantTest\n[PASS]\nSeasonInvariantTest invariants:\n[PASS] invariant_prizeMoneyIsPaidOnceOrRemainsInThePotOrWall\n[PASS] invariant_rankingsMatchAllRecordedApprovalsAndClosedSeasonsNeverChange\n SeasonInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------+-------------------------+-------+---------+----------╮\n| Contract      | Selector                | Calls | Reverts | Discards |\n+======================================================================+\n| SeasonHandler | advance                 | 813   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | approvePlea             | 831   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | checkpoint              | 877   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | closeOldest             | 781   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donate                  | 836   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateClaims            | 832   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateWithoutCheckpoint | 804   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | endCabal                | 828   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | flush                   | 771   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | record                  | 819   | 0       | 0        |\n╰---------------+-------------------------+-------+---------+----------╯\n\n[PASS] test_modelCoversDelayedDonationsAndPostFlushClaims() (gas: 3620935)\n[PASS] test_modelCoversPayableClosesRolloverAndFinalFlush() (gas: 4324339)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 9.47s (9.47s CPU time)\n\nRan 11 tests for test/Seasons.t.sol:FastClockTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4792795)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236713)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 1072222)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 41914330)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 1127942)\n[PASS] test_fastFullCycle() (gas: 77173420)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13521)\n[PASS] test_onlyApprovedPleasScore() (gas: 4902188)\n[PASS] test_secondSeasonScoresSeparately() (gas: 47202409)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 2261085)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 117706280)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 9.56s (95.52ms CPU time)\n\nRan 51 test suites in 9.62s (50.93s CPU time): 407 tests passed, 0 failed, 2 skipped (409 total tests)\n","passed":true},{"durationMs":179,"exitCode":0,"name":"source-index","output":"{\"v\":1,\"entryPoints\":[\"CabalGate.appeal(uint256,uint256,string)\",\"CabalGate.appealFor(address,uint256,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.begin()\",\"CabalGate.executeSell(uint256)\",\"CabalGate.executeSellFor(uint256,uint256)\",\"CabalGate.expire(uint256)\",\"CabalGate.onOracleResult(bytes32,(bytes32,uint256,bytes32,uint8,bytes,uint256,uint64,uint64,bytes32,bytes32,uint16,uint16,uint16,uint64,uint64),bytes)\",\"CabalGate.onPleaFailure(bytes32,uint8,bytes32,uint16,uint16,bytes)\",\"CabalGate.submitFor(address,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.submitSell(uint256,string)\",\"CabalGate.unlockCallback(bytes)\",\"Letterbox.appealAuto(uint256,string)\",\"Letterbox.deliver(uint256)\",\"Letterbox.fallback()\",\"Letterbox.letter(string)\",\"Letterbox.plead(uint256,string)\",\"Letterbox.setName(string)\",\"Letterbox.settle(uint256)\",\"PLEA.acceptOwnership()\",\"PLEA.allow(address)\",\"PLEA.approve(address,uint256)\",\"PLEA.burn(uint256)\",\"PLEA.courtTake(address,uint256)\",\"PLEA.init(address,address)\",\"PLEA.renounceOwnership()\",\"PLEA.setLauncher(address,address,address)\",\"PLEA.setLetterbox(address)\",\"PLEA.transfer(address,uint256)\",\"PLEA.transferFrom(address,address,uint256)\",\"PLEA.transferOwnership(address)\",\"PleaDistributor.claim(uint256,address,uint256,bytes32[])\",\"PleaDistributor.renounceOwnership()\",\"PleaDistributor.setMerkleRoot(bytes32)\",\"PleaDistributor.transferOwnership(address)\",\"PleaHook.afterSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),int256,bytes)\",\"PleaHook.beforeSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),bytes)\",\"PleaHook.fundWall(uint256)\",\"PleaHook.rebalance()\",\"PleaHook.seed()\",\"PleaHook.unlockCallback(bytes)\",\"PleaLaunch.deployHook(bytes32,bytes)\",\"PleaLaunch.deployLetterbox(bytes)\",\"PleaLaunch.seed()\",\"Seasons.checkpoint()\",\"Seasons.closeSeason(uint256[])\",\"Seasons.flushToWall()\",\"Seasons.record(uint256)\",\"Seasons.unlockCallback(bytes)\"],\"files\":{\".gitignore\":4,\"ADAPTATION.md\":35,\"README.md\":269,\"foundry.toml\":25,\"launch.json\":56,\"remappings.txt\":4,\"script/Deploy.s.sol\":55,\"script/DeployLetterbox.s.sol\":22,\"script/MineSalt.s.sol\":44,\"src/CabalGate.sol\":817,\"src/Letterbox.sol\":669,\"src/OracleAttestation.sol\":227,\"src/PLEA.sol\":151,\"src/PleaDistributor.sol\":49,\"src/PleaHook.sol\":1062,\"src/PleaLaunch.sol\":152,\"src/Seasons.sol\":357,\"src/interfaces/IPleaParts.sol\":74,\"src/interfaces/IStacker.sol\":12,\"test/AppealRounding.t.sol\":140,\"test/AuditImported.t.sol\":142,\"test/AuditRevision.t.sol\":277,\"test/AuditRun3.t.sol\":391,\"test/BonusInvariant.t.sol\":526,\"test/DistributorAdversarial.t.sol\":329,\"test/GasPass.t.sol\":329,\"test/Gate.t.sol\":408,\"test/GateAdversarial.t.sol\":400,\"test/GateFailureInvariant.t.sol\":330,\"test/Hook.t.sol\":357,\"test/HookAdversarial.t.sol\":256,\"test/HookRevision.t.sol\":378,\"test/JudgeFindings.t.sol\":193,\"test/Launch.t.sol\":156,\"test/LaunchManifest.t.sol\":317,\"test/Letterbox.t.sol\":752,\"test/LetterboxInvariant.t.sol\":441,\"test/OracleConformance.t.sol\":114,\"test/OracleReplay.t.sol\":60,\"test/Orientation.t.sol\":58,\"test/SeasonAdversarial.t.sol\":203,\"test/SeasonFunds.t.sol\":343,\"test/SeasonInvariant.t.sol\":341,\"test/SeasonRanking.t.sol\":168,\"test/Seasons.t.sol\":266,\"test/Token.t.sol\":78,\"test/TraderResolution.t.sol\":207,\"test/TradingInvariant.t.sol\":476,\"test/fork/ForkMainnet.t.sol\":368,\"test/fork/ForkTestnet.t.sol\":765,\"test/utils/ClaimTree.sol\":41,\"test/utils/Fixture.sol\":238,\"test/utils/Mocks.sol\":324,\"test/utils/SeasonModel.sol\":117,\"test/utils/SepoliaFixture.sol\":34},\"excluded\":[\"lib/\",\"node_modules/\"],\"truncated\":false}","passed":true},{"durationMs":18453,"exitCode":0,"name":"slither","output":"[high/medium] weak-prng at src/PleaHook.sol:973: PleaHook._updateWallGuard(int24) (src/PleaHook.sol#973-998) uses a weak PRNG: \"guardRemainder = numerator % 86400 (src/PleaHook.sol#985)\"\n[high/medium] weak-prng at src/PleaHook.sol:1000: PleaHook._checkpoint(uint160) (src/PleaHook.sol#1000-1010) uses a weak PRNG: \"c = ring[hour % 25] (src/PleaHook.sol#1002)\"\n[high/medium] weak-prng at src/PleaHook.sol:283: PleaHook.price24hAgo() (src/PleaHook.sol#283-296) uses a weak PRNG: \"t = ring[target % 25] (src/PleaHook.sol#286)\"\n[high/medium] weak-prng at src/PleaHook.sol:267: PleaHook.latestPrice() (src/PleaHook.sol#267-280) uses a weak PRNG: \"best = ring[lastCheckpointHour % 25].priceX96 (src/PleaHook.sol#270)\"\n[high/high] uninitialized-state at src/Seasons.sol:90: Seasons._best (src/Seasons.sol#63) is never initialized. It is used in:\n[high/high] uninitialized-state at src/Seasons.sol:164: Seasons._bestPleaIds (src/Seasons.sol#64) is never initialized. It is used in:\n[high/high] uninitialized-state at src/Seasons.sol:86: Seasons._top (src/Seasons.sol#62) is never initialized. It is used in:\n[medium/medium] divide-before-multiply at src/PleaHook.sol:1032: PleaHook._alignUp(int24) (src/PleaHook.sol#1032-1036) performs a multiplication on the result of a division:\n[medium/medium] divide-before-multiply at src/PleaHook.sol:1038: PleaHook._alignDown(int24) (src/PleaHook.sol#1038-1042) performs a multiplication on the result of a division:\n[medium/high] incorrect-equality at src/PleaHook.sol:739: PleaHook._applyCap() (src/PleaHook.sol#739-781) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/CabalGate.sol:208: CabalGate.restricted() (src/CabalGate.sol#208-210) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:802: PleaHook.rebalance() (src/PleaHook.sol#802-808) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:739: PleaHook._applyCap() (src/PleaHook.sol#739-781) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:329: PleaHook._pleaIn(PleaHook.Band,uint160) (src/PleaHook.sol#329-341) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:400: Letterbox._settleOpen(address) (src/Letterbox.sol#400-405) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:813: PleaHook._rebalance() (src/PleaHook.sol#813-874) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:377: Letterbox._settle(uint256) (src/Letterbox.sol#377-397) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Seasons.sol:256: Seasons.flushToWall() (src/Seasons.sol#256-274) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:339: Letterbox._close(uint256,Letterbox.Escrow) (src/Letterbox.sol#339-343) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/CabalGate.sol:252: CabalGate._factScore(address,uint256,uint256) (src/CabalGate.sol#252-283) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:938: PleaHook._settleImd(uint256) (src/PleaHook.sol#938-943) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/CabalGate.sol:213: CabalGate.diedAt() (src/CabalGate.sol#213-216) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:377: Letterbox._settle(uint256) (src/Letterbox.sol#377-397) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:407: Letterbox._settleable(uint256) (src/Letterbox.sol#407-414) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:813: PleaHook._rebalance() (src/PleaHook.sol#813-874) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:299: PleaHook.launchExtraBps() (src/PleaHook.sol#299-304) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Seasons.sol:126: Seasons.checkpoint() (src/Seasons.sol#126-137) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Seasons.sol:353: Seasons._pay(address,uint256) (src/Seasons.sol#353-356) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:876: PleaHook._closeWall() (src/PleaHook.sol#876-893) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/PleaHook.sol:283: PleaHook.price24hAgo() (src/PleaHook.sol#283-296) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:407: Letterbox._settleable(uint256) (src/Letterbox.sol#407-414) uses a dangerous strict equality:\n[medium/high] incorrect-equality at src/Letterbox.sol:377: Letterbox._settle(uint256) (src/Letterbox.sol#377-397) uses a dangerous strict equality:\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:473: Reentrancy in PleaHook.afterSwap(address,PoolKey,SwapParams,BalanceDelta,bytes) (src/PleaHook.sol#473-549):\n[medium/medium] reentrancy-no-eth at src/Letterbox.sol:377: Reentrancy in Letterbox._settle(uint256) (src/Letterbox.sol#377-397):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:473: Reentrancy in PleaHook.afterSwap(address,PoolKey,SwapParams,BalanceDelta,bytes) (src/PleaHook.sol#473-549):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:714: Reentrancy in PleaHook._payCashback(address,uint256) (src/PleaHook.sol#714-731):\n[medium/medium] reentrancy-no-eth at src/Letterbox.sol:282: Reentrancy in Letterbox._appeal(address,uint256,string,uint8) (src/Letterbox.sol#282-316):\n[medium/medium] reentrancy-no-eth at src/CabalGate.sol:416: Reentrancy in CabalGate._ask(uint256) (src/CabalGate.sol#416-431):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:739: Reentrancy in PleaHook._applyCap() (src/PleaHook.sol#739-781):\n[medium/medium] reentrancy-no-eth at src/CabalGate.sol:331: Reentrancy in CabalGate.appealFor(address,uint256,uint256,uint256,string,uint8,uint256,uint256) (src/CabalGate.sol#331-346):\n[medium/medium] reentrancy-no-eth at src/Letterbox.sol:264: Reentrancy in Letterbox._plead(address,uint256,string,uint8) (src/Letterbox.sol#264-280):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:813: Reentrancy in PleaHook._rebalance() (src/PleaHook.sol#813-874):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:876: Reentrancy in PleaHook._closeWall() (src/PleaHook.sol#876-893):\n[medium/medium] reentrancy-no-eth at src/PleaHook.sol:473: Reentrancy in PleaHook.afterSwap(address,PoolKey,SwapParams,BalanceDelta,bytes) (src/PleaHook.sol#473-549):\n[medium/medium] reentrancy-no-eth at src/Seasons.sol:221: Reentrancy in Seasons.closeSeason(uint256[]) (src/Seasons.sol#221-252):\n[medium/medium] reentrancy-no-eth at src/Seasons.sol:256: Reentrancy in Seasons.flushToWall() (src/Seasons.sol#256-274):\n[medium/medium] reentrancy-no-eth at src/CabalGate.sol:302: Reentrancy in CabalGate.submitFor(address,uint256,uint256,string,uint8,uint256,uint256) (src/CabalGate.sol#302-319):\n[medium/medium] uninitialized-local at src/Seasons.sol:332: Seasons._payBonus(uint256,Seasons.Entry[10]).paid (src/Seasons.sol#332) is a local variable never initialized\n[medium/medium] uninitialized-local at src/Seasons.sol:168: Seasons._record(uint256,uint256,address,uint8).mi (src/Seasons.sol#168) is a local variable never initialized\n[medium/medium] uninitialized-local at src/PleaHook.sol:288: PleaHook.price24hAgo().bestHour (src/PleaHook.sol#288) is a local variable never initialized\n[medium/medium] uninitialized-local at src/PleaHook.sol:567: PleaHook._payFees(address,bool,uint256,uint256,uint256).toPrize (src/PleaHook.sol#567) is a local variable never initialized\n[medium/medium] uninitialized-local at src/CabalGate.sol:759: CabalGate._validateText(string).len (src/CabalGate.sol#759) is a local variable never initialized\n[medium/medium] uninitialized-local at src/Seasons.sol:236: Seasons.closeSeason(uint256[]).paid (src/Seasons.sol#236) is a local variable never initialized\n[medium/medium] uninitialized-local at src/Seasons.sol:173: Seasons._record(uint256,uint256,address,uint8).pts (src/Seasons.sol#173) is a local variable never initialized\n[medium/medium] uninitialized-local at src/PleaHook.sol:272: PleaHook.latestPrice().bestHour (src/PleaHook.sol#272) is a local variable never initialized\n[medium/medium] unused-return at src/Seasons.sol:278: Seasons._redeemClaims() (src/Seasons.sol#278-285) ignores return value by pm.unlock(abi.encode(amount)) (src/Seasons.sol#284)\n[medium/medium] unused-return at src/PleaHook.sol:908: PleaHook.unlockCallback(bytes) (src/PleaHook.sol#908-936) ignores return value by (d,None) = poolManager.modifyLiquidity(poolKey(),ModifyLiquidityParams({tickLower:lower,tickUpper:upper,liquidityDelta:int256(uint256(liquidity)),salt:0}),) (src/PleaHook.sol#915-921)\n[medium/medium] unused-return at src/PleaHook.sol:245: PleaHook.currentSqrtPriceX96() (src/PleaHook.sol#245-247) ignores return value by (sqrtPriceX96,None,None,None) = poolManager.getSlot0(poolId()) (src/PleaHook.sol#246)\n[medium/medium] unused-return at src/PleaHook.sol:783: PleaHook._removeLiquidity(int24,int24,uint256) (src/PleaHook.sol#783-795) ignores return value by (d,None) = poolManager.modifyLiquidity(poolKey(),ModifyLiquidityParams({tickLower:lower,tickUpper:upper,liquidityDelta:- int256(liquidity),salt:0}),) (src/PleaHook.sol#787-791)\n[medium/medium] unused-return at src/PleaHook.sol:908: PleaHook.unlockCallback(bytes) (src/PleaHook.sol#908-936) ignores return value by poolManager.settle() (src/PleaHook.sol#928)\n[medium/medium] unused-return at src/PleaHook.sol:249: PleaHook.currentTick() (src/PleaHook.sol#249-251) ignores return value by (None,tick,None,None) = poolManager.getSlot0(poolId()) (src/PleaHook.sol#250)\n[medium/medium] unused-return at src/PleaHook.sol:813: PleaHook._rebalance() (src/PleaHook.sol#813-874) ignores return value by (d,None) = poolManager.modifyLiquidity(poolKey(),ModifyLiquidityParams({tickLower:lower,tickUpper:upper,liquidityDelta:int256(uint256(liquidity)),salt:0}),) (src/PleaHook.sol#854-860)\n[medium/medium] unused-return at src/OracleAttestation.sol:158: OracleAttestationConsumer._verifyAttestation(OracleAttestation.Attestation,bytes) (src/OracleAttestation.sol#158-171) ignores return value by (recovered,err,None) = ECDSA.tryRecover(digest,signature) (src/OracleAttestation.sol#166)\n[medium/medium] unused-return at src/PleaHook.sol:938: PleaHook._settleImd(uint256) (src/PleaHook.sol#938-943) ignores return value by poolManager.settle() (src/PleaHook.sol#942)\n[medium/medium] unused-return at src/CabalGate.sol:461: CabalGate._stale(CabalGate.Plea) (src/CabalGate.sol#461-465) ignores return value by (None,None,None,completed) = intake.requests(p.intakeId) (src/CabalGate.sol#463)\n[medium/medium] unused-return at src/CabalGate.sol:613: CabalGate.unlockCallback(bytes) (src/CabalGate.sol#613-646) ignores return value by pm.settle() (src/CabalGate.sol#643)\n[medium/medium] unused-return at src/Letterbox.sol:416: Letterbox._intakeDone(bytes32) (src/Letterbox.sol#416-418) ignores return value by (None,None,None,done) = gate.intake().requests(intakeId) (src/Letterbox.sol#417)\n[low/medium] missing-zero-check at src/PleaLaunch.sol:66: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).plea_ (src/PleaLaunch.sol#66) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:70: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).poolManager_ (src/PleaLaunch.sol#70) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:68: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).seasons_ (src/PleaLaunch.sol#68) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:88: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).owner_ (src/PleaLaunch.sol#88) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:71: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).imd_ (src/PleaLaunch.sol#71) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaHook.sol:194: PleaHook.constructor(IPoolManager,address,IERC20,IStacker,address,address,uint256).seasons_ (src/PleaHook.sol#194) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:67: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).gate_ (src/PleaLaunch.sol#67) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaLaunch.sol:75: PleaLaunch.constructor(address,address,address,address,address,address,address,uint256,uint256,address,bool,bytes32).oracleAsset_ (src/PleaLaunch.sol#75) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaHook.sol:193: PleaHook.constructor(IPoolManager,address,IERC20,IStacker,address,address,uint256).owner_ (src/PleaHook.sol#193) lacks a zero-check on :\n[low/medium] missing-zero-check at src/PleaHook.sol:190: PleaHook.constructor(IPoolManager,address,IERC20,IStacker,address,address,uint256).plea_ (src/PleaHook.sol#190) lacks a zero-check on :\n[low/medium] calls-loop at src/Seasons.sol:297: Seasons._tryRecord(uint256) (src/Seasons.sol#297-304) has external calls inside a loop: (seller,score,approved,verdictAt) = gate.result(pleaId) (src/Seasons.sol#299)\n[low/medium] calls-loop at src/Seasons.sol:330: Seasons._payBonus(uint256,Seasons.Entry[10]) (src/Seasons.sol#330-350) has external calls inside a loop: (ok,ret) = address(token).call(abi.encodeCall(IERC20.transfer,(t[i].wallet,amount))) (src/Seasons.sol#336)\n[low/medium] calls-loop at src/Seasons.sol:160: Seasons._seasonOf(uint64) (src/Seasons.sol#160-162) has external calls inside a loop: (uint256(verdictAt) - gate.startedAt()) / SEASON (src/Seasons.sol#161)\n[low/medium] calls-loop at src/Seasons.sol:353: Seasons._pay(address,uint256) (src/Seasons.sol#353-356) has external calls inside a loop: (ok,ret) = address(imd).call(abi.encodeCall(IERC20.transfer,(to,amount))) (src/Seasons.sol#354)\n[low/medium] calls-loop at src/Seasons.sol:297: Seasons._tryRecord(uint256) (src/Seasons.sol#297-304) has external calls inside a loop: ! approved || seller == plea.owner() (src/Seasons.sol#300)\n[low/medium] reentrancy-benign at src/PleaHook.sol:365: Reentrancy in PleaHook.seed() (src/PleaHook.sol#365-407):\n[low/medium] reentrancy-benign at src/PleaHook.sol:556: Reentrancy in PleaHook._payFees(address,bool,uint256,uint256,uint256) (src/PleaHook.sol#556-601):\n[low/medium] reentrancy-benign at src/Letterbox.sol:377: Reentrancy in Letterbox._settle(uint256) (src/Letterbox.sol#377-397):\n[low/medium] reentrancy-benign at src/CabalGate.sol:416: Reentrancy in CabalGate._ask(uint256) (src/CabalGate.sol#416-431):\n[low/medium] reentrancy-benign at src/PleaHook.sol:876: Reentrancy in PleaHook._closeWall() (src/PleaHook.sol#876-893):\n[low/medium] reentrancy-benign at src/PleaHook.sol:365: Reentrancy in PleaHook.seed() (src/PleaHook.sol#365-407):\n[low/medium] reentrancy-benign at src/PleaHook.sol:473: Reentrancy in PleaHook.afterSwap(address,PoolKey,SwapParams,BalanceDelta,bytes) (src/PleaHook.sol#473-549):\n[low/medium] reentrancy-benign at src/PleaHook.sol:473: Reentrancy in PleaHook.afterSwap(address,PoolKey,SwapParams,BalanceDelta,bytes) (src/PleaHook.sol#473-549):\n[low/medium] reentrancy-benign at src/Seasons.sol:256: Reentrancy in Seasons.flushToWall() (src/Seasons.sol#256-274):\n[low/medium] reentrancy-benign at src/Letterbox.sol:345: Reentrancy in Letterbox._deliver(uint256,address) (src/Letterbox.sol#345-368):\n[low/medium] reentrancy-benign at src/CabalGate.sol:373: Reentrancy in CabalGate._payAppeal(uint256) (src/CabalGate.sol#373-379):\n[low/medium] reentrancy-benign at src/PleaHook.sol","passed":true},{"durationMs":1359,"exitCode":0,"name":"aderyn","output":"[high] abi-encode-packed-hash-collision at src/PleaLaunch.sol:91: `abi.encodePacked()` Hash Collision\n[high] reentrancy-state-change at src/CabalGate.sol:193: Reentrancy: State change after external call (17 places)\n[high] storage-array-memory-edit at src/PleaHook.sol:307: Storage Array Edited with Memory (3 places)\n[high] unsafe-casting at src/CabalGate.sol:402: Unsafe Casting of integers (2 places)\n[low] centralization-risk at src/PLEA.sol:14: Centralization Risk (4 places)\n[low] costly-loop at src/Seasons.sol:211: Costly operations inside loop (2 places)\n[low] internal-function-used-once at src/OracleAttestation.sol:206: Internal Function Used Only Once\n[low] large-numeric-literal at src/CabalGate.sol:254: Large Numeric Literal (11 places)\n[low] literal-instead-of-constant at src/CabalGate.sol:254: Literal Instead of Constant (115 places)\n[low] missing-inheritance at src/PleaHook.sol:35: Missing Inheritance (3 places)\n[low] require-revert-in-loop at src/CabalGate.sol:751: Loop Contains `require`/`revert` (4 places)\n[low] state-change-without-event at src/CabalGate.sol:613: State Change Without Event (4 places)\n[low] unchecked-return at src/CabalGate.sol:643: Unchecked Return (7 places)\n[low] uninitialized-local-variable at src/Letterbox.sol:234: Uninitialized Local Variable (9 places)\n[low] unsafe-erc20-operation at src/PleaHook.sol:724: Unsafe ERC20 Operation (3 places)\n[low] unused-import at src/PleaLaunch.sol:4: Unused Import (3 places)\n[low] unused-public-function at src/CabalGate.sol:213: Public Function Not Used Internally (8 places)\n[low] unused-state-variable at src/PLEA.sol:29: Unused State Variable (5 places)","passed":true}],"detail":"all checks passed","evaluation":"checks","profile":"foundry","status":"accepted","submissionHash":"1e3abc010d97d3551c9d686a6f162a62105e6d52dd80160ee243f544b5154b28","verifiedTreeHash":"13bb23b6567fa949b772e7b7e5c1659e9d8f9d34","verifierVersion":"0.1.0+327e1e9f"},{"checks":[{"durationMs":384025,"exitCode":0,"name":"build","output":"Compiling 152 files with Solc 0.8.26\nSolc 0.8.26 finished in 383.84s\nCompiler run successful with warnings:\nWarning (2018): Function state mutability can be restricted to pure\n   --> src/CabalGate.sol:706:5:\n    |\n706 |     function _text(string storage t, bool json) internal view returns (string memory) {\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\n","passed":true},{"durationMs":8643,"exitCode":0,"name":"test","output":"No files changed, compilation skipped\n\nRan 1 test for test/fork/ForkTestnet.t.sol:ForkTestnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 1.13ms (0.00ns CPU time)\n\nRan 16 tests for test/SeasonFunds.t.sol:SeasonFundsTest\n[PASS] testFuzz_lateCloseConservesAssets(uint96,uint96,bool) (runs: 32, μ: 1010284, ~: 970679)\n[PASS] test_bonusIsMintedToSeasonsAndCannotBeWithdrawn() (gas: 24077)\n[PASS] test_bonusPaysTheTopTenAndBurnsTheUnpaidShares() (gas: 1265441)\n[PASS] test_claimRedemptionCallbackCannotBeInvokedOutsideUnlock() (gas: 75348)\n[PASS] test_deathAtBoundaryFlushesClaimsAndLateDonationsOnce() (gas: 1582716)\n[PASS] test_deathBeforeTheSixthSeasonBurnsTheRest() (gas: 909477)\n[PASS] test_deathMidSeasonPreservesEarlierSeasonFees() (gas: 1364594)\n[PASS] test_emptySeasonBurnsItsWholeBonus() (gas: 210361)\n[PASS] test_failedBonusTransferIsBurnedNotStuck() (gas: 584544)\n[PASS] test_failedPayoutRollsForwardWithoutBlockingOtherWinners() (gas: 1302002)\n[PASS] test_feeAtBoundaryBelongsToNextSeason() (gas: 985296)\n[PASS] test_flushBeforeTheEndCannotTouchTheBonus() (gas: 43338)\n[PASS] test_lateClosesOnlyRollUnpaidSharesForward() (gas: 2057793)\n[PASS] test_onlyTheFirstSixSeasonsPayABonus() (gas: 3725664)\n[PASS] test_prizePleaStaysGatedWhileTheCabalWatches() (gas: 650344)\n[PASS] test_unobservedDonationCannotFlowBackwards() (gas: 895448)\nSuite result: ok. 16 passed; 0 failed; 0 skipped; finished in 18.57ms (16.89ms CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:OwnerExclusionTest\n[PASS] test_nobodyGetsAKeeperTip() (gas: 486471)\n[PASS] test_ownerPleasEarnNoPoints() (gas: 4972130)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 23.39ms (1.02ms CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:LetterboxMainnetPathTest\n[PASS] test_letterBuysTheOracleFeeAndTheTipWithPlea() (gas: 9213648)\n[PASS] test_mintingTheFeeIsRefusedOnMainnet() (gas: 733988)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 25.16ms (2.18ms CPU time)\n\nRan 4 tests for test/Token.t.sol:TokenTest\n[PASS] test_distributorAndAllowlistMaySend() (gas: 213606)\n[PASS] test_freeForeverOnceTheCabalDies() (gas: 184114)\n[PASS] test_launcherAndInitAreOneShot() (gas: 127121)\n[PASS] test_walletsCannotSendWhileTheCabalWatches() (gas: 331572)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 39.18ms (768.26µs CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12782094)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12715392)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9320559)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8539202)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9346550)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8182546)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8442182)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 51.16ms (14.89ms CPU time)\n\nRan 6 tests for test/DistributorAdversarial.t.sol:DistributorAdversarialTest\n[PASS] testFuzz_modifiedLeafOrProofCannotRedirectFunds(uint8,uint8,uint256) (runs: 256, μ: 259272, ~: 259209)\n[PASS] test_claimsCrossBitmapWordsAndCannotBeClaimedTwice() (gas: 1724610)\n[PASS] test_failedTokenTransferRollsBackBitmapAndCanBeRetried() (gas: 317232)\n[PASS] test_fullAllocationAndZeroAmountLeavesDoNotCorruptAdjacentBits() (gas: 260500)\n[PASS] test_rootCannotChangeAfterCommitmentEvenBeforeFirstClaim() (gas: 115955)\n[PASS] test_unsetRootAndUnauthorizedRootDoNotConsumeClaims() (gas: 276001)\nSuite result: ok. 6 passed; 0 failed; 0 skipped; finished in 35.99ms (34.68ms CPU time)\n\nRan 1 test for test/fork/ForkMainnet.t.sol:ForkMainnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 405.60µs (0.00ns CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:AtomicManifestTest\n[PASS] test_factoryDeploysExactManifestOnAnEmptySepoliaChain() (gas: 50242067)\nLogs:\n  five-contract launch transaction gas through IMD's factory: 12652544\n  gas limit with IMD's headroom: 15436103\n  margin to the 16,777,216 cap: 1341113\n\n[PASS] test_launchJsonCommitsToThisLetterbox() (gas: 31298)\n[PASS] test_launchJsonEncodesOracleMintFlagAsStaticWord() (gas: 10484)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 63.49ms (59.85ms CPU time)\n\nRan 12 tests for test/TraderResolution.t.sol:TraderResolutionTest\n[PASS] testFuzz_dirtyHookDataFallsBackToRouterCaller(uint96,bool) (runs: 32, μ: 710090, ~: 719305)\n[PASS] test_dirtyHookDataAfterDeathBuyHasNoTrader() (gas: 482078)\n[PASS] test_dirtyHookDataFallsBackToRouterCallerWhileAlive() (gas: 718951)\n[PASS] test_dirtyHookDataWithoutFallbackWhileAliveRequiresRecipient() (gas: 82148)\n[PASS] test_feeSurplusWithoutATraderIsBurnedOrKeptForThePool() (gas: 520853)\n[PASS] test_hookDataNamesTheTrader() (gas: 673932)\n[PASS] test_invalidHookDataFallsBackToTheRouterCaller() (gas: 2690957)\n[PASS] test_noTraderAfterDeathBuyGoesThroughWithoutCashback() (gas: 440515)\n[PASS] test_noTraderAfterDeathSellGoesThroughWithoutCashback() (gas: 522336)\n[PASS] test_routerCallerIsTheTraderWithoutHookData() (gas: 696907)\n[PASS] test_routerCallerStillCreditedAfterDeath() (gas: 629432)\n[PASS] test_routerWithoutMsgSenderNeedsHookDataWhileTheCabalLives() (gas: 149373)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 70.42ms (29.48ms CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedPaidFeeTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12726109)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12659407)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9283912)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8527902)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9309902)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8171246)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8430882)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 71.07ms (20.93ms CPU time)\n\nRan 2 tests for test/LaunchManifest.t.sol:PostLaunchTest\n[PASS] test_committedHookDeploysLaterAndMintsOnlyTheFixedSplit() (gas: 135922104)\n[PASS] test_committedLetterboxDeploysLater() (gas: 9913801)\nLogs:\n  deployLetterbox transaction gas: 5136020\n\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 77.58ms (70.53ms CPU time)\n\nRan 11 tests for test/Seasons.t.sol:FastClockTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4792795)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236713)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 1072222)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 41914330)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 1127942)\n[PASS] test_fastFullCycle() (gas: 77173420)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13521)\n[PASS] test_onlyApprovedPleasScore() (gas: 4902188)\n[PASS] test_secondSeasonScoresSeparately() (gas: 47202409)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 2261085)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 117706280)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 81.81ms (53.03ms CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:RehearsalManifestTest\n[PASS] test_laterBlockCannotRegisterLauncher() (gas: 13266059)\n[PASS] test_separateConstructorCallsInDeploymentBlockStillWork() (gas: 14183820)\n[PASS] test_separateTransactionsLeaveTheAcceptedDeploymentBlockWindow() (gas: 13400445)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 6.28ms (4.16ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeePleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9262301, ~: 9267965)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 85.37ms (79.43ms CPU time)\n\nRan 29 tests for test/Gate.t.sol:GateTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340238)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886515)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803827)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826287)\n[PASS] test_callbackFitsTheStipend() (gas: 7822839)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096040)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277015)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791432)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762349)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614957)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684709)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730745)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465765)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754199)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817153)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 29 passed; 0 failed; 0 skipped; finished in 41.38ms (20.68ms CPU time)\n\nRan 26 tests for test/Letterbox.t.sol:LetterboxTest\n[PASS] testFuzz_namesAreUniqueIdempotentAndReleasedOnClear(uint256,uint8) (runs: 32, μ: 322807, ~: 320039)\n[PASS] test_aBareCommandWordIsNotAPlea() (gas: 5966436)\n[PASS] test_aLapsedApprovalSettlesAndStillCounts() (gas: 5501137)\n[PASS] test_anyoneDeliversAnApprovalForTheTip() (gas: 6123174)\n[PASS] test_appealByLetterKeepsTheOriginalShareAndPaysTheWall() (gas: 10183024)\n[PASS] test_appealLetterRetriesAnAppealTheOracleNeverAnswered() (gas: 21400328)\n[PASS] test_autoSellFeeOnlyOnASaleAndNeverMoreThanHalfOfIt() (gas: 9745542)\n[PASS] test_deadCabalRefusesLettersButSettles() (gas: 5338963)\n[PASS] test_deliverNeedsAnApprovalInsideTheWindowAndTheMinimum() (gas: 6096229)\n[PASS] test_deployLetterboxRefusesOtherCode() (gas: 5287739)\n[PASS] test_expiredPendingPleaSettlesAfterTwentyMinutes() (gas: 5206752)\n[PASS] test_explorerLetterIsTheSameAsARawLetter() (gas: 13547986)\n[PASS] test_invalidNamesAndFailedRenamesPreserveTheOldReservation() (gas: 1334827)\n[PASS] test_leaderboardListsTheSeason() (gas: 6192745)\n[PASS] test_letterCommandsParse() (gas: 8817636)\n[PASS] test_letterPleadsTenPercentPaysFeesInPleaAndEscrows() (gas: 5289498)\n[PASS] test_letterRefusesEthTinyBalancesAndBadText() (gas: 1387704)\n[PASS] test_letterboxIsDeployedOnceFromTheCommittedCode() (gas: 482774)\n[PASS] test_noFunctionIdCanStartALetter() (gas: 835480)\n[PASS] test_noVerdictSettlesAtOnceAndTheNextLetterSettlesTheOldOne() (gas: 8643144)\n[PASS] test_settleReturnsEscrowAndTipAfterADenial() (gas: 5561375)\n[PASS] test_siteAutoSellPleadsAnyValidAmount() (gas: 10121890)\n[PASS] test_statusTellsEachState() (gas: 10135603)\n[PASS] test_strangersCannotUseTheCourtEntryPoints() (gas: 210957)\n[PASS] test_theGateRefusesAManualSaleOfAnEscrowedPlea() (gas: 5296061)\n[PASS] test_theSellLetterIsTheWritersOwnSale() (gas: 6016985)\nSuite result: ok. 26 passed; 0 failed; 0 skipped; finished in 80.39ms (50.07ms CPU time)\n\nRan 19 tests for test/Hook.t.sol:HookTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697442)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294753)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571808)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103571)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819702)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764200)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249359)\nSuite result: ok. 19 passed; 0 failed; 0 skipped; finished in 110.89ms (90.26ms CPU time)\n\nRan 12 tests for test/AuditRun3.t.sol:AuditRun3Test\n[PASS] test_F1_appealLetterCannotRetryAnAppealTheOracleNeverAnswered() (gas: 16420906)\n[PASS] test_F2_aCapSizedAutoSellPleaCannotBeAppealedThroughTheLetterbox() (gas: 33480907)\n[PASS] test_F3_aBareCommandWordBecomesAPaidPlea() (gas: 112574)\n[PASS] test_aLetterboxDeployedByAnyoneElseHasNoPowers() (gas: 5737587)\n[PASS] test_autoSellCannotAcceptASpotPriceUnderTheSnapshotFloor() (gas: 6742997)\n[PASS] test_escrowsAfterTheCabalDies() (gas: 12786705)\n[PASS] test_feeSaleIsBoundedAndTheTipReturns() (gas: 5225357)\n[PASS] test_letterParsingEdgeCases() (gas: 21094806)\n[PASS] test_markerRuleUnchanged() (gas: 6340228)\n[PASS] test_oneCapSizedSaleMovesSpotUnderOnePercent() (gas: 26980332)\nLogs:\n  price impact of a 2.5M PLEA sale, bps: 80\n\n[PASS] test_oracleBodyIsValidJsonForHostileTexts() (gas: 26155768)\n[PASS] test_priceViewsEqualAFullRingScan() (gas: 47483779)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 120.03ms (96.07ms CPU time)\n\nRan 30 tests for test/Orientation.t.sol:GatePleaIsZeroTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340260)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886537)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803849)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826309)\n[PASS] test_callbackFitsTheStipend() (gas: 7822861)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096062)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277037)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791454)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762371)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_orientationIsPleaZero() (gas: 15922)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614979)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684731)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730767)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465787)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754221)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817175)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 30 passed; 0 failed; 0 skipped; finished in 49.53ms (30.15ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9295790, ~: 9301963)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 126.63ms (89.77ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeeTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9261800, ~: 9267965)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 149.59ms (112.04ms CPU time)\n\nRan 5 tests for test/SeasonRanking.t.sol:SeasonRankingTest\n[PASS] testFuzz_rankingsMatchSortedResultsInAnyRecordOrder(uint256) (runs: 32, μ: 10578925, ~: 10572455)\n[PASS] test_closeSeasonUsesTheSameTiesForPrizes() (gas: 948987)\n[PASS] test_earlierEqualScoreCanReplaceACountedPleaWithoutChangingPoints() (gas: 737882)\n[PASS] test_replacingALowerScoreRemovesItsIdFromTheTieKey() (gas: 738576)\n[PASS] test_walletTieUsesNewestCountedPleaNotLastRecordedPlea() (gas: 775525)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 165.57ms (164.97ms CPU time)\n\nRan 6 tests for test/TraderResolverBoundary.t.sol:TraderResolverBoundaryTest\n[PASS] testFuzz_malformedVaultDiscoveryDoesNotRevertOrTruncate(uint8,uint96) (runs: 256, μ: 163888, ~: 159148)\n[PASS] test_missingRevertingAndZeroVaultDiscoveryAllowsDeployment() (gas: 564113)\n[PASS] test_namedContractWalletIsAcceptedWhenItIsNotTheRouter() (gas: 21054)\n[PASS] test_plainWalletFallbackUsesSenderAndNeverTransactionOrigin() (gas: 62439)\n[PASS] test_plainWalletInfrastructureIsExcludedEvenWithoutCode() (gas: 45858)\n[PASS] test_vaultAddressIsCachedAndIsNotReadAgainDuringResolution() (gas: 169436)\nSuite result: ok. 6 passed; 0 failed; 0 skipped; finished in 95.97ms (94.30ms CPU time)\n\nRan 10 tests for test/TraderFallbackAdversarial.t.sol:TraderFallbackAdversarialPleaZeroTest\n[PASS] testFuzz_dirtyRouterReturnCannotBeTruncatedIntoATrader(uint96,bool) (runs: 128, μ: 444200, ~: 291653)\n[PASS] testFuzz_nonAddressLengthHookDataFallsBackToRouter(uint8) (runs: 128, μ: 791103, ~: 790862)\n[PASS] testFuzz_nonAddressLengthResponsesDoNotResolve(uint8,bool) (runs: 128, μ: 422383, ~: 301254)\n[PASS] test_everyExcludedRouterResponseHasNoRecipientFallbackToOrigin() (gas: 4998907)\n[PASS] test_gateSaleAlwaysNamesSellerEvenWhenRelayedByLetterboxRunner() (gas: 6608480)\n[PASS] test_hookDataTakesPriorityEvenWhenRouterCannotAnswer() (gas: 2651759)\n[PASS] test_msgSenderReceivesExactlyTheThirtyThousandGasBudget() (gas: 804099)\n[PASS] test_partialBuyWithoutTraderKeepsBothCashbackAndImdFeeSurplusForPool() (gas: 1270574)\n[PASS] test_revertingOutOfGasAndStateWritingRoutersCannotBlockDeadCabalBuys() (gas: 2066973)\n[PASS] test_successThenUnresolvedThenNewTraderDoesNotLeakTransientIdentity() (gas: 1621370)\nSuite result: ok. 10 passed; 0 failed; 0 skipped; finished in 171.49ms (157.97ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4130895, ~: 4135969)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11955070)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2078725)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046909)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12106289)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576732)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2173128)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13474309)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1053405)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10100131)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240662)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8792122)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 173.76ms (177.93ms CPU time)\n\nRan 11 tests for test/Orientation.t.sol:SeasonsPleaIsZeroTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793343)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236802)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471961)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905035)\n[PASS] test_orientationIsPleaZero() (gas: 15724)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814485)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816570)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 70.27ms (50.62ms CPU time)\n\nRan 10 tests for test/TraderFallbackAdversarial.t.sol:TraderFallbackAdversarialTest\n[PASS] testFuzz_dirtyRouterReturnCannotBeTruncatedIntoATrader(uint96,bool) (runs: 128, μ: 444477, ~: 291665)\n[PASS] testFuzz_nonAddressLengthHookDataFallsBackToRouter(uint8) (runs: 128, μ: 791474, ~: 791233)\n[PASS] testFuzz_nonAddressLengthResponsesDoNotResolve(uint8,bool) (runs: 128, μ: 423020, ~: 301266)\n[PASS] test_everyExcludedRouterResponseHasNoRecipientFallbackToOrigin() (gas: 5001297)\n[PASS] test_gateSaleAlwaysNamesSellerEvenWhenRelayedByLetterboxRunner() (gas: 6608551)\n[PASS] test_hookDataTakesPriorityEvenWhenRouterCannotAnswer() (gas: 2653596)\n[PASS] test_msgSenderReceivesExactlyTheThirtyThousandGasBudget() (gas: 804470)\n[PASS] test_partialBuyWithoutTraderKeepsBothCashbackAndImdFeeSurplusForPool() (gas: 1272271)\n[PASS] test_revertingOutOfGasAndStateWritingRoutersCannotBlockDeadCabalBuys() (gas: 2068662)\n[PASS] test_successThenUnresolvedThenNewTraderDoesNotLeakTransientIdentity() (gas: 1622640)\nSuite result: ok. 10 passed; 0 failed; 0 skipped; finished in 194.66ms (170.55ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1147985, ~: 1142701)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196572)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653721)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 134604)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64100)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309863)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2555263)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 462551)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290623)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601944)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 201.61ms (187.52ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialPleaZeroTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1148079, ~: 1142863)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196880)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653449)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 135432)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64040)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309347)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2554435)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 466981)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290599)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601256)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 216.59ms (204.87ms CPU time)\n\nRan 3 tests for test/HookAdversarial.t.sol:LaunchFeeBoundaryTest\n[PASS] testFuzz_launchFeeOnlyFallsWithTime(uint256,uint256) (runs: 256, μ: 23995, ~: 24133)\n[PASS] test_largeLaunchBuyRollsBackAndSucceedsAtWindowEnd() (gas: 730740)\n[PASS] test_launchFeeHasExactStartMidpointAndEndValues() (gas: 43067)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 19.24ms (6.31ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionPleaZeroTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4129261, ~: 4133461)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11954633)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2079681)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046221)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12105852)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576295)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2172992)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13472092)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1052581)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10098966)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240213)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8791685)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 173.29ms (161.30ms CPU time)\n\nRan 4 tests for test/OracleConformance.t.sol:OracleConformanceTest\n[PASS] test_callbackSelectorHasTheProtocolStruct() (gas: 748)\n[PASS] test_digestMatchesTheProtocol() (gas: 10527)\n[PASS] test_liveAttestationRecoversToOracleSigner() (gas: 146604)\n[PASS] test_protocolSignatureRecoversToVectorSigner() (gas: 13943)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 961.31µs (496.02µs CPU time)\n\nRan 20 tests for test/Orientation.t.sol:HookPleaIsZeroTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697464)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294775)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571830)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103593)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_orientationIsPleaZero() (gas: 15910)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819724)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764243)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249381)\nSuite result: ok. 20 passed; 0 failed; 0 skipped; finished in 123.23ms (105.47ms CPU time)\n\nRan 5 tests for test/Launch.t.sol:LaunchTest\n[PASS] test_deployHookChecksTheInitCodeAndFlags() (gas: 84639443)\n[PASS] test_eachStepFitsAMainnetTransaction() (gas: 88788260)\nLogs:\n  launch (5 contracts + intake mock): 1248530\n  deployLetterbox: 4774223\n  deployHook: 5607943\n  seed: 598464\n\n[PASS] test_launchWiresEverythingWithoutCallingOutside() (gas: 1320309)\n[PASS] test_ownerMaySeedEarly() (gas: 83866858)\n[PASS] test_seedByOwnerAnyTimeByAnyoneAfterStart() (gas: 83965685)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 149.50ms (200.53ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9296312, ~: 9302078)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 112.53ms (104.04ms CPU time)\n\nRan 3 tests for test/OracleReplay.t.sol:OracleReplayTest\n[PASS] testFuzz_oneSignedRequestCannotSettleTwoPleas(bool,bool) (runs: 32, μ: 7935414, ~: 7943865)\n[PASS] test_deniedRequestCannotBeResignedToApproveItsAppeal() (gas: 8285757)\n[PASS] test_invalidCallbackDoesNotConsumeTheRequest() (gas: 7780529)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 56.48ms (37.14ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 265.83ms (161.52ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsPleaZeroTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 355.28ms (219.56ms CPU time)\n\nRan 10 tests for test/Seasons.t.sol:SeasonsTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793321)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236691)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471939)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905013)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814463)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816548)\nSuite result: ok. 10 passed; 0 failed; 0 skipped; finished in 427.54ms (77.69ms CPU time)\n\nRan 7 tests for test/SeasonAdversarial.t.sol:SeasonAdversarialTest\n[PASS] testFuzz_failedPrizeDoesNotBlockOthersAndUnpaidShareReachesWall(bool) (runs: 256, μ: 1821800, ~: 1820869)\n[PASS] testFuzz_prizeRoundingConservesAnOddSizedPot(uint256) (runs: 256, μ: 4910930, ~: 4925839)\n[PASS] test_batchIgnoresUnknownDeniedAndRepeatedIdsButCannotReopenASeason() (gas: 1061724)\n[PASS] test_closeBeforeGraceRollsBackItsBatchRecording() (gas: 634562)\n[PASS] test_flushBeforeFinalCloseCannotMoveAnyFunds() (gas: 553044)\n[PASS] test_prizesRequireSixtyPoints() (gas: 1262699)\n[PASS] test_recordRejectsDenialsDuplicatesAndLateApprovals() (gas: 813836)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 449.23ms (448.97ms CPU time)\n\nRan 12 tests for test/HookRevision.t.sol:HookRevisionPleaIsZeroTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 32, μ: 1314307, ~: 1314387)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 32, μ: 2555347, ~: 2570946)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 32, μ: 5206339, ~: 5206388)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 32, μ: 2706917, ~: 2709741)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 32, μ: 4186240, ~: 4356317)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 32, μ: 2142228, ~: 2133322)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 32, μ: 3147674, ~: 3270016)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 32, μ: 2253457, ~: 2263864)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594904)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848319)\n[PASS] test_orientationIsPleaZero() (gas: 15668)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117392)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 260.15ms (627.59ms CPU time)\n\nRan 11 tests for test/BonusInvariant.t.sol:BonusEdgeTest\n[PASS] testFuzz_anyRankingPaysPlusBurnsExactlyTheBonus(uint256) (runs: 512, μ: 3375533, ~: 3247080)\n[PASS] test_bonusPaidAfterDeathIsFreelyTransferable() (gas: 694020)\n[PASS] test_closeWithinTheGraceHourIsRefused() (gas: 656998)\n[PASS] test_closingTwiceCannotPayASeasonsBonusTwice() (gas: 648680)\n[PASS] test_deathBeforeTradingSeasonZeroEndsBurnsEverythingButSeasonZero() (gas: 817416)\n[PASS] test_eleventhWalletIsNotPaidAndCannotDisplaceRankTen() (gas: 4437034)\n[PASS] test_gateAsSellerForfeitsWhileWatchedButIsPaidAfterDeath() (gas: 1187960)\n[PASS] test_lateApprovalListedAtCloseStillEarnsTheBonus() (gas: 616880)\n[PASS] test_onlyTheBestThreePleasCount() (gas: 1540529)\n[PASS] test_sixtyPointsQualifiesFiftyNineDoesNot() (gas: 1286951)\n[PASS] test_tenQualifiersReceiveTheWholeBonusAndNothingBurns() (gas: 4183387)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 378.34ms (384.27ms CPU time)\n\nRan 5 tests for test/GasPass.t.sol:GasPassTest\n[PASS] testFuzz_bodyEqualsEscapingTheWholeQuestion(uint256) (runs: 500, μ: 5575669, ~: 5596723)\n[PASS] testFuzz_textCheckMatchesTheOldRules(uint256) (runs: 5000, μ: 876535, ~: 83943)\n[PASS] test_bodyEqualsEscapingTheWholeQuestion() (gas: 12832911)\n[PASS] test_priceViewsMatchAFullScan() (gas: 128851660)\n[PASS] test_textCheckEdgeCases() (gas: 53621558)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 497.64ms (918.30ms CPU time)\n\nRan 18 tests for test/GateAdversarial.t.sol:GateAdversarialTest\n[PASS] testFuzz_panelAndAnswerValidationCannotConsumeRequests(uint8) (runs: 256, μ: 4954946, ~: 4957679)\n[PASS] testFuzz_printablePleaRoundTripsThroughQuestionJson(uint256,uint16) (runs: 256, μ: 5049863, ~: 4974263)\n[PASS] testFuzz_signedQuorumMustBeReached(uint16,bool) (runs: 256, μ: 5044137, ~: 5055058)\n[PASS] test_aWhaleCanStillPleadTheMaximum() (gas: 5227666)\n[PASS] test_amountLimitsFailBeforeChargingAndOnePercentIsTheMinimum() (gas: 4977182)\n[PASS] test_appealIsAcceptedAtItsLastSecondAndCannotBeStolen() (gas: 8193866)\n[PASS] test_appealOracleFeeFailureRollsBackWallFundingAndOriginalFlag() (gas: 8695669)\n[PASS] test_approvedWindowOnlyClearsAfterTheLastSecond() (gas: 7922615)\n[PASS] test_changingSignedAnswerOrConsumerChainInvalidatesSignature() (gas: 4978232)\n[PASS] test_deadManExpiresAtTheExactSecondAndNeverAcceptsANewVerdict() (gas: 4874288)\n[PASS] test_denialCooldownEndsExactlyAtFourHours() (gas: 7699273)\n[PASS] test_futureIssuanceAndExpiredAttestationsRejectAtExactBoundaries() (gas: 7892452)\n[PASS] test_gateUnlockCallbackCannotBeInvokedOutsideItsOwnSale() (gas: 88179)\n[PASS] test_latePendingCannotConsumeSignatureOrExtendHeartbeat() (gas: 4863973)\n[PASS] test_malformedUtf8AndHiddenControlsFailWithoutCharging() (gas: 958224)\n[PASS] test_missingSellAllowanceDoesNotConsumeTheApprovedPlea() (gas: 4979060)\n[PASS] test_pendingAndExecutionDeadlinesAreInclusive() (gas: 5395699)\n[PASS] test_slippageRevertRestoresApprovalSupplyAndAllFeeState() (gas: 6050183)\nSuite result: ok. 18 passed; 0 failed; 0 skipped; finished in 612.99ms (897.92ms CPU time)\n\nRan 11 tests for test/HookRevision.t.sol:HookRevisionTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 64, μ: 1314138, ~: 1314045)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 64, μ: 2526844, ~: 2565010)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 64, μ: 5206340, ~: 5206389)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 64, μ: 2706903, ~: 2709737)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 64, μ: 3971086, ~: 3661445)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 64, μ: 2142570, ~: 2133345)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 64, μ: 2811197, ~: 2742031)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 64, μ: 2248851, ~: 2237249)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594882)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848297)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117370)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 612.85ms (1.13s CPU time)\n\nRan 3 tests for test/GateFailureInvariant.t.sol:GateFailureInvariantTest\n[PASS]\nGateFailureInvariantTest invariants:\n[PASS] invariant_gateHoldsNothing\n[PASS] invariant_onlyVerdictsMoveTheClock\n[PASS] invariant_pendingBookkeepingIsConsistent\n GateFailureInvariantTest invariants (runs: 64, calls: 4096, reverts: 0)\n\n╭--------------------+---------------+-------+---------+----------╮\n| Contract           | Selector      | Calls | Reverts | Discards |\n+=================================================================+\n| GateFailureHandler | advance       | 464   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | answer        | 441   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | appeal        | 481   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | directFailure | 438   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | execute       | 447   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | expire        | 441   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | fail          | 461   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | plead         | 452   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | strangerFails | 471   | 0       | 0        |\n╰--------------------+---------------+-------+---------+----------╯\n\n[PASS] test_failureAfterDeathDoesNotReviveTheCabal() (gas: 4763614)\n[PASS] test_handlerReachesFailuresVerdictsAndAppeals() (gas: 18558972)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 961.14ms (941.43ms CPU time)\n\nRan 2 tests for test/BonusInvariant.t.sol:BonusInvariantTest\n[PASS]\nBonusInvariantTest invariants:\n[PASS] invariant_bonusIsHeldPaidOrBurned\n[PASS] invariant_flushedSeasonsStayFinished\n[PASS] invariant_openBonusSeasonsStayFunded\n[PASS] invariant_supplyFallsOnlyByTheBurnedBonus\n BonusInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭--------------+----------+-------+---------+----------╮\n| Contract     | Selector | Calls | Reverts | Discards |\n+======================================================+\n| BonusHandler | advance  | 1158  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | approve  | 1185  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | close    | 1144  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | die      | 1216  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | donate   | 1195  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | flush    | 1131  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | pull     | 1163  | 0       | 0        |\n╰--------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesPaidClosesDeathAndFlush() (gas: 2140371)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 1.50s (1.50s CPU time)\n\nRan 1 test for test/DistributorAdversarial.t.sol:DistributionInvariantTest\n[PASS]\nDistributionInvariantTest invariants:\n[PASS] invariant_deathAndSystemWiringArePermanent\n[PASS] invariant_distributorPaysEachCommittedLeafAtMostOnce\n[PASS] invariant_supplyEqualsAllBalancesAndOnlyBurnsReduceIt\n DistributionInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------------+----------------------------+-------+---------+----------╮\n| Contract            | Selector                   | Calls | Reverts | Discards |\n+===============================================================================+\n| DistributionHandler | advance                    | 978   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | allowSender                | 1012  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | approveAndSpend            | 1042  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | burnTokens                 | 972   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | claimAllocation            | 1030  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | donate                     | 1074  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | transferTokens             | 1043  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | unauthorizedAdministration | 1041  | 0       | 0        |\n╰---------------------+----------------------------+-------+---------+----------╯\n\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 1.73s (1.72s CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxInvariantTest\n[PASS]\nLetterboxInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 594   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 597   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 529   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 546   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 544   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 577   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 588   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 549   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 596   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26112427)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.36s (2.34s CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxMainnetInvariantTest\n[PASS]\nLetterboxMainnetInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxMainnetInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 594   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 597   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 529   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 546   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 544   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 577   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 588   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 549   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 596   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26017407)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.44s (2.42s CPU time)\n\nRan 4 tests for test/OwnershipTransitionInvariant.t.sol:OwnershipTransitionInvariantTest\n[PASS]\nOwnershipTransitionInvariantTest invariants:\n[PASS] invariant_onlyAcceptedTransfersChangeOwnerOrAllowlistAuthority\n[PASS] invariant_ownershipChangesCannotMoveOrDuplicateCustodiedPrizes\n OwnershipTransitionInvariantTest invariants (runs: 256, calls: 16384, reverts: 0)\n\n╭----------------------------+-------------+-------+---------+----------╮\n| Contract                   | Selector    | Calls | Reverts | Discards |\n+=======================================================================+\n| OwnershipTransitionHandler | accept      | 4069  | 0       | 0        |\n|----------------------------+-------------+-------+---------+----------|\n| OwnershipTransitionHandler | allow       | 4077  | 0       | 0        |\n|----------------------------+-------------+-------+---------+----------|\n| OwnershipTransitionHandler | closePrizes | 4108  | 0       | 0        |\n|----------------------------+-------------+-------+---------+----------|\n| OwnershipTransitionHandler | nominate    | 4130  | 0       | 0        |\n╰----------------------------+-------------+-------+---------+----------╯\n\n[PASS] test_cancelledNomineeCannotAcceptAndBothLeadersKeepTheirPrizes() (gas: 870144)\n[PASS] test_renounceClearsNominationAndDoesNotLetFormerNomineeClaimAuthority() (gas: 1096278)\n[PASS] test_replacedNomineeCannotAcceptAndNewOwnerAloneLosesTheirPrize() (gas: 1135097)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 2.51s (2.51s CPU time)\n\nRan 2 tests for test/TraderAttributionInvariant.t.sol:TraderAttributionInvariantPleaZeroTest\n[PASS]\nTraderAttributionInvariantPleaZeroTest invariants:\n[PASS] invariant_infrastructureNeverReceivesTraderCredit\n[PASS] invariant_supplyAndPoolReserveRemainBacked\n[PASS] invariant_tokensAndBuyRecordsFollowTheirIndependentRecipients\n TraderAttributionInvariantPleaZeroTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭--------------------------+------------+-------+---------+----------╮\n| Contract                 | Selector   | Calls | Reverts | Discards |\n+====================================================================+\n| TraderAttributionHandler | advance    | 2674  | 0       | 0        |\n|--------------------------+------------+-------+---------+----------|\n| TraderAttributionHandler | buy        | 2759  | 0       | 0        |\n|--------------------------+------------+-------+---------+----------|\n| TraderAttributionHandler | pauseVault | 2759  | 0       | 0        |\n╰--------------------------+------------+-------+---------+----------╯\n\n[PASS] test_handlerExercisesFallbacksDeathAndPlainCashback() (gas: 4083353)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.72s (2.71s CPU time)\n\nRan 2 tests for test/TraderAttributionInvariant.t.sol:TraderAttributionInvariantTest\n[PASS]\nTraderAttributionInvariantTest invariants:\n[PASS] invariant_infrastructureNeverReceivesTraderCredit\n[PASS] invariant_supplyAndPoolReserveRemainBacked\n[PASS] invariant_tokensAndBuyRecordsFollowTheirIndependentRecipients\n TraderAttributionInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭--------------------------+------------+-------+---------+----------╮\n| Contract                 | Selector   | Calls | Reverts | Discards |\n+====================================================================+\n| TraderAttributionHandler | advance    | 2674  | 0       | 0        |\n|--------------------------+------------+-------+---------+----------|\n| TraderAttributionHandler | buy        | 2759  | 0       | 0        |\n|--------------------------+------------+-------+---------+----------|\n| TraderAttributionHandler | pauseVault | 2759  | 0       | 0        |\n╰--------------------------+------------+-------+---------+----------╯\n\n[PASS] test_handlerExercisesFallbacksDeathAndPlainCashback() (gas: 4085377)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.84s (2.82s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingPleaZeroInvariantTest\n[PASS]\nTradingPleaZeroInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingPleaZeroInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 713   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 788   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 734   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 733   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 743   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 743   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 748   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 730   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 774   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 750   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 736   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2944481, ~: 2955251)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9141711)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.83s (3.90s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingInvariantTest\n[PASS]\nTradingInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 713   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 788   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 734   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 733   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 743   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 743   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 748   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 730   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 774   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 750   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 736   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2945297, ~: 2956067)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9136901)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.86s (3.90s CPU time)\n\nRan 3 tests for test/SeasonInvariant.t.sol:SeasonInvariantTest\n[PASS]\nSeasonInvariantTest invariants:\n[PASS] invariant_prizeMoneyIsPaidOnceOrRemainsInThePotOrWall\n[PASS] invariant_rankingsMatchAllRecordedApprovalsAndClosedSeasonsNeverChange\n SeasonInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------+-------------------------+-------+---------+----------╮\n| Contract      | Selector                | Calls | Reverts | Discards |\n+======================================================================+\n| SeasonHandler | advance                 | 825   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | approvePlea             | 802   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | checkpoint              | 788   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | closeOldest             | 793   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donate                  | 799   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateClaims            | 806   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateWithoutCheckpoint | 799   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | endCabal                | 870   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | flush                   | 854   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | record                  | 856   | 0       | 0        |\n╰---------------+-------------------------+-------+---------+----------╯\n\n[PASS] test_modelCoversDelayedDonationsAndPostFlushClaims() (gas: 3620935)\n[PASS] test_modelCoversPayableClosesRolloverAndFinalFlush() (gas: 4324339)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 8.48s (8.48s CPU time)\n\nRan 57 test suites in 8.49s (40.35s CPU time): 441 tests passed, 0 failed, 2 skipped (443 total tests)\n","passed":true},{"durationMs":124,"exitCode":0,"name":"source-index","output":"{\"v\":1,\"entryPoints\":[\"CabalGate.appeal(uint256,uint256,string)\",\"CabalGate.appealFor(address,uint256,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.begin()\",\"CabalGate.executeSell(uint256)\",\"CabalGate.executeSellFor(uint256,uint256)\",\"CabalGate.expire(uint256)\",\"CabalGate.onOracleResult(bytes32,(bytes32,uint256,bytes32,uint8,bytes,uint256,uint64,uint64,bytes32,bytes32,uint16,uint16,uint16,uint64,uint64),bytes)\",\"CabalGate.onPleaFailure(bytes32,uint8,bytes32,uint16,uint16,bytes)\",\"CabalGate.submitFor(address,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.submitSell(uint256,string)\",\"CabalGate.unlockCallback(bytes)\",\"Letterbox.appealAuto(uint256,string)\",\"Letterbox.deliver(uint256)\",\"Letterbox.fallback()\",\"Letterbox.letter(string)\",\"Letterbox.plead(uint256,string)\",\"Letterbox.setName(string)\",\"Letterbox.settle(uint256)\",\"PLEA.acceptOwnership()\",\"PLEA.allow(address)\",\"PLEA.approve(address,uint256)\",\"PLEA.burn(uint256)\",\"PLEA.courtTake(address,uint256)\",\"PLEA.init(address,address)\",\"PLEA.renounceOwnership()\",\"PLEA.setLauncher(address,address,address)\",\"PLEA.setLetterbox(address)\",\"PLEA.transfer(address,uint256)\",\"PLEA.transferFrom(address,address,uint256)\",\"PLEA.transferOwnership(address)\",\"PleaDistributor.claim(uint256,address,uint256,bytes32[])\",\"PleaDistributor.renounceOwnership()\",\"PleaDistributor.setMerkleRoot(bytes32)\",\"PleaDistributor.transferOwnership(address)\",\"PleaHook.afterSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),int256,bytes)\",\"PleaHook.beforeSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),bytes)\",\"PleaHook.fundWall(uint256)\",\"PleaHook.rebalance()\",\"PleaHook.seed()\",\"PleaHook.unlockCallback(bytes)\",\"PleaLaunch.deployHook(bytes32,bytes)\",\"PleaLaunch.deployLetterbox(bytes)\",\"PleaLaunch.seed()\",\"Seasons.checkpoint()\",\"Seasons.closeSeason(uint256[])\",\"Seasons.flushToWall()\",\"Seasons.record(uint256)\",\"Seasons.unlockCallback(bytes)\"],\"files\":{\".gitignore\":4,\"ADAPTATION.md\":35,\"README.md\":269,\"foundry.toml\":25,\"launch.json\":56,\"remappings.txt\":4,\"script/Deploy.s.sol\":55,\"script/DeployLetterbox.s.sol\":22,\"script/MineSalt.s.sol\":44,\"src/CabalGate.sol\":817,\"src/Letterbox.sol\":669,\"src/OracleAttestation.sol\":227,\"src/PLEA.sol\":151,\"src/PleaDistributor.sol\":49,\"src/PleaHook.sol\":1062,\"src/PleaLaunch.sol\":152,\"src/Seasons.sol\":357,\"src/interfaces/IPleaParts.sol\":74,\"src/interfaces/IStacker.sol\":12,\"test/AppealRounding.t.sol\":140,\"test/AuditImported.t.sol\":142,\"test/AuditRevision.t.sol\":277,\"test/AuditRun3.t.sol\":391,\"test/BonusInvariant.t.sol\":526,\"test/DistributorAdversarial.t.sol\":329,\"test/GasPass.t.sol\":329,\"test/Gate.t.sol\":408,\"test/GateAdversarial.t.sol\":400,\"test/GateFailureInvariant.t.sol\":330,\"test/Hook.t.sol\":357,\"test/HookAdversarial.t.sol\":256,\"test/HookRevision.t.sol\":378,\"test/JudgeFindings.t.sol\":193,\"test/Launch.t.sol\":156,\"test/LaunchManifest.t.sol\":317,\"test/Letterbox.t.sol\":752,\"test/LetterboxInvariant.t.sol\":441,\"test/OracleConformance.t.sol\":114,\"test/OracleReplay.t.sol\":60,\"test/Orientation.t.sol\":58,\"test/OwnershipTransitionInvariant.t.sol\":229,\"test/SeasonAdversarial.t.sol\":203,\"test/SeasonFunds.t.sol\":343,\"test/SeasonInvariant.t.sol\":341,\"test/SeasonRanking.t.sol\":168,\"test/Seasons.t.sol\":266,\"test/Token.t.sol\":78,\"test/TraderAttributionInvariant.t.sol\":287,\"test/TraderFallbackAdversarial.t.sol\":307,\"test/TraderResolution.t.sol\":207,\"test/TraderResolverBoundary.t.sol\":126,\"test/TradingInvariant.t.sol\":476,\"test/fork/ForkMainnet.t.sol\":368,\"test/fork/ForkTestnet.t.sol\":765,\"test/utils/AdversarialTraderRouter.sol\":38,\"test/utils/ClaimTree.sol\":41,\"test/utils/Fixture.sol\":238,\"test/utils/Mocks.sol\":324,\"test/utils/SeasonModel.sol\":117,\"test/utils/SepoliaFixture.sol\":34},\"excluded\":[\"lib/\",\"node_modules/\"],\"truncated\":false}","passed":true}],"detail":"all checks passed","evaluation":"checks","profile":"foundry","status":"accepted","submissionHash":"bae94b55764a2f56bca851063241110f166ef53b35caa69f7c939f890bea2015","verifiedTreeHash":"41bc41c55610f193c66d18640ebcbbe30ddd6af0","verifierVersion":"0.1.0+327e1e9f"},{"checks":[{"durationMs":342981,"exitCode":0,"name":"build","output":"Compiling 147 files with Solc 0.8.26\nSolc 0.8.26 finished in 342.83s\nCompiler run successful with warnings:\nWarning (2018): Function state mutability can be restricted to pure\n   --> src/CabalGate.sol:706:5:\n    |\n706 |     function _text(string storage t, bool json) internal view returns (string memory) {\n    |     ^ (Relevant source part starts here and spans across multiple lines).\n\n","passed":true},{"durationMs":8758,"exitCode":0,"name":"test","output":"No files changed, compilation skipped\n\nRan 4 tests for test/OracleConformance.t.sol:OracleConformanceTest\n[PASS] test_callbackSelectorHasTheProtocolStruct() (gas: 748)\n[PASS] test_digestMatchesTheProtocol() (gas: 10527)\n[PASS] test_liveAttestationRecoversToOracleSigner() (gas: 146604)\n[PASS] test_protocolSignatureRecoversToVectorSigner() (gas: 13943)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 2.11ms (828.15µs CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:RehearsalManifestTest\n[PASS] test_laterBlockCannotRegisterLauncher() (gas: 13266059)\n[PASS] test_separateConstructorCallsInDeploymentBlockStillWork() (gas: 14183820)\n[PASS] test_separateTransactionsLeaveTheAcceptedDeploymentBlockWindow() (gas: 13400445)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 15.79ms (15.64ms CPU time)\n\nRan 4 tests for test/Token.t.sol:TokenTest\n[PASS] test_distributorAndAllowlistMaySend() (gas: 213606)\n[PASS] test_freeForeverOnceTheCabalDies() (gas: 184114)\n[PASS] test_launcherAndInitAreOneShot() (gas: 127121)\n[PASS] test_walletsCannotSendWhileTheCabalWatches() (gas: 331572)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 21.59ms (474.88µs CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:OwnerExclusionTest\n[PASS] test_nobodyGetsAKeeperTip() (gas: 486471)\n[PASS] test_ownerPleasEarnNoPoints() (gas: 4972130)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 24.34ms (1.10ms CPU time)\n\nRan 2 tests for test/Letterbox.t.sol:LetterboxMainnetPathTest\n[PASS] test_letterBuysTheOracleFeeAndTheTipWithPlea() (gas: 9213648)\n[PASS] test_mintingTheFeeIsRefusedOnMainnet() (gas: 733988)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 27.67ms (2.68ms CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedPaidFeeTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12726109)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12659407)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9283912)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8527902)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9309902)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8171246)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8430882)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 42.97ms (12.45ms CPU time)\n\nRan 3 tests for test/OracleReplay.t.sol:OracleReplayTest\n[PASS] testFuzz_oneSignedRequestCannotSettleTwoPleas(bool,bool) (runs: 32, μ: 7930479, ~: 7921324)\n[PASS] test_deniedRequestCannotBeResignedToApproveItsAppeal() (gas: 8285757)\n[PASS] test_invalidCallbackDoesNotConsumeTheRequest() (gas: 7780529)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 53.65ms (34.42ms CPU time)\n\nRan 30 tests for test/Orientation.t.sol:GatePleaIsZeroTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340260)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886537)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803849)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826309)\n[PASS] test_callbackFitsTheStipend() (gas: 7822861)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096062)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277037)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791454)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762371)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_orientationIsPleaZero() (gas: 15922)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614979)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684731)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730767)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465787)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754221)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817175)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 30 passed; 0 failed; 0 skipped; finished in 55.86ms (30.99ms CPU time)\n\nRan 12 tests for test/TraderResolution.t.sol:TraderResolutionTest\n[PASS] testFuzz_dirtyHookDataFallsBackToRouterCaller(uint96,bool) (runs: 32, μ: 706241, ~: 694728)\n[PASS] test_dirtyHookDataAfterDeathBuyHasNoTrader() (gas: 482078)\n[PASS] test_dirtyHookDataFallsBackToRouterCallerWhileAlive() (gas: 718951)\n[PASS] test_dirtyHookDataWithoutFallbackWhileAliveRequiresRecipient() (gas: 82148)\n[PASS] test_feeSurplusWithoutATraderIsBurnedOrKeptForThePool() (gas: 520853)\n[PASS] test_hookDataNamesTheTrader() (gas: 673932)\n[PASS] test_invalidHookDataFallsBackToTheRouterCaller() (gas: 2690957)\n[PASS] test_noTraderAfterDeathBuyGoesThroughWithoutCashback() (gas: 440515)\n[PASS] test_noTraderAfterDeathSellGoesThroughWithoutCashback() (gas: 522336)\n[PASS] test_routerCallerIsTheTraderWithoutHookData() (gas: 696907)\n[PASS] test_routerCallerStillCreditedAfterDeath() (gas: 629432)\n[PASS] test_routerWithoutMsgSenderNeedsHookDataWhileTheCabalLives() (gas: 149373)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 47.24ms (19.96ms CPU time)\n\nRan 6 tests for test/DistributorAdversarial.t.sol:DistributorAdversarialTest\n[PASS] testFuzz_modifiedLeafOrProofCannotRedirectFunds(uint8,uint8,uint256) (runs: 256, μ: 259328, ~: 259279)\n[PASS] test_claimsCrossBitmapWordsAndCannotBeClaimedTwice() (gas: 1724610)\n[PASS] test_failedTokenTransferRollsBackBitmapAndCanBeRetried() (gas: 317232)\n[PASS] test_fullAllocationAndZeroAmountLeavesDoNotCorruptAdjacentBits() (gas: 260500)\n[PASS] test_rootCannotChangeAfterCommitmentEvenBeforeFirstClaim() (gas: 115955)\n[PASS] test_unsetRootAndUnauthorizedRootDoNotConsumeClaims() (gas: 276001)\nSuite result: ok. 6 passed; 0 failed; 0 skipped; finished in 59.48ms (44.32ms CPU time)\n\nRan 3 tests for test/LaunchManifest.t.sol:AtomicManifestTest\n[PASS] test_factoryDeploysExactManifestOnAnEmptySepoliaChain() (gas: 50242067)\nLogs:\n  five-contract launch transaction gas through IMD's factory: 12652544\n  gas limit with IMD's headroom: 15436103\n  margin to the 16,777,216 cap: 1341113\n\n[PASS] test_launchJsonCommitsToThisLetterbox() (gas: 31360)\n[PASS] test_launchJsonEncodesOracleMintFlagAsStaticWord() (gas: 10530)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 60.33ms (58.37ms CPU time)\n\nRan 1 test for test/fork/ForkMainnet.t.sol:ForkMainnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 455.61µs (0.00ns CPU time)\n\nRan 1 test for test/fork/ForkTestnet.t.sol:ForkTestnetTest\n[SKIP: skipped] setUp() (gas: 0)\nSuite result: ok. 0 passed; 0 failed; 1 skipped; finished in 475.97µs (0.00ns CPU time)\n\nRan 7 tests for test/AuditImported.t.sol:AuditImportedTest\n[PASS] test_appealLetterRetriesCompletedRequestWithFailedCallback() (gas: 12782094)\n[PASS] test_appealLetterRetriesLazyTimeoutWithoutSeparateSettlement() (gas: 12715392)\n[PASS] test_autoAppealSurvivesBalanceGrowth() (gas: 9320559)\n[PASS] test_growingBalanceDoesNotEnableDustOrLargerAppeals() (gas: 8539202)\n[PASS] test_rawAppealLetterSurvivesBalanceGrowth() (gas: 9346550)\n[PASS] test_shrinkingBalanceStillUsesCurrentMinimumAndMaximum() (gas: 8182546)\n[PASS] test_siteAppealSurvivesBalanceGrowthAtOriginalMinimum() (gas: 8442182)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 66.55ms (16.06ms CPU time)\n\nRan 2 tests for test/LaunchManifest.t.sol:PostLaunchTest\n[PASS] test_committedHookDeploysLaterAndMintsOnlyTheFixedSplit() (gas: 135922104)\n[PASS] test_committedLetterboxDeploysLater() (gas: 9913801)\nLogs:\n  deployLetterbox transaction gas: 5136020\n\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 69.64ms (64.73ms CPU time)\n\nRan 16 tests for test/SeasonFunds.t.sol:SeasonFundsTest\n[PASS] testFuzz_lateCloseConservesAssets(uint96,uint96,bool) (runs: 32, μ: 1019036, ~: 1006793)\n[PASS] test_bonusIsMintedToSeasonsAndCannotBeWithdrawn() (gas: 24077)\n[PASS] test_bonusPaysTheTopTenAndBurnsTheUnpaidShares() (gas: 1265441)\n[PASS] test_claimRedemptionCallbackCannotBeInvokedOutsideUnlock() (gas: 75348)\n[PASS] test_deathAtBoundaryFlushesClaimsAndLateDonationsOnce() (gas: 1582716)\n[PASS] test_deathBeforeTheSixthSeasonBurnsTheRest() (gas: 909477)\n[PASS] test_deathMidSeasonPreservesEarlierSeasonFees() (gas: 1364594)\n[PASS] test_emptySeasonBurnsItsWholeBonus() (gas: 210361)\n[PASS] test_failedBonusTransferIsBurnedNotStuck() (gas: 584544)\n[PASS] test_failedPayoutRollsForwardWithoutBlockingOtherWinners() (gas: 1302002)\n[PASS] test_feeAtBoundaryBelongsToNextSeason() (gas: 985296)\n[PASS] test_flushBeforeTheEndCannotTouchTheBonus() (gas: 43338)\n[PASS] test_lateClosesOnlyRollUnpaidSharesForward() (gas: 2057793)\n[PASS] test_onlyTheFirstSixSeasonsPayABonus() (gas: 3725664)\n[PASS] test_prizePleaStaysGatedWhileTheCabalWatches() (gas: 650344)\n[PASS] test_unobservedDonationCannotFlowBackwards() (gas: 895448)\nSuite result: ok. 16 passed; 0 failed; 0 skipped; finished in 13.40ms (19.41ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeePleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9260276, ~: 9259942)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 98.18ms (90.44ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9294725, ~: 9301847)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 107.86ms (79.37ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPaidFeeTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9261321, ~: 9267938)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9345940)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9251319)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27594939)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 118.04ms (84.77ms CPU time)\n\nRan 11 tests for test/Seasons.t.sol:FastClockTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4792795)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236713)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 1072222)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 41914330)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 1127942)\n[PASS] test_fastFullCycle() (gas: 77173420)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13521)\n[PASS] test_onlyApprovedPleasScore() (gas: 4902188)\n[PASS] test_secondSeasonScoresSeparately() (gas: 47202409)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 2261085)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 117706280)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 118.69ms (76.74ms CPU time)\n\nRan 20 tests for test/Orientation.t.sol:HookPleaIsZeroTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697464)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294775)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571830)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103593)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_orientationIsPleaZero() (gas: 15910)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819724)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764243)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249381)\nSuite result: ok. 20 passed; 0 failed; 0 skipped; finished in 105.60ms (93.85ms CPU time)\n\nRan 4 tests for test/AppealRounding.t.sol:AppealRoundingPleaZeroTest\n[PASS] testFuzz_minimumPleaAppealsThroughEveryLetterEntry(uint8,uint8) (runs: 32, μ: 9295299, ~: 9301936)\n[PASS] test_cappedMinimumSitePleaCanAppealAfterFeeSale() (gas: 9382593)\n[PASS] test_minimumSitePleaCanAppealAfterFeeSaleRounding() (gas: 9285316)\n[PASS] test_shareBandsAndFiftyPercentClampKeepTheirExistingRounding() (gas: 27696930)\nSuite result: ok. 4 passed; 0 failed; 0 skipped; finished in 127.99ms (111.69ms CPU time)\n\nRan 5 tests for test/SeasonRanking.t.sol:SeasonRankingTest\n[PASS] testFuzz_rankingsMatchSortedResultsInAnyRecordOrder(uint256) (runs: 32, μ: 10552766, ~: 10538974)\n[PASS] test_closeSeasonUsesTheSameTiesForPrizes() (gas: 948987)\n[PASS] test_earlierEqualScoreCanReplaceACountedPleaWithoutChangingPoints() (gas: 737882)\n[PASS] test_replacingALowerScoreRemovesItsIdFromTheTieKey() (gas: 738576)\n[PASS] test_walletTieUsesNewestCountedPleaNotLastRecordedPlea() (gas: 775525)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 162.14ms (163.00ms CPU time)\n\nRan 3 tests for test/HookAdversarial.t.sol:LaunchFeeBoundaryTest\n[PASS] testFuzz_launchFeeOnlyFallsWithTime(uint256,uint256) (runs: 256, μ: 24011, ~: 24133)\n[PASS] test_largeLaunchBuyRollsBackAndSucceedsAtWindowEnd() (gas: 730740)\n[PASS] test_launchFeeHasExactStartMidpointAndEndValues() (gas: 43067)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 20.95ms (6.91ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4129846, ~: 4132433)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11955070)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2078725)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046909)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12106289)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576732)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2173128)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13474309)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1053405)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10100131)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240662)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8792122)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 178.49ms (182.55ms CPU time)\n\nRan 12 tests for test/AuditRevision.t.sol:AuditRevisionPleaZeroTest\n[PASS] testFuzz_cumulativeCapDecayStaysWithinElapsedBudget(uint256) (runs: 32, μ: 4130773, ~: 4135293)\n[PASS] test_appealRetryClearsTimedOutPendingAppeal() (gas: 11954633)\n[PASS] test_deadCabalBuyWithoutARecipientSkipsTheCashback() (gas: 2079681)\n[PASS] test_dustBuyDoesNotGiveUntrackedTokensLossOrHoldingPoints() (gas: 1046221)\n[PASS] test_expiredAppealCanBeRetriedWithoutLiftingDenialCooldown() (gas: 12105852)\n[PASS] test_lapsedApprovalCannotBypassCooldown() (gas: 8576295)\n[PASS] test_largeBuyClaimsAreRedeemableAndNextBuyStacksNormally() (gas: 2172992)\n[PASS] test_lateCloseDoesNotPayFutureSeasonFees() (gas: 13472092)\n[PASS] test_sameSecondCapRatchetsCannotReuseFractionalBudget() (gas: 1052581)\n[PASS] test_seasonClaimsArePaidAsImdAtClose() (gas: 10098966)\n[PASS] test_secondLargeBuyPreservesEveryPayee() (gas: 1240213)\n[PASS] test_unansweredAppealDoesNotExtendTheOriginalWindow() (gas: 8791685)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 186.83ms (179.37ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1147357, ~: 1142615)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196572)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653721)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 134604)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64100)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309863)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2555263)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 462551)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290623)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601944)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 191.21ms (185.21ms CPU time)\n\nRan 26 tests for test/Letterbox.t.sol:LetterboxTest\n[PASS] testFuzz_namesAreUniqueIdempotentAndReleasedOnClear(uint256,uint8) (runs: 32, μ: 321348, ~: 316815)\n[PASS] test_aBareCommandWordIsNotAPlea() (gas: 5966436)\n[PASS] test_aLapsedApprovalSettlesAndStillCounts() (gas: 5501137)\n[PASS] test_anyoneDeliversAnApprovalForTheTip() (gas: 6123174)\n[PASS] test_appealByLetterKeepsTheOriginalShareAndPaysTheWall() (gas: 10183024)\n[PASS] test_appealLetterRetriesAnAppealTheOracleNeverAnswered() (gas: 21400328)\n[PASS] test_autoSellFeeOnlyOnASaleAndNeverMoreThanHalfOfIt() (gas: 9745542)\n[PASS] test_deadCabalRefusesLettersButSettles() (gas: 5338963)\n[PASS] test_deliverNeedsAnApprovalInsideTheWindowAndTheMinimum() (gas: 6096229)\n[PASS] test_deployLetterboxRefusesOtherCode() (gas: 5287739)\n[PASS] test_expiredPendingPleaSettlesAfterTwentyMinutes() (gas: 5206752)\n[PASS] test_explorerLetterIsTheSameAsARawLetter() (gas: 13547986)\n[PASS] test_invalidNamesAndFailedRenamesPreserveTheOldReservation() (gas: 1334827)\n[PASS] test_leaderboardListsTheSeason() (gas: 6192745)\n[PASS] test_letterCommandsParse() (gas: 8817636)\n[PASS] test_letterPleadsTenPercentPaysFeesInPleaAndEscrows() (gas: 5289498)\n[PASS] test_letterRefusesEthTinyBalancesAndBadText() (gas: 1387704)\n[PASS] test_letterboxIsDeployedOnceFromTheCommittedCode() (gas: 482774)\n[PASS] test_noFunctionIdCanStartALetter() (gas: 835480)\n[PASS] test_noVerdictSettlesAtOnceAndTheNextLetterSettlesTheOldOne() (gas: 8643144)\n[PASS] test_settleReturnsEscrowAndTipAfterADenial() (gas: 5561375)\n[PASS] test_siteAutoSellPleadsAnyValidAmount() (gas: 10121890)\n[PASS] test_statusTellsEachState() (gas: 10135603)\n[PASS] test_strangersCannotUseTheCourtEntryPoints() (gas: 210957)\n[PASS] test_theGateRefusesAManualSaleOfAnEscrowedPlea() (gas: 5296061)\n[PASS] test_theSellLetterIsTheWritersOwnSale() (gas: 6016985)\nSuite result: ok. 26 passed; 0 failed; 0 skipped; finished in 248.45ms (54.65ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 333.08ms (175.72ms CPU time)\n\nRan 11 tests for test/Orientation.t.sol:SeasonsPleaIsZeroTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793343)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236802)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471961)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905035)\n[PASS] test_orientationIsPleaZero() (gas: 15724)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814485)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816570)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 294.84ms (62.22ms CPU time)\n\nRan 11 tests for test/BonusInvariant.t.sol:BonusEdgeTest\n[PASS] testFuzz_anyRankingPaysPlusBurnsExactlyTheBonus(uint256) (runs: 512, μ: 3360449, ~: 3166370)\n[PASS] test_bonusPaidAfterDeathIsFreelyTransferable() (gas: 694020)\n[PASS] test_closeWithinTheGraceHourIsRefused() (gas: 656998)\n[PASS] test_closingTwiceCannotPayASeasonsBonusTwice() (gas: 648680)\n[PASS] test_deathBeforeTradingSeasonZeroEndsBurnsEverythingButSeasonZero() (gas: 817416)\n[PASS] test_eleventhWalletIsNotPaidAndCannotDisplaceRankTen() (gas: 4437034)\n[PASS] test_gateAsSellerForfeitsWhileWatchedButIsPaidAfterDeath() (gas: 1187960)\n[PASS] test_lateApprovalListedAtCloseStillEarnsTheBonus() (gas: 616880)\n[PASS] test_onlyTheBestThreePleasCount() (gas: 1540529)\n[PASS] test_sixtyPointsQualifiesFiftyNineDoesNot() (gas: 1286951)\n[PASS] test_tenQualifiersReceiveTheWholeBonusAndNothingBurns() (gas: 4183387)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 435.69ms (439.97ms CPU time)\n\nRan 18 tests for test/GateAdversarial.t.sol:GateAdversarialTest\n[PASS] testFuzz_panelAndAnswerValidationCannotConsumeRequests(uint8) (runs: 256, μ: 4954432, ~: 4957610)\n[PASS] testFuzz_printablePleaRoundTripsThroughQuestionJson(uint256,uint16) (runs: 256, μ: 4985142, ~: 4848020)\n[PASS] testFuzz_signedQuorumMustBeReached(uint16,bool) (runs: 256, μ: 5043884, ~: 5032726)\n[PASS] test_aWhaleCanStillPleadTheMaximum() (gas: 5227666)\n[PASS] test_amountLimitsFailBeforeChargingAndOnePercentIsTheMinimum() (gas: 4977182)\n[PASS] test_appealIsAcceptedAtItsLastSecondAndCannotBeStolen() (gas: 8193866)\n[PASS] test_appealOracleFeeFailureRollsBackWallFundingAndOriginalFlag() (gas: 8695669)\n[PASS] test_approvedWindowOnlyClearsAfterTheLastSecond() (gas: 7922615)\n[PASS] test_changingSignedAnswerOrConsumerChainInvalidatesSignature() (gas: 4978232)\n[PASS] test_deadManExpiresAtTheExactSecondAndNeverAcceptsANewVerdict() (gas: 4874288)\n[PASS] test_denialCooldownEndsExactlyAtFourHours() (gas: 7699273)\n[PASS] test_futureIssuanceAndExpiredAttestationsRejectAtExactBoundaries() (gas: 7892452)\n[PASS] test_gateUnlockCallbackCannotBeInvokedOutsideItsOwnSale() (gas: 88179)\n[PASS] test_latePendingCannotConsumeSignatureOrExtendHeartbeat() (gas: 4863973)\n[PASS] test_malformedUtf8AndHiddenControlsFailWithoutCharging() (gas: 958224)\n[PASS] test_missingSellAllowanceDoesNotConsumeTheApprovedPlea() (gas: 4979060)\n[PASS] test_pendingAndExecutionDeadlinesAreInclusive() (gas: 5395699)\n[PASS] test_slippageRevertRestoresApprovalSupplyAndAllFeeState() (gas: 6050183)\nSuite result: ok. 18 passed; 0 failed; 0 skipped; finished in 214.16ms (483.05ms CPU time)\n\nRan 10 tests for test/Seasons.t.sol:SeasonsTest\n[PASS] test_aLateCallbackCannotRevive() (gas: 4793321)\n[PASS] test_aliveFromSeedDeadAfterSilenceForever() (gas: 236691)\n[PASS] test_bestThreeCountAndTopTenOrder() (gas: 23471939)\n[PASS] test_closeSeasonPaysTheTopTen() (gas: 56577624)\n[PASS] test_deathEndsTheLastSeasonAndTheRestGoesToTheWall() (gas: 11792328)\n[PASS] test_mainnetGuardRefusesShortTimings() (gas: 13499)\n[PASS] test_onlyApprovedPleasScore() (gas: 4905013)\n[PASS] test_secondSeasonScoresSeparately() (gas: 44264367)\n[PASS] test_tenthPlaceIsEvictedByABetterWallet() (gas: 39814463)\n[PASS] test_verdictsKeepItAliveAcrossManySeasons() (gas: 111816548)\nSuite result: ok. 10 passed; 0 failed; 0 skipped; finished in 390.51ms (65.18ms CPU time)\n\nRan 12 tests for test/AuditRun3.t.sol:AuditRun3Test\n[PASS] test_F1_appealLetterCannotRetryAnAppealTheOracleNeverAnswered() (gas: 16420906)\n[PASS] test_F2_aCapSizedAutoSellPleaCannotBeAppealedThroughTheLetterbox() (gas: 33480907)\n[PASS] test_F3_aBareCommandWordBecomesAPaidPlea() (gas: 112574)\n[PASS] test_aLetterboxDeployedByAnyoneElseHasNoPowers() (gas: 5737587)\n[PASS] test_autoSellCannotAcceptASpotPriceUnderTheSnapshotFloor() (gas: 6742997)\n[PASS] test_escrowsAfterTheCabalDies() (gas: 12786705)\n[PASS] test_feeSaleIsBoundedAndTheTipReturns() (gas: 5225357)\n[PASS] test_letterParsingEdgeCases() (gas: 21094806)\n[PASS] test_markerRuleUnchanged() (gas: 6340228)\n[PASS] test_oneCapSizedSaleMovesSpotUnderOnePercent() (gas: 26980332)\nLogs:\n  price impact of a 2.5M PLEA sale, bps: 80\n\n[PASS] test_oracleBodyIsValidJsonForHostileTexts() (gas: 26155768)\n[PASS] test_priceViewsEqualAFullRingScan() (gas: 47483779)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 458.88ms (82.51ms CPU time)\n\nRan 7 tests for test/SeasonAdversarial.t.sol:SeasonAdversarialTest\n[PASS] testFuzz_failedPrizeDoesNotBlockOthersAndUnpaidShareReachesWall(bool) (runs: 256, μ: 1821822, ~: 1822746)\n[PASS] testFuzz_prizeRoundingConservesAnOddSizedPot(uint256) (runs: 256, μ: 4898607, ~: 4925839)\n[PASS] test_batchIgnoresUnknownDeniedAndRepeatedIdsButCannotReopenASeason() (gas: 1061724)\n[PASS] test_closeBeforeGraceRollsBackItsBatchRecording() (gas: 634562)\n[PASS] test_flushBeforeFinalCloseCannotMoveAnyFunds() (gas: 553044)\n[PASS] test_prizesRequireSixtyPoints() (gas: 1262699)\n[PASS] test_recordRejectsDenialsDuplicatesAndLateApprovals() (gas: 813836)\nSuite result: ok. 7 passed; 0 failed; 0 skipped; finished in 458.74ms (592.05ms CPU time)\n\nRan 12 tests for test/HookRevision.t.sol:HookRevisionPleaIsZeroTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 32, μ: 1314126, ~: 1313831)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 32, μ: 2490527, ~: 2452586)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 32, μ: 5206336, ~: 5206371)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 32, μ: 2706525, ~: 2703950)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 32, μ: 4014114, ~: 3661467)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 32, μ: 2149512, ~: 2160004)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 32, μ: 2665774, ~: 2693683)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 32, μ: 2243180, ~: 2236342)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594904)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848319)\n[PASS] test_orientationIsPleaZero() (gas: 15668)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117392)\nSuite result: ok. 12 passed; 0 failed; 0 skipped; finished in 356.17ms (666.11ms CPU time)\n\nRan 5 tests for test/JudgeFindings.t.sol:JudgeFindingsPleaZeroTest\n[PASS] test_aSmallWriterCanAppealByLetter() (gas: 7938613)\n[PASS] test_appealLetterKeepsTheOriginalShareBand() (gas: 7840266)\n[PASS] test_deliverAfterACrashCapsTheFeeAtTheSale() (gas: 377447390)\n[PASS] test_fiftyPercentCeilingAndShareBands() (gas: 3874994)\n[PASS] test_ownershipTransferNeedsAcceptanceSoALeaderKeepsThePrize() (gas: 6528289)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 480.80ms (230.04ms CPU time)\n\nRan 5 tests for test/GasPass.t.sol:GasPassTest\n[PASS] testFuzz_bodyEqualsEscapingTheWholeQuestion(uint256) (runs: 500, μ: 5586745, ~: 5617291)\n[PASS] testFuzz_textCheckMatchesTheOldRules(uint256) (runs: 5000, μ: 903056, ~: 84243)\n[PASS] test_bodyEqualsEscapingTheWholeQuestion() (gas: 12832911)\n[PASS] test_priceViewsMatchAFullScan() (gas: 128851660)\n[PASS] test_textCheckEdgeCases() (gas: 53621558)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 420.59ms (699.15ms CPU time)\n\nRan 29 tests for test/Gate.t.sol:GateTest\n[PASS] test_appealClosesAfterFourHoursAndOnlyOnce() (gas: 11340238)\n[PASS] test_appealWithinFourHoursForNoMore() (gas: 8886515)\n[PASS] test_approvedScoreOpensTheSellWindow() (gas: 5502541)\n[PASS] test_badAttestationsAreNotDelivered() (gas: 4803827)\n[PASS] test_bodyIsTheNumericPanelQuestion() (gas: 4826287)\n[PASS] test_callbackFitsTheStipend() (gas: 7822839)\nLogs:\n  approve callback gas: 58946\n  deny callback gas: 83545\n\n[PASS] test_callbackOnlyFromIntakeAndOnlyForAPendingPlea() (gas: 5338713)\n[PASS] test_cannotPassIsRefusedBeforePaying() (gas: 1180888)\n[PASS] test_cooldownAfterExecutedSell() (gas: 8096040)\n[PASS] test_failedAppealCanBeRetried() (gas: 11277015)\n[PASS] test_failureAfterExpireIsRefused() (gas: 4791432)\n[PASS] test_failureClearsThePendingPleaWithoutCooldownOrClock() (gas: 7668347)\n[PASS] test_failureFitsTheMainnetGas() (gas: 4762349)\n[PASS] test_failureForAnUnknownOrSettledRequestDoesNothing() (gas: 4934924)\n[PASS] test_failureOnlyFromTheIntake() (gas: 4730912)\n[PASS] test_noPleasWhileTheCabalSleeps() (gas: 56324)\n[PASS] test_noVerdictIsClearedAtOnceWhenTheIntakeCompletes() (gas: 7651530)\n[PASS] test_onePendingPleaPerWallet() (gas: 4714765)\n[PASS] test_pendingExpiresAfterTwentyMinutesAndLateCallbacksFail() (gas: 7614957)\n[PASS] test_pleaAsksWithTheFailureFunction() (gas: 4684709)\n[PASS] test_pleaPaysTheIntakeAndNamesTheCallback() (gas: 4730745)\n[PASS] test_prizePleaOnTopOfAWeekOldBuy() (gas: 1465765)\n[PASS] test_refusalClearsThePleaToo() (gas: 4784271)\n[PASS] test_scoreAboveRangeOrWrongTypeIsRefused() (gas: 7754199)\n[PASS] test_scoreBelowNeedDenies() (gas: 4977940)\n[PASS] test_sellWindowLapses() (gas: 7684442)\n[PASS] test_signerWithDelegationCodeStillVerifies() (gas: 4817153)\n[PASS] test_textFilter() (gas: 5167814)\n[PASS] test_wrongSignerIsRefused() (gas: 4781395)\nSuite result: ok. 29 passed; 0 failed; 0 skipped; finished in 256.83ms (23.51ms CPU time)\n\nRan 11 tests for test/HookAdversarial.t.sol:HookAdversarialPleaZeroTest\n[PASS] testFuzz_immediateRoundTripCannotProfitIncludingCashback(uint256) (runs: 256, μ: 1147517, ~: 1142825)\n[PASS] test_exactOutputBuyWorksAfterDeathAndKeepsAllAccountingSettled() (gas: 1196880)\n[PASS] test_firstPartialFillRefundIsBackedByRedeemableQuoteClaims() (gas: 653449)\n[PASS] test_hookCallbacksRejectCallersAndForeignPools() (gas: 135432)\n[PASS] test_onlyHookMayInitializeOrAddLiquidity() (gas: 64040)\n[PASS] test_partialFillRefundChargesOnlyRealizedImdAndKeepsCostBasisCorrect() (gas: 1309347)\n[PASS] test_realCreditBudgetMustBeAffordableAndExhaustedCreditFallsBack() (gas: 2554435)\n[PASS] test_rebalancePaysNoTipAndDeploysTheWholeReserve() (gas: 466981)\n[PASS] test_seedAndUnlockAreOneShotAndOnlyAuthorizedContextsWork() (gas: 138226)\n[PASS] test_wallFundingCannotCreateUnbackedReserveWhenTransferFails() (gas: 290599)\n[PASS] test_zeroBuyRevertsAndOneWeiBuyConservesSupply() (gas: 601256)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 391.14ms (386.18ms CPU time)\n\nRan 5 tests for test/Launch.t.sol:LaunchTest\n[PASS] test_deployHookChecksTheInitCodeAndFlags() (gas: 84639443)\n[PASS] test_eachStepFitsAMainnetTransaction() (gas: 88788260)\nLogs:\n  launch (5 contracts + intake mock): 1248530\n  deployLetterbox: 4774223\n  deployHook: 5607943\n  seed: 598464\n\n[PASS] test_launchWiresEverythingWithoutCallingOutside() (gas: 1320309)\n[PASS] test_ownerMaySeedEarly() (gas: 83866858)\n[PASS] test_seedByOwnerAnyTimeByAnyoneAfterStart() (gas: 83965685)\nSuite result: ok. 5 passed; 0 failed; 0 skipped; finished in 481.14ms (191.54ms CPU time)\n\nRan 11 tests for test/HookRevision.t.sol:HookRevisionTest\n[PASS] testFuzz_aGreedyStackerCannotReachTheWallReserve(uint256,uint256) (runs: 64, μ: 1314029, ~: 1313796)\n[PASS] testFuzz_aLimitAnywhereInTheLiquidityFreeRegionNeverMovesTheGuard(uint256,uint256) (runs: 64, μ: 2467825, ~: 2418877)\n[PASS] testFuzz_aLimitInsideTheLiquidMarketBandMovesTheGuardToTheStopTick(uint256) (runs: 64, μ: 5206315, ~: 5206349)\n[PASS] testFuzz_aSameHourPumpCannotMoveAPleasFactScore(uint256) (runs: 64, μ: 2706532, ~: 2703964)\n[PASS] testFuzz_repeatedDrainsToTheExtremeNeverMoveTheGuard(uint8) (runs: 64, μ: 3971069, ~: 3661445)\n[PASS] testFuzz_successfulCreditsNeverAccumulateAllowance(uint256,uint256,uint256) (runs: 64, μ: 2147982, ~: 2157719)\n[PASS] testFuzz_theGuardClimbsAtMost400TicksADay(uint256,uint256,uint8) (runs: 64, μ: 2759633, ~: 2654606)\n[PASS] testFuzz_theHoursFirstTradeRecordsThePriceItFoundWhateverItsSize(uint256,uint256) (runs: 64, μ: 2240168, ~: 2236320)\n[PASS] test_aCreditThatBurnsAllItsGasLeavesNoAllowance() (gas: 1594882)\n[PASS] test_anHourOpeningSellRecordsThePriceItFound() (gas: 1848297)\n[PASS] test_wallGuardFollowsASellThatStopsWhereTheMarketHasLiquidity() (gas: 6117370)\nSuite result: ok. 11 passed; 0 failed; 0 skipped; finished in 380.50ms (1.30s CPU time)\n\nRan 19 tests for test/Hook.t.sol:HookTest\n[PASS] test_aBuyMustAffordTheCredit() (gas: 1248084)\n[PASS] test_aSellAboveTheCapIsTrimmedAndBurned() (gas: 1697442)\n[PASS] test_avgBuyTimeIsBuyWeighted() (gas: 1106242)\n[PASS] test_capDecayIsSetSoTheFloorIsReachableIn25Days() (gas: 18018)\n[PASS] test_capFollowsBuysAtMostOneDayOfDecayPerDay() (gas: 1686366)\n[PASS] test_everyFeeIsPaidInTheSameSwap() (gas: 1294753)\n[PASS] test_factScoreUsesCheckpointsNotSpot() (gas: 1660765)\n[PASS] test_firstBuyWithAnEmptyPoolSendsPayoutsToLiquidity() (gas: 571808)\n[PASS] test_freeTradingWhenTheCabalSleeps() (gas: 1103571)\n[PASS] test_hourlyCheckpointIsNotSetByTheTradeThatOpensTheHour() (gas: 1931674)\n[PASS] test_plainImdOnlyWhenTheCreditReverts() (gas: 1201142)\n[PASS] test_rebalanceRedeemsClaimsIntoTheWall() (gas: 4564491)\n[PASS] test_sellsAndExactOutputOnlyThroughTheGateWhileAlive() (gas: 747994)\n[PASS] test_stackerIsApprovedOnlyForTheCashbackBeingCredited() (gas: 1819702)\n[PASS] test_wallGuardDropsAtOnceAndRisesFourPercentADay() (gas: 34363426)\n[PASS] test_wallGuardIgnoresASellerChosenLimitReachedThroughAnEmptyPool() (gas: 2789499)\n[PASS] test_wallGuardIgnoresTheEmptyPoolsPriceLimit() (gas: 2764200)\n[PASS] test_wallGuardLagsAPumpAndCapsTheWall() (gas: 16743433)\n[PASS] test_wallGuardStillDropsAtOnceToASellerChosenLimitInsideTheBand() (gas: 33249359)\nSuite result: ok. 19 passed; 0 failed; 0 skipped; finished in 429.80ms (118.80ms CPU time)\n\nRan 3 tests for test/GateFailureInvariant.t.sol:GateFailureInvariantTest\n[PASS]\nGateFailureInvariantTest invariants:\n[PASS] invariant_gateHoldsNothing\n[PASS] invariant_onlyVerdictsMoveTheClock\n[PASS] invariant_pendingBookkeepingIsConsistent\n GateFailureInvariantTest invariants (runs: 64, calls: 4096, reverts: 0)\n\n╭--------------------+---------------+-------+---------+----------╮\n| Contract           | Selector      | Calls | Reverts | Discards |\n+=================================================================+\n| GateFailureHandler | advance       | 483   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | answer        | 440   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | appeal        | 434   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | directFailure | 441   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | execute       | 478   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | expire        | 436   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | fail          | 479   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | plead         | 468   | 0       | 0        |\n|--------------------+---------------+-------+---------+----------|\n| GateFailureHandler | strangerFails | 437   | 0       | 0        |\n╰--------------------+---------------+-------+---------+----------╯\n\n[PASS] test_failureAfterDeathDoesNotReviveTheCabal() (gas: 4763614)\n[PASS] test_handlerReachesFailuresVerdictsAndAppeals() (gas: 18558972)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 831.75ms (812.39ms CPU time)\n\nRan 2 tests for test/BonusInvariant.t.sol:BonusInvariantTest\n[PASS]\nBonusInvariantTest invariants:\n[PASS] invariant_bonusIsHeldPaidOrBurned\n[PASS] invariant_flushedSeasonsStayFinished\n[PASS] invariant_openBonusSeasonsStayFunded\n[PASS] invariant_supplyFallsOnlyByTheBurnedBonus\n BonusInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭--------------+----------+-------+---------+----------╮\n| Contract     | Selector | Calls | Reverts | Discards |\n+======================================================+\n| BonusHandler | advance  | 1191  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | approve  | 1161  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | close    | 1174  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | die      | 1175  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | donate   | 1136  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | flush    | 1171  | 0       | 0        |\n|--------------+----------+-------+---------+----------|\n| BonusHandler | pull     | 1184  | 0       | 0        |\n╰--------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesPaidClosesDeathAndFlush() (gas: 2140371)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 1.34s (1.34s CPU time)\n\nRan 1 test for test/DistributorAdversarial.t.sol:DistributionInvariantTest\n[PASS]\nDistributionInvariantTest invariants:\n[PASS] invariant_deathAndSystemWiringArePermanent\n[PASS] invariant_distributorPaysEachCommittedLeafAtMostOnce\n[PASS] invariant_supplyEqualsAllBalancesAndOnlyBurnsReduceIt\n DistributionInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------------+----------------------------+-------+---------+----------╮\n| Contract            | Selector                   | Calls | Reverts | Discards |\n+===============================================================================+\n| DistributionHandler | advance                    | 1065  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | allowSender                | 1008  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | approveAndSpend            | 1054  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | burnTokens                 | 1046  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | claimAllocation            | 1039  | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | donate                     | 992   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | transferTokens             | 963   | 0       | 0        |\n|---------------------+----------------------------+-------+---------+----------|\n| DistributionHandler | unauthorizedAdministration | 1025  | 0       | 0        |\n╰---------------------+----------------------------+-------+---------+----------╯\n\nSuite result: ok. 1 passed; 0 failed; 0 skipped; finished in 1.69s (1.69s CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxMainnetInvariantTest\n[PASS]\nLetterboxMainnetInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxMainnetInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 545   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 557   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 638   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 535   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 572   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 551   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 579   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 556   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 587   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26017407)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.14s (2.12s CPU time)\n\nRan 2 tests for test/LetterboxInvariant.t.sol:LetterboxInvariantTest\n[PASS]\nLetterboxInvariantTest invariants:\n[PASS] invariant_escrowsMatchTheirPleas\n[PASS] invariant_everyWritersPleaIsAccountedFor\n[PASS] invariant_holdsExactlyTheOpenEscrowsAndTips\n[PASS] invariant_noStepBrokeAnExpectation\n LetterboxInvariantTest invariants (runs: 64, calls: 5120, reverts: 0)\n\n╭------------------+----------+-------+---------+----------╮\n| Contract         | Selector | Calls | Reverts | Discards |\n+==========================================================+\n| LetterboxHandler | advance  | 545   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | answer   | 557   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | appeal   | 638   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | deliver  | 535   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | fail     | 572   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | poke     | 551   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | sell     | 579   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | settle   | 556   | 0       | 0        |\n|------------------+----------+-------+---------+----------|\n| LetterboxHandler | write    | 587   | 0       | 0        |\n╰------------------+----------+-------+---------+----------╯\n\n[PASS] test_handlerReachesEveryPath() (gas: 26112427)\nSuite result: ok. 2 passed; 0 failed; 0 skipped; finished in 2.21s (2.17s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingInvariantTest\n[PASS]\nTradingInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 740   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 766   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 761   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 709   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 727   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 719   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 753   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 736   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 794   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 678   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 809   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2941983, ~: 2929557)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9136901)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.60s (3.63s CPU time)\n\nRan 3 tests for test/TradingInvariant.t.sol:TradingPleaZeroInvariantTest\n[PASS]\nTradingPleaZeroInvariantTest invariants:\n[PASS] invariant_allPleaIsAccountedForAndSupplyOnlyFallsByActualBurns\n[PASS] invariant_quoteConservationAndFeePaymentsMatchTheirCounters\n[PASS] invariant_stackerHoldsNoStandingAllowanceOnTheHooksImd\n[PASS] invariant_wallReservesClaimsAndGateStateRemainBacked\n TradingPleaZeroInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭----------------+---------------+-------+---------+----------╮\n| Contract       | Selector      | Calls | Reverts | Discards |\n+=============================================================+\n| TradingHandler | advance       | 740   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | buy           | 766   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | donateQuote   | 761   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | execute       | 709   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | freeSell      | 727   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | fundWall      | 719   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | pauseCashback | 753   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | rebalance     | 736   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | redeemClaims  | 794   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | submit        | 678   | 0       | 0        |\n|----------------+---------------+-------+---------+----------|\n| TradingHandler | verdict       | 809   | 0       | 0        |\n╰----------------+---------------+-------+---------+----------╯\n\n[PASS] testFuzz_handlerAccountsForClaimFeesAndTheirRedemption(bool) (runs: 32, μ: 2941167, ~: 2928741)\n[PASS] test_handlerExercisesTradingVerdictsRebalancesAndDeath() (gas: 9141711)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 3.62s (3.67s CPU time)\n\nRan 3 tests for test/SeasonInvariant.t.sol:SeasonInvariantTest\n[PASS]\nSeasonInvariantTest invariants:\n[PASS] invariant_prizeMoneyIsPaidOnceOrRemainsInThePotOrWall\n[PASS] invariant_rankingsMatchAllRecordedApprovalsAndClosedSeasonsNeverChange\n SeasonInvariantTest invariants (runs: 128, calls: 8192, reverts: 0)\n\n╭---------------+-------------------------+-------+---------+----------╮\n| Contract      | Selector                | Calls | Reverts | Discards |\n+======================================================================+\n| SeasonHandler | advance                 | 808   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | approvePlea             | 832   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | checkpoint              | 798   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | closeOldest             | 818   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donate                  | 849   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateClaims            | 865   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | donateWithoutCheckpoint | 806   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | endCabal                | 840   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | flush                   | 822   | 0       | 0        |\n|---------------+-------------------------+-------+---------+----------|\n| SeasonHandler | record                  | 754   | 0       | 0        |\n╰---------------+-------------------------+-------+---------+----------╯\n\n[PASS] test_modelCoversDelayedDonationsAndPostFlushClaims() (gas: 3620935)\n[PASS] test_modelCoversPayableClosesRolloverAndFinalFlush() (gas: 4324339)\nSuite result: ok. 3 passed; 0 failed; 0 skipped; finished in 8.54s (8.54s CPU time)\n\nRan 51 test suites in 8.61s (31.98s CPU time): 407 tests passed, 0 failed, 2 skipped (409 total tests)\n","passed":true},{"durationMs":154,"exitCode":0,"name":"source-index","output":"{\"v\":1,\"entryPoints\":[\"CabalGate.appeal(uint256,uint256,string)\",\"CabalGate.appealFor(address,uint256,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.begin()\",\"CabalGate.executeSell(uint256)\",\"CabalGate.executeSellFor(uint256,uint256)\",\"CabalGate.expire(uint256)\",\"CabalGate.onOracleResult(bytes32,(bytes32,uint256,bytes32,uint8,bytes,uint256,uint64,uint64,bytes32,bytes32,uint16,uint16,uint16,uint64,uint64),bytes)\",\"CabalGate.onPleaFailure(bytes32,uint8,bytes32,uint16,uint16,bytes)\",\"CabalGate.submitFor(address,uint256,uint256,string,uint8,uint256,uint256)\",\"CabalGate.submitSell(uint256,string)\",\"CabalGate.unlockCallback(bytes)\",\"Letterbox.appealAuto(uint256,string)\",\"Letterbox.deliver(uint256)\",\"Letterbox.fallback()\",\"Letterbox.letter(string)\",\"Letterbox.plead(uint256,string)\",\"Letterbox.setName(string)\",\"Letterbox.settle(uint256)\",\"PLEA.acceptOwnership()\",\"PLEA.allow(address)\",\"PLEA.approve(address,uint256)\",\"PLEA.burn(uint256)\",\"PLEA.courtTake(address,uint256)\",\"PLEA.init(address,address)\",\"PLEA.renounceOwnership()\",\"PLEA.setLauncher(address,address,address)\",\"PLEA.setLetterbox(address)\",\"PLEA.transfer(address,uint256)\",\"PLEA.transferFrom(address,address,uint256)\",\"PLEA.transferOwnership(address)\",\"PleaDistributor.claim(uint256,address,uint256,bytes32[])\",\"PleaDistributor.renounceOwnership()\",\"PleaDistributor.setMerkleRoot(bytes32)\",\"PleaDistributor.transferOwnership(address)\",\"PleaHook.afterSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),int256,bytes)\",\"PleaHook.beforeSwap(address,(address,address,uint24,int24,address),(bool,int256,uint160),bytes)\",\"PleaHook.fundWall(uint256)\",\"PleaHook.rebalance()\",\"PleaHook.seed()\",\"PleaHook.unlockCallback(bytes)\",\"PleaLaunch.deployHook(bytes32,bytes)\",\"PleaLaunch.deployLetterbox(bytes)\",\"PleaLaunch.seed()\",\"Seasons.checkpoint()\",\"Seasons.closeSeason(uint256[])\",\"Seasons.flushToWall()\",\"Seasons.record(uint256)\",\"Seasons.unlockCallback(bytes)\"],\"files\":{\".gitignore\":4,\"ADAPTATION.md\":35,\"README.md\":269,\"foundry.toml\":25,\"launch.json\":56,\"remappings.txt\":4,\"script/Deploy.s.sol\":55,\"script/DeployLetterbox.s.sol\":22,\"script/MineSalt.s.sol\":44,\"src/CabalGate.sol\":817,\"src/Letterbox.sol\":669,\"src/OracleAttestation.sol\":227,\"src/PLEA.sol\":151,\"src/PleaDistributor.sol\":49,\"src/PleaHook.sol\":1062,\"src/PleaLaunch.sol\":152,\"src/Seasons.sol\":357,\"src/interfaces/IPleaParts.sol\":74,\"src/interfaces/IStacker.sol\":12,\"test/AppealRounding.t.sol\":140,\"test/AuditImported.t.sol\":142,\"test/AuditRevision.t.sol\":277,\"test/AuditRun3.t.sol\":391,\"test/BonusInvariant.t.sol\":526,\"test/DistributorAdversarial.t.sol\":329,\"test/GasPass.t.sol\":329,\"test/Gate.t.sol\":408,\"test/GateAdversarial.t.sol\":400,\"test/GateFailureInvariant.t.sol\":330,\"test/Hook.t.sol\":357,\"test/HookAdversarial.t.sol\":256,\"test/HookRevision.t.sol\":378,\"test/JudgeFindings.t.sol\":193,\"test/Launch.t.sol\":156,\"test/LaunchManifest.t.sol\":317,\"test/Letterbox.t.sol\":752,\"test/LetterboxInvariant.t.sol\":441,\"test/OracleConformance.t.sol\":114,\"test/OracleReplay.t.sol\":60,\"test/Orientation.t.sol\":58,\"test/SeasonAdversarial.t.sol\":203,\"test/SeasonFunds.t.sol\":343,\"test/SeasonInvariant.t.sol\":341,\"test/SeasonRanking.t.sol\":168,\"test/Seasons.t.sol\":266,\"test/Token.t.sol\":78,\"test/TraderResolution.t.sol\":207,\"test/TradingInvariant.t.sol\":476,\"test/fork/ForkMainnet.t.sol\":368,\"test/fork/ForkTestnet.t.sol\":765,\"test/utils/ClaimTree.sol\":41,\"test/utils/Fixture.sol\":238,\"test/utils/Mocks.sol\":324,\"test/utils/SeasonModel.sol\":117,\"test/utils/SepoliaFixture.sol\":34},\"excluded\":[\"lib/\",\"node_modules/\"],\"truncated\":false}","passed":true}],"detail":"all checks passed","evaluation":"checks","profile":"foundry","status":"accepted","submissionHash":"e41c52c3b6a7529955b2ba0781d5ce5ba2f5597d6ca4da97c99b8f192190940a","verifiedTreeHash":"663a7b7e9b4defdadc76939aadcbaef6c70d6056","verifierVersion":"0.1.0+327e1e9f"}]}