Add a type to tighten control of certain information
May 28, 7-8 PM (44)
May 28, 8-9 PM (34)
May 28, 9-10 PM (17)
May 28, 10-11 PM (36)
May 28, 11-12 AM (32)
May 29, 12-1 AM (12)
May 29, 1-2 AM (13)
May 29, 2-3 AM (4)
May 29, 3-4 AM (3)
May 29, 4-5 AM (0)
May 29, 5-6 AM (2)
May 29, 6-7 AM (5)
May 29, 7-8 AM (16)
May 29, 8-9 AM (37)
May 29, 9-10 AM (34)
May 29, 10-11 AM (69)
May 29, 11-12 PM (25)
May 29, 12-1 PM (44)
May 29, 1-2 PM (66)
May 29, 2-3 PM (61)
May 29, 3-4 PM (26)
May 29, 4-5 PM (26)
May 29, 5-6 PM (83)
May 29, 6-7 PM (11)
May 29, 7-8 PM (19)
May 29, 8-9 PM (15)
May 29, 9-10 PM (9)
May 29, 10-11 PM (27)
May 29, 11-12 AM (8)
May 30, 12-1 AM (16)
May 30, 1-2 AM (25)
May 30, 2-3 AM (1)
May 30, 3-4 AM (7)
May 30, 4-5 AM (2)
May 30, 5-6 AM (11)
May 30, 6-7 AM (0)
May 30, 7-8 AM (2)
May 30, 8-9 AM (11)
May 30, 9-10 AM (13)
May 30, 10-11 AM (10)
May 30, 11-12 PM (5)
May 30, 12-1 PM (8)
May 30, 1-2 PM (5)
May 30, 2-3 PM (18)
May 30, 3-4 PM (5)
May 30, 4-5 PM (1)
May 30, 5-6 PM (9)
May 30, 6-7 PM (9)
May 30, 7-8 PM (1)
May 30, 8-9 PM (5)
May 30, 9-10 PM (4)
May 30, 10-11 PM (27)
May 30, 11-12 AM (12)
May 31, 12-1 AM (17)
May 31, 1-2 AM (0)
May 31, 2-3 AM (1)
May 31, 3-4 AM (1)
May 31, 4-5 AM (0)
May 31, 5-6 AM (0)
May 31, 6-7 AM (7)
May 31, 7-8 AM (4)
May 31, 8-9 AM (10)
May 31, 9-10 AM (3)
May 31, 10-11 AM (4)
May 31, 11-12 PM (4)
May 31, 12-1 PM (1)
May 31, 1-2 PM (2)
May 31, 2-3 PM (24)
May 31, 3-4 PM (16)
May 31, 4-5 PM (2)
May 31, 5-6 PM (1)
May 31, 6-7 PM (2)
May 31, 7-8 PM (2)
May 31, 8-9 PM (2)
May 31, 9-10 PM (7)
May 31, 10-11 PM (25)
May 31, 11-12 AM (11)
Jun 01, 12-1 AM (14)
Jun 01, 1-2 AM (7)
Jun 01, 2-3 AM (3)
Jun 01, 3-4 AM (10)
Jun 01, 4-5 AM (13)
Jun 01, 5-6 AM (16)
Jun 01, 6-7 AM (10)
Jun 01, 7-8 AM (14)
Jun 01, 8-9 AM (46)
Jun 01, 9-10 AM (50)
Jun 01, 10-11 AM (19)
Jun 01, 11-12 PM (27)
Jun 01, 12-1 PM (49)
Jun 01, 1-2 PM (40)
Jun 01, 2-3 PM (44)
Jun 01, 3-4 PM (34)
Jun 01, 4-5 PM (54)
Jun 01, 5-6 PM (5)
Jun 01, 6-7 PM (32)
Jun 01, 7-8 PM (37)
Jun 01, 8-9 PM (9)
Jun 01, 9-10 PM (12)
Jun 01, 10-11 PM (30)
Jun 01, 11-12 AM (22)
Jun 02, 12-1 AM (13)
Jun 02, 1-2 AM (8)
Jun 02, 2-3 AM (5)
Jun 02, 3-4 AM (14)
Jun 02, 4-5 AM (10)
Jun 02, 5-6 AM (43)
Jun 02, 6-7 AM (32)
Jun 02, 7-8 AM (58)
Jun 02, 8-9 AM (65)
Jun 02, 9-10 AM (28)
Jun 02, 10-11 AM (19)
Jun 02, 11-12 PM (15)
Jun 02, 12-1 PM (47)
Jun 02, 1-2 PM (66)
Jun 02, 2-3 PM (97)
Jun 02, 3-4 PM (23)
Jun 02, 4-5 PM (15)
Jun 02, 5-6 PM (27)
Jun 02, 6-7 PM (29)
Jun 02, 7-8 PM (18)
Jun 02, 8-9 PM (9)
Jun 02, 9-10 PM (19)
Jun 02, 10-11 PM (33)
Jun 02, 11-12 AM (22)
Jun 03, 12-1 AM (13)
Jun 03, 1-2 AM (31)
Jun 03, 2-3 AM (16)
Jun 03, 3-4 AM (0)
Jun 03, 4-5 AM (7)
Jun 03, 5-6 AM (12)
Jun 03, 6-7 AM (80)
Jun 03, 7-8 AM (16)
Jun 03, 8-9 AM (24)
Jun 03, 9-10 AM (22)
Jun 03, 10-11 AM (39)
Jun 03, 11-12 PM (76)
Jun 03, 12-1 PM (93)
Jun 03, 1-2 PM (28)
Jun 03, 2-3 PM (62)
Jun 03, 3-4 PM (26)
Jun 03, 4-5 PM (24)
Jun 03, 5-6 PM (23)
Jun 03, 6-7 PM (15)
Jun 03, 7-8 PM (17)
Jun 03, 8-9 PM (16)
Jun 03, 9-10 PM (8)
Jun 03, 10-11 PM (31)
Jun 03, 11-12 AM (14)
Jun 04, 12-1 AM (12)
Jun 04, 1-2 AM (4)
Jun 04, 2-3 AM (1)
Jun 04, 3-4 AM (3)
Jun 04, 4-5 AM (1)
Jun 04, 5-6 AM (0)
Jun 04, 6-7 AM (14)
Jun 04, 7-8 AM (10)
Jun 04, 8-9 AM (11)
Jun 04, 9-10 AM (19)
Jun 04, 10-11 AM (11)
Jun 04, 11-12 PM (13)
Jun 04, 12-1 PM (53)
Jun 04, 1-2 PM (38)
Jun 04, 2-3 PM (60)
Jun 04, 3-4 PM (12)
Jun 04, 4-5 PM (4)
Jun 04, 5-6 PM (7)
Jun 04, 6-7 PM (40)
Jun 04, 7-8 PM (3)
3,421 commits this week
May 28, 2026
-
Jun 04, 2026
fix(database/sqlite): Made changes to shutdownTimeout while waiting for background deferred index maintenance to finish during cleanup.
Signed-off-by: Akhil Repala <[email protected]>
Add a type to tighten control of certain information
chore(deps): bump github.com/blinklabs-io/plutigo from 0.1.13 to 0.1.14 (#737)
Bumps [github.com/blinklabs-io/plutigo](https://github.com/blinklabs-io/plutigo) from 0.1.13 to 0.1.14. - [Release notes](https://github.com/blinklabs-io/plutigo/releases) - [Changelog](https://github.com/blinklabs-io/plutigo/blob/main/RELEASE_NOTES.md) - [Commits](https://github.com/blinklabs-io/plutigo/compare/v0.1.13...v0.1.14) --- updated-dependencies: - dependency-name: github.com/blinklabs-io/plutigo dependency-version: 0.1.14 dependency-type: direct:production update-type: version-update:semver-patch ... Signed-off-by: dependabot[bot] <[email protected]> Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
fix(database/sqlite): Made changes to Wait for background deferred-index maintenance before closing the node database handle during startup cleanup or graceful shutdown.
Signed-off-by: Akhil Repala <[email protected]>
fix(database/sqlite): Added a log message for rebuild of lazy indexes
Signed-off-by: Akhil Repala <[email protected]>
fix(ledger): fee calculation and min-fee handling
Signed-off-by: Chris Gianelloni <[email protected]>
Fix CRS substitution: validate txOutAddress in withCRSLookup
withCRSLookup only checked txOutReferenceScript (script hash) but not txOutAddress. An attacker could create a UTxO at any address, attach the legitimate CRS script as a reference, and provide malicious G2 identity elements as datum — bypassing the KZG membership check and fanning out arbitrary outputs after the contestation deadline. Fix: add addressCredential (txOutAddress resolved) == ScriptCredential expectedHash check. Since expectedHash is already compiled into the head validator, no new parameters are needed. Move CRS UTxO publishing to the CRS script address (which already always-fails) so the on-chain check is self-consistent. Update the test generator to match. Add WrongAddressCRS mutation tests to FinalPartialFanout, PartialFanout, and FanOut (the full fanout path had no CRS mutation coverage at all). Signed-off-by: Sasha Bogicevic <[email protected]>
Simplify findLargestFitting to a single callback
Merge the two-callback interface (mkTx + fitsCheck) into one (Int -> m (Maybe tx)) where Nothing means doesn't fit and Just tx means fits. This enforces at the type level that construction and checking always happen together. Also rename mkTxM to buildTx in findFittingFanoutTx's where bindings. Signed-off-by: Sasha Bogicevic <[email protected]>
Restore numberOfFanoutOutputs to Fanout redeemer
The accumulator-based headIsFinalizedWith used txInfoOutputs directly, which includes the wallet's change output appended by coverFee. Since that output is not in the accumulator, the KZG membership proof failed for every real on-chain fanout. Restore numberOfFanoutOutputs :: Integer to the Fanout redeemer (as in the original hash-based validator) so the validator slices txInfoOutputs to only the distributed UTxOs before running the pairing check and value conservation. Also update the FanOut.hs head output to carry the UTxO value so mustConserveValue passes, and add a unit test that appends a trailing wallet change output and asserts the transaction still evaluates — this would have caught the regression at the contract test level rather than requiring a devnet E2E run. Signed-off-by: Sasha Bogicevic <[email protected]>
Changelog
Also reduce a diff in the test code Signed-off-by: Sasha Bogicevic <[email protected]>
Improve Greeting and Environment serialisation
Replace UTxO hash verification with BLS accumulator commitment
Remove utxoHash/alphaUTxOHash/omegaUTxOHash from ClosedDatum, all Close/Contest redeemers, and the snapshot signing tuple. The BLS accumulator already commits to the full UTxO set (utxo ∪ alpha ∪ omega), making the three separate SHA256 hashes redundant. Full fanout now verifies outputs via a KZG membership proof (same as partial fanout) rather than hash comparison. The Fanout redeemer gains proof and crsRef fields; the three output-count fields are dropped. Snapshot signing shrinks from a 7-tuple to a 4-tuple (headId, version, snapshotNumber, accumulatorHash). Signed-off-by: Sasha Bogicevic <[email protected]>
Fix stale mutation test error code expectations in hydra-tx
Four mutation tests expected error codes that no longer match the
validator's check ordering or error code assignments:
- IncrementDifferentClaimRedeemer: H44 (DepositInputNotFound) is not
referenced anywhere in the on-chain validator; H43 (DepositNotSpent)
is the actual check that fires when the increment TxOutRef is absent
from tx inputs.
- DropDecommitOutput and ChangeDecrementedValue: signatures cover
(headId, version, snapshotNumber, accumulatorHash), not output values,
so removing or changing a decommit output fails mustDecreaseValue
(H4) before any signature check (H12) can run.
- ContestFromDifferentHead: replacePolicyIdWith mutates token values
but not the datum's headId field, so mustBeSignedByParticipant fires
H5 before the signature check reaches H37.
Signed-off-by: Sasha Bogicevic <[email protected]>
Fix fanout for pre-settled UTxOs: remove isG1Generator, add headAdaOverhead
When a UTxO is settled on-chain via Increment or Decrement before Close,
its scalar remains in the snapshot's KZG accumulator but its value has
already left (or entered) the head. Fanning out only the remaining UTxOs
produces a subset membership proof, but the old on-chain check required
isG1Generator(proof) — only true when the subset equals the full
accumulator. This caused H39 FanoutUTxOHashMismatch for any CloseUsed
scenario.
Fix (two inseparable halves):
1. Remove `&& isG1Generator proof` from headIsFinalizedWith and
checkFinalPartialFanout. Fanout and final-partial-fanout now accept
any valid subset membership proof.
2. Replace the `geq` conservation check with strict equality using a new
`headAdaOverhead :: Integer` field in ClosedDatum and
FanoutProgressDatum. This field holds the fixed lovelace overhead in
the head UTxO not attributable to any L2 UTxO (the min-UTxO cost set
at CollectCom). It closes the security hole that geq would leave: a
valid subset proof + >= would let an attacker leave value unaccounted.
Off-chain: fanoutTx receives a separate utxoForProof argument (the full
snapshot UTxO set including pre-settled ones) to rebuild the accumulator
matching the ClosedDatum commitment, while the fanned-out outputs cover
only the UTxOs whose values are still in the head. closeTx computes
headAdaOverhead as lovelace(headInputValue) - lovelace(UTxOs currently
in head), with case analysis on incrementalAction × (version ==
openVersion). contestTx propagates it unchanged; partialFanoutTx threads
it through FanoutProgressDatum.
checkContest preserves headAdaOverhead so it cannot be altered after the
initial Close. checkPartialFanout also preserves it across intermediate
steps.
Signed-off-by: Sasha Bogicevic <[email protected]>
Fix FanOut tx-cost bench
genFanoutTx generated a snapshot with utxoToCommit/utxoToDecommit but called unsafeFanout with mempty mempty — the BLS proof was built for a different accumulator than the one committed in the closed head datum, so every evaluateTx call failed script validation and the FanOut table produced no rows. Fix: pass utxoToCommit and utxoToDecommit through to unsafeFanout, and inflate the head output value by the total fanout value (same pattern as computePartialFanOutNominalCost) so mustConserveValue passes. Signed-off-by: Sasha Bogicevic <[email protected]>
Small cleanups: nullary IncrementalAction constructors and isG1Generator helper
Remove UTxO fields from ToCommit and ToDecommit constructors of IncrementalAction — the UTxO was already ignored at every callsite. Update setIncrementalActionMaybe and pattern matches in Close.hs and Contest.hs accordingly. Extract repeated BLS12-381 generator check into isG1Generator helper in Head.hs, and add a comment explaining why mustConserveValue uses geq rather than == (min-UTxO overhead on the head output). Signed-off-by: Sasha Bogicevic <[email protected]>
Use dynamic binary search to find largest fitting fanout chunk
Replace the hardcoded numToDistribute = totalUTxO - 1 in the partial fanout benchmarks with a binary search that finds the largest chunk actually fitting within both the tx size and execution budget, mirroring findFittingFanoutTx in the real node. The Remaining column in the output table now carries meaningful information instead of always showing 1. Also add ContestationDeadlineOutsideTimeHorizon to the PostTxError oneOf in api.yaml, which was defined in Chain.hs but missing from the schema, causing ServerOutputSpec to fail. Signed-off-by: Sasha Bogicevic <[email protected]>