| Commit message (Collapse) | Author | Age | Files | Lines |
| ... | |
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
day's own Sunday-ness, not observed
Fix round 1 review, two findings landed together because each golden pin's
correctness depends on both.
CRITICAL (item 1): reverts this branch's own first-pass retag of the
Purification (2 February) from Lord back to Bvm -> Lord. The calendarium
titles it 'B. Mariae Virg.', but missalemeum -- this project's designated
EF oracle -- treats it as taking an occurring II-class Sunday's place
outright, commemorations empty, exactly RG16(a)'s own festum Domini
treatment (2020-02-02, 2014-02-02, independently fetched). Control,
2019-09-08 (the Nativity of the BVM, an ordinary Marian feast, on a
Sunday): the Sunday observed, the feast merely commemorated -- the
opposite pattern, proving the Purification's own oracle treatment is
deliberate, not a gap. RG16(a) alone, on the untouched data, would have
matched the oracle character for character; retagging Bvm is what moved
colitur away from it on 1200 domain-wide days. The user has ruled: follow
the oracle. Genuine primary-text counter-evidence (RG120(b), the colour
rule grouping 2 February under 'B. Mariae Virg.', a category separate
from 'Domini') is recorded in the register, not discarded -- a different
project could reasonably rule the other way on the same evidence.
most-holy-name-of-mary stays retagged Bvm; that one was never disputed.
Removes the now-unneeded C12 lectio allow-list entry (data/ef/
expected-divergences.sexp, test_differential.ml): with the Purification
Lord again, colitur matches lectio's own class = lord on every affected
date, no divergence to allow-list.
IMPORTANT (item 2): Precedence.rules.admit gains a ~temporal parameter --
a genuine kernel signature change, unlike RG16(a) itself. RG111(b)'s own
Sunday rank floor ('one commemoration, namely of a II-class feast') used
to be detected by reading observed's own slug for a Sunday marker, which
silently assumed observed IS the day's temporal-cycle office. RG16(a)
breaks that assumption on purpose: a Feast of the Lord standing in for an
impeded Sunday 'cum omnibus iuribus et privilegiis' keeps the day a
dominica II classis for RG111(b) too, even though the FEAST, not the
Sunday, is observed. Before this fix an unrelated saint (Pope Sixtus II
et al., 6 August, Class3) was wrongly admitted into the freed slot on
every one of 1178 domain-wide days. Oracle-confirmed directly: 2023-08-06
(a Sunday) shows him displaced, commemorations empty; 2026-08-06 (an
ordinary Thursday) shows him admitted -- being a Sunday is exactly what
excludes him. admit now reads Sunday-ness off ~temporal (the day's own
temporal-cycle candidate, passed through from Precedence.resolve
unchanged) instead of observed. Validate's own admission fixed-point
invariant updated to pass the same real temporal candidate through.
Both golden pins in test_golden.ml were promoted from actual colitur day
output without independently consulting the rubric or the oracle first --
a real defect the review caught. Re-derived from both before re-pinning:
2028-08-06 and 2025-02-02 now pin comms=[], no commemoration at all,
matching missalemeum exactly in both cases.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Sunday uncommemorated
Caput III "De Dominicis", RG 16(a): a Feast of the Lord, I or II class,
occurring on a II-class Sunday takes the Sunday's own place with all its
rights and privileges -- of the Sunday, therefore, no commemoration is
made. band's entry 14 already ranked such a feast above the Sunday
correctly; disposition had no exception for the collision, so the impeded
Sunday fell through to the ordinary RG 95/109(a) commemorate-or-omit
catch-all and was wrongly admitted as a privileged commemoration.
Adds a branch to Rite_ef.Precedence_ef.disposition, gated on all four of:
loser is temporal-origin, loser rank Class2, loser carries the Sunday slug
marker, winner rank Class1-or-2 with subject Lord. No signature change --
disposition already receives the winner (RG 33's own vigil-omission branch
already reads it); each conjunct is proved independently load-bearing by
a dedicated disposition_cases row, including one real-data case each for
the winner's subject and rank conjuncts, and a defensive synthetic case
for the winner rank conjunct's currently-unreachable Class3 shape. A new
end-to-end resolve-level test (2028-08-06, the Transfiguration) proves the
real band/disposition pipeline together, checking the Omit reason string
distinguishes this from admit's own admission-limit cut.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
precedence_ef.mli said "there is no fifth, unclassified case" after the
same commit renumbered the disposition list from four cases to five; the
count is now six.
precedence.mli's physical-equality obligation described the failure mode
as counting a drop "a SECOND time (once because it is genuinely absent,
once because its identity no longer matches)" -- the same condition
stated twice. What actually happens to a rebuilt candidate record is
that the celebration surfaces in BOTH commemorations (the copy) and
omitted (the original), one admission double-reported. precedence_ef.ml
carried the same muddled sentence, which is where the kernel's copy came
from; both now say it plainly.
vocab.ml/.mli referenced {!Rite_ef.rite_ef.ml} -- a filename inside an
odoc reference, which is malformed. Now plain [Rite_ef.rite].
README documented only `dune test`, so the exhaustive 1583-9999 Validate
sweep was discoverable only by reading test_validate.ml's own comment.
With no CI in this repo, that line is what stands between a committed
artifact and one anyone runs.
No behaviour change: `colitur day` output is byte-identical across 1583,
1900, 1902, 2008, 2011, 2026, 2038 and 9999 (2921 days, both domain
edges). 259 tests by default, 260 with the sweep.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Several comments described work as "arriving with Plan 3" or "waiting
for Plan 3" that either shipped without it or refer to the wrong future
plan number, all now false in ways that would mislead the next reader:
- temporal_ef.ml (two places) and precedence_ef.ml said the Major
Litanies (25 April, RG 80) "arrive with Plan 3's sanctoral". Plan 3
shipped, in this branch, without them; register §6 tracks this as a
plain open item with no plan committed to build it, and now says so.
- temporal_ef.ml said the Sacred Triduum's "own named offices are a Plan
3 sanctoral addition". Wrong on two counts: Plan 3 shipped without
adding them, AND a proper office for I-class FERIAS was never a
sanctoral matter in the first place (RG 21 defines "feria" to exclude
Sundays/feasts, not the reverse). 2026-04-02/03/04 still resolve to the
ordinary Passiontide ferial fallback's own generic slugs
(ef-passiontide-2-{thursday,friday,saturday}), confirmed against real
output; register §6 now records this as its own open item.
- temporal_ef.ml said the Rogation-Wednesday commemoration (Ascension
Vigil day, entry 21) "waits for RG 108-111" -- both the precedence
framework and RG 108-111 exist now; the Wednesday's own commemoration
is still never constructed, but for a different, still-real reason (no
candidate is wired for it), not a forward dependency. Fixed at both of
this comment's two occurrences in the file.
- vocab.ml/vocab.mli's `seasons` field doc said "Validate's contiguity
check reads this" -- false since validate.ml's "seasons" check switched
to Rite.t.season_runs in this branch (rite-supplied, to support a
season appearing in more than one run, which the modern form's Ordinary
Time needs and EF does not).
- vocab.ml/vocab.mli's `ranks` field doc said "it is not a precedence
relation until Plan 3 defines one" -- Plan 3 did define one (RG 111's
dignity ordering), but as its own small, separately-hardcoded function
in precedence_ef.ml, not one derived from this field; corrected to say
so precisely rather than leaving a forward-looking claim unresolved.
- The lectionary bootstrap (reading citations, Liturgical_day.t's own
`citations` field) is called "Plan 3" at slug.ml, vocab_ef.ml, and
three places in temporal_ef.ml, but "Plan 4" at liturgical_day.mli
(whose own doc comment -- "always empty until Plan 4" -- is the
authoritative one: the SANCTORAL bootstrap is Plan 3 and shipped; the
LECTIONARY bootstrap is a separate, later Plan 4). All six corrected to
say Plan 4, cross-referencing the Plan 3/4 distinction at the first
(slug.ml) occurrence so the reasoning is not duplicated six times.
No behaviour change: every edit here is a comment/documentation
correction. Verified byte-identical `colitur day` output across 1583,
1900, 1902, 2008, 2011, 2026, 2038, 9999. 259/259 tests green.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
68 "register line N" pointers in tracked code and data cited the
register's line numbers directly. The register has moved since: line 334
(cited six times as RG 91 entry 8) is now rose/colour prose; lines
375-376 (cited as "RG 109 leaves Advent/Lent Ember ordinary") are now
RG 26, the paragraph that refutes that exact reading; line 374 (cited as
RG 109(a)) is now RG 25's Latin; line 378 (RG 111) is blank.
expected-divergences.sexp even wrote "RG 91 line 332" three times, as
though the line offset were part of the rubric's own identity. Since
docs/research/rules-register.md is gitignored, no reader of the public
repo could resolve any of these, and -- since the register has moved on
its own copy too -- neither can the author's.
Replaced every pointer with an anchor that survives editing: the RG
paragraph/entry number itself (already present in nearly every case,
since the citation text already names "RG 91 entry N" or "RG 109(a)"
next to the stale line number -- the line number was redundant, not
load-bearing) plus a "§4" or quoted-subsection-heading pointer into the
register for readers who want to locate the fuller discussion. Also
corrected one genuinely stale content error found while migrating its
anchor: test_precedence_ef.ml's RG33 disposition-cases comment still said
"a I/II-class vigil impeded by any Sunday" -- the pre-Task-16
mistranscription the register itself corrects to II/III class; fixed the
prose alongside its citation, since leaving a wrong RG-class claim next
to a freshly-verified anchor would be worse than the stale line number it
replaced.
Covers lib/rites/rite_ef/precedence_ef.ml (18), precedence_ef.mli
(already fixed with item 1), test/test_precedence_ef.ml (44, including
two instances that only word-wrapped "register\nline N" across a line
break and so did not match a same-line grep), and
data/ef/expected-divergences.sexp (5, including three "RG 91 line 332"
instances). All 68 original pointers resolved -- none needed guessing;
every citation's target rule was already named in the surrounding prose.
No behaviour change: every edit is a comment/citation/data-note change.
Verified byte-identical `colitur day` output across 1583, 1900, 1902,
2008, 2011, 2026, 2038, 9999. 259/259 tests green.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Four citation problems, all resolved against the primary scans
(docs/research/*.pdf via pdftotext):
1. temporal_ef.ml's Ember-day date-derivation comment still carried a
retracted note claiming the scans have no numbered-paragraph statement
of the rule. Register §3a corrected this in an earlier commit (the
search used the genitive "Quatuor Temporum"; the rubric heading is the
nominative "Quatuor Tempora") and the register's own words warn "a
false 'not in the source' note is worse than no note" -- the code
still carried the retracted note verbatim. Replaced with the verified
citation and the primary Latin.
2. temporal_ef.ml cited RG 71 for "Advent I is the Sunday nearest 30
November". RG 71 is a season-boundary citation only ("a I Vesperis
dominicae I Adventus..."); it does not say which Sunday opens the
season. The actual rule is RG 20 (Caput III, "De Dominicis"):
"Dominica I Adventus ea est, quae cadit die 30 novembris vel est ipsi
proximior" -- verified against the scan and added to the register.
Behaviour was always correct; only the citation was borrowed.
3. RG 88 ("de Litaniis minoribus nihil fit in Officio") is cited five
times across code and tests, load-bearing twice (why Rogation days
take their season's ordinary ferial class; why privilege_of lets them
fall through to Ordinary), but appeared nowhere in the register. RG 67
and RG 69 were likewise cited at expected-divergences-missalemeum.sexp
(M11) without register backing. All three verified against the scan
and added to the register's §4 (Octaves / Rogations subsections).
4. Two citations flagged for re-verification, both CONFIRMED accurate
against the primary scan (word for word):
- precedence_ef.ml's RG 32 "si impeditur, commemoratur" (the sole
textual basis for treating a vigil as always-commemorated once RG 33
doesn't omit it outright) -- the register previously stated RG 32
only as "same pattern as RG 31", not verbatim; the full sentence is
now in the register too.
- precedence_ef.ml's RG 111(b) full sentence (the sole textual basis
for the shipped Sunday rank-floor fix) -- the register previously
carried only the fragment "de festo II classis"; the full sentence
is now there.
- temporal_ef.ml's RG 91 entry 7 "feria IV cinerum et II, III et IV
Hebdomadae sanctae" (the sole justification for stopping the I-class
ferias at Wednesday) was also checked and matches the scan exactly;
left as-is (already correctly cited), noted in the report.
Bonus finding while re-verifying RG 20: RG 17(d), same chapter, states
"festum D. N. Iesu Christi Regis, celebrandum dominica ultima mensis
octobris" -- primary-source confirmation that Christ the King falls on
the last Sunday of October. This was the register's one
oracle-backed-but-not-primary-verified rule (CLAUDE.md's own carried-item
language); it no longer is. Updated temporal_ef.ml's christ_the_king
comment and closed the item in register §6.
No behaviour change: every edit here is a comment/citation change to
already-correct code. Verified byte-identical `colitur day` output across
1583, 1900, 1902, 2008, 2011, 2026, 2038, 9999. 259/259 tests green.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The .mli's disposition doc still said a Class1-or-Class2 vigil is Omit
(RG 33) -- the pre-Task-16 mistranscription the register corrects at its
RG 33 entry. The .ml has read Class2 || Class3 since commit 079e332; the
.mli never caught up. It also named only vigil_suffix, when the vigil
test the code actually runs also checks vigil_prefix (the shape the
sanctoral bootstrap's four real vigils use); omitted RG 26's Class4
temporal-ferias-are-never-commemorated branch entirely, then asserted the
listed cases 'exhaust every representable shape', which was false as
written; and omitted RG 111(b)'s 'de festo II classis' rank floor from
admit's doc, describing only the privilege-override half of that rule.
Fixed all four: the vigil-omission bullet now names Class2/Class3 and
both slug conventions; the missing RG 26 branch is now documented,
folding the exhaustiveness claim into an accurate five-branch count;
admit's Sunday case now states the rank floor as a second, independent
condition.
The same stale RG 109(e) reading this interface carried ('leaves the
Advent and Lent Ember sets ordinary') also survived as the stated reason
september_ember_prefix exists, in the .ml, about 330 lines from the
already-corrected privilege_of comment it contradicts. Fixed there too:
September is broken out because it sits outside RG 109(e)'s three named
seasons entirely, not because Advent/Lent Ember needs excluding from (e)
-- it does not, per privilege_of's own corrected comment.
No behaviour change: both fixes are doc-comment-only edits to already-
correct code (precedence_ef.ml's disposition/admit implementations were
fixed in an earlier commit; only the .mli's prose and one earlier .ml
comment lagged).
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
RG109
Review round 1 (F1, Critical): the commemoration-eligibility fix from
the previous commit silently dropped II-class Advent and Lent Ember
ferias when impeded, while ordinary (lower-solemnity) ferias of the
same seasons kept their commemoration -- backwards on any reading.
Reproduced: 1900-12-21 (an Advent Ember Friday) lost its commemoration
entirely; 2026-12-21 (an ordinary Advent feria the same week) kept
its.
F2 (Important, the direct cause of F1): the branch's own justification
mis-stated RG 109 as an exhaustive list of the only temporal
circumstances that generate a commemoration. RG 109 is headed
"Commemorationes privilegiatae sunt commemorationes" and closes
"Omnes aliae commemorationes sunt commemorationes ordinariae" -- it
sorts commemorations that already exist into two HONOUR classes
(RG 108's differing liturgical hours), and says nothing about which
offices have the right to be commemorated at all. That right belongs
to Caput IV, "De feriis" (RG 21-27), never opened by the original
pass:
RG 24 (II-class ferias): "si vero impediuntur, commemorari debent"
-- if impeded, MUST be commemorated. Not optional.
RG 25 (III-class ferias): same mandate.
RG 26: every feria not named in 23-25 is IV class, and IV-class
ferias are NEVER commemorated -- the one exclusion RG 21-27 actually
states.
The omission branch is now gated on `rank = Class4` (RG 26) directly,
not on `privilege_of = Ordinary` -- the old gate happened to reach the
right answer for IV-class ferias (RG 26 also excludes them, for a
reason the old citation did not give) and the wrong one for II/III-
class Ember ferias RG 109(e) did not name by letter.
RG 109(e) itself is also corrected: its bare "feriis Adventus,
Quadragesimae et Passionis" previously excluded the Advent and Lent
Ember sub-days by analogy with (d)'s separate September carve-out.
RG 91's own TABLE needs an explicit "exceptis feriis Quatuor
Temporum" at entries 22 and 25 to keep Ember days from being double-
listed against their own entry 18 -- an exception that would be
unnecessary drafting if "feriae Adventus"/"feriae Quadragesimae" did
not already include their Ember sub-days by default. RG 109(e) carries
no such exception, so it is read at that same default, inclusive
scope: the Advent and Lent Ember ferias are privileged under (e), not
merely ordinary-but-commemorable. (d)'s own existence is unaffected --
September Ember days sit outside Advent/Lent/Passiontide under any
reading, so (d) remains necessary regardless.
Verified: 1900-12-21 and 1902-02-22 now correctly commemorate their
Ember ferias; 2026-12-21 and 1902-02-24 (ordinary ferias) unchanged.
Blast radius re-measured against the prior commit, 1900-2100: 102
civil days changed, every one an Advent/Lent Ember (or Ember-vs-
Joseph-collision) day regaining its commemoration, nothing else.
Validate re-swept exhaustively, 1583-9998: 0 failures.
F6: two privilege-boundary test rows that had been bent to expect the
bug's own output (Commemorate -> Omit) are restored to what RG 24/25
actually require, now Commemorate(Privileged) given the RG 109(e)
correction above -- these are the rows that should have caught F1.
F7: admit_cases had no witness for RG 111(b)'s rank floor that wasn't
already Class2, so reverting that filter only reddened the oracle
suite, never this file. Added a row (II-class Sunday, sole candidate
an ordinary Class3) that fails without the filter and passes with it.
F9: RG 122 cited alongside RG 128(b) for Holy Thursday's white --
states the same fact affirmatively ("Demum adhibetur color albus,
feria V Hebdomadae sanctae...") rather than as an exception to violet.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
RG 128(b) excepts "Missa sive Chrismatis sive in Cena Domini feria V
Hebdomadae sanctae" from the Septuagesima-to-Easter-Vigil violet span
as a whole-Mass exception (unlike Palm Sunday's blessing/procession,
which the same sentence carves out as only part of that day) -- so
Holy Thursday's Mass is white, not violet. temporal_ef.ml fell through
to the generic Passiontide ferial path (season_colour Passiontide =
violet) for this date, since [named] has no entry for the Triduum at
all (rank was already correct via [privileged_feria]; only colour was
wrong).
Found via Task 16's missalemeum oracle comparison: every other Triduum
day's oracle colour set includes violet as an option (Good Friday
"bv", Holy Saturday "vw" -- already-flagged, deliberately deferred
per-action gaps, register §3b), but Holy Thursday's is white alone.
This is a genuine NEW divergence from lectio too (lectio has no such
exception and still prints violet for Holy Thursday) -- added as
Layer C11 to the differential harness and data/ef/expected-divergences
.sexp, 46 rows (2005-2050), rather than silently changing what that
harness accepts.
Also corrected a stale comment on season_colour claiming white's RG
paragraph was never pinned -- RG 119 was found and cited in the
register on 2026-08-11 but the correction was never copied into this
file's own comment.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Task 16's missalemeum oracle comparison (2026-2027) surfaced three
distinct precedence-engine bugs, each confirmed against the primary
1962 Missale Romanum text and cross-checked against the oracle:
1. RG 33 (vigil omission) was transcribed backwards. The primary text
reads "Vigilia II AUT III classis penitus omittitur" (a II OR III
class vigil is entirely omitted on any Sunday or I-class feast) --
not "I aut II" as the register and this module's own rank check
(Class1 || Class2) previously had it. I-class vigils (Nativity,
Pentecost) can never actually lose in this engine (band always
ranks them above anything that could coincide with their dates), so
the Class1 half was dead code; the real bug was that Class3 (St
Lawrence's vigil, the sole III-class vigil) was MISSING, so it fell
through to an ordinary commemoration instead of RG 33's mandatory
omission whenever 9 August landed on a Sunday.
2. RG 93/95/109/113 read together: an ordinary, non-privileged
TEMPORAL-cycle office (a bog-standard green-season feria, a plain
Advent/Lent Ember day, a Minor Rogation day) has no standing to be
commemorated at all when impeded -- RG 109's six-item list is a
CLOSED set of the only temporal circumstances that generate a
commemoration, not a floor under which anything ordinary still
gets one. The engine previously commemorated the losing feria
itself in this situation; confirmed wrong against ~190 independent
missalemeum days (2026-2027) showing zero commemorations for the
exact shape. Vigils are explicitly excluded from this new rule --
RG 31/32 give them their own "if impeded, commemorated" mandate,
independent of RG 109's list.
3. RG 111(b)'s Sunday admission slot is restricted to "de festo II
classis" -- a rank restriction, not merely the best available
ordinary candidate. A III/IV-class ordinary saint competing for a
II-class Sunday's single commemoration slot had no such restriction
applied before; confirmed wrong via St Hyginus (11 Jan, Class3)
losing to Holy Family, which missalemeum shows entirely displaced,
never commemorated.
All three fixes are pure disposition/admission changes -- they never
touch band, so the observed day (season/slug/rank/colour) is
unaffected in every case; the lectio differential (which never
compares commemorations) stays green untouched. test_precedence_ef.ml
updated throughout: two previously-wrong test expectations corrected
(the RG33 III-class-vigil boundary row, the IV-class-feria totality
row), three privilege boundary rows sharpened from "commemorated but
unprivileged" to "omitted entirely" now that temporal+ordinary
means omission, and a new contrast row added to keep the SANCTORAL
side of rule 2 covered separately from the TEMPORAL side.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
The register was transcribed faithfully but was itself wrong: RG 96's
Attamen (a), primary-source-verified from the scans and now corrected
in the register, reads 'festum Annuntiationis B. Mariae Virg., quando
est transferendum post Pascha, transfertur ... in feriam II post
dominicam in albis' -- the Monday-after-Low-Sunday seat applies ONLY
'quando est transferendum post Pascha', when the feast is to be
transferred PAST EASTER. The unconditional transcription made the
exception fire on every impeded Annunciation regardless of cause.
transfer_target now computes the general RG 96 target first, for every
candidate, and overrides to the Monday after Low Sunday only when that
general target itself falls after Easter Sunday -- testing the rubric's
own condition directly rather than re-deriving a date-proximity rule
from first principles.
Confirmed against three real years the review named: 2007, 2012 and
2057 all previously sent the Annunciation to Easter + 8 (16 April,
16 April, 30 April respectively) when the correct, now-produced target
is the next free day before Easter (26 March in each case -- Passion
Sunday in 2007/2012, Lent III Sunday in 2057). Verified with actual CLI
output for all three, before and after.
Also cites RG 96 Attamen (b), the same primary-source passage, as the
direct authority for All Souls' own move to the following Monday when
impeded by a Sunday -- previously inferred from RG 91 entry 8's
parenthetical plus the general walk, which happened to produce the
right date; now stated directly.
Rewrote the two existing Annunciation unit tests, whose synthetic
occupants no longer trigger the (now correctly conditional) exception,
and added a 2057 regression test using the real Temporal_ef.temporal as
occupant plus a real-data cram pin -- both mutation-verified against
the unconditional reading.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
search_from could walk up to 400 days past origin before Calendar's own
~start ~stop clamp is ever consulted, and nothing stopped it probing
occupant on a date past 31 December 9999 -- occupant chains through the
real EF rite's temporal, which calls Computus.gregorian_easter, not
total outside 1583..9999 (it Date.makes and failwiths on Error).
Not reachable with the shipped sanctoral data alone, but reachable
through the project's own primary extension path: an overlay adding an
I-class feast on 25 December leaves nothing but Class2 Nativity-octave
days for the rest of civil year 9999, so the unguarded search reached 1
January of year 10000 and crashed there with 'computus: year 10000 out
of range 1583..9999'. 9999 is an in-range year and the kernel's contract
is 'never raises on in-range input'.
search_from now also stops, without probing occupant again, once it
passes Date's own domain ceiling -- the same 'return a finite date, let
Calendar's own out-of-range handling record it, never pretend to have
found something admissible' contract the existing step-count guard
already follows.
Two new tests, both mutation-verified to actually reproduce the crash
when the guard is removed (see the task report): a precedence_ef.ml unit
test using the real Temporal_ef.temporal as occupant (a synthetic
occupant can never discriminate this, since it never calls Computus
itself), and a Calendar-level integration test reproducing the exact
overlay-based scenario the review found.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Assembles Rite_ef.context (lib/rites/rite_ef/rite_ef.ml[i]): temporal,
anchors and vocab from Temporal_ef; rules from Precedence_ef's band,
disposition and admit; season_runs = Vocab_ef.seasons; transfer_target
newly implemented here.
transfer_target (RG 96): the next following day that is not I or II
class, with the Annunciation's own exception (Monday after Low Sunday).
Terminates by a structural step bound on its internal search, independent
of Calendar's own round guard, which bounds rounds across a year, not one
call's walk; documented as an obligation on rite.mli's transfer_target
field, which did not previously state it.
Fixes the vigil-naming mismatch Task 7's review predicted: the sanctoral
bootstrap names its vigils with a vigil-of-X prefix (lectio's own
convention), while Precedence_ef's is_vigil only recognised the temporal
cycle's own X-vigil suffix. Both are now recognised, fixing RG 91 entries
21/26 and RG 33's vigil omission for the four affected celebrations.
Verified by unit test and by mutation-testing the fix (reverting it fails
exactly the new rows) and against real output across several years.
Suppresses data/ef/sanctoral.sexp's vigil-of-christmas via a new overlay,
data/ef/adjustments.sexp: it is the same celebration as the temporal
cycle's own ef-nativity-vigil, both dated 24 December.
colitur day <year>: one line per civil-year day, temporal and sanctoral
fully resolved through Layer, Overlay, Precedence_ef and Calendar -- the
first CLI path exercising the whole Plan 3 pipeline against real data.
Verified the All Souls transfer chain (Tasks 7-8-11) end to end against
real output for both a Sunday year (2025, lands on 3 Nov) and a
non-Sunday year (2026, observed directly on 2 Nov).
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
disposition's Class1 branch was unconditional on rank, so an impeded
I-class Sunday (Advent/Lent/Passiontide/Low Sunday) currently
transferred like a feast. RG 95 (register lines 323, 363) restricts the
right of translation to I-class FEASTS -- RG 91's own table lists
Sundays as a separate row (entry 6, line 332) from feasts (entries
11-13, lines 337-339) -- and RG 109(a) (line 374) lists "of a Sunday"
as a privileged commemoration category, which presupposes an impeded
Sunday stays put rather than moving to another day.
Excludes is_sunday_slug losers from the Transfer branch so they fall
through to the existing Commemorate (privilege_of loser) branch, which
already tags them Privileged via RG 109(a) with no further change.
Fires on real dates in the 2005-2050 differential window: 24 December
on Advent IV in 2023, 2028, 2034, 2045; 8 December on an Advent Sunday
in 2024, 2030, 2041.
Verified no previously-passing Transfer assertion used a Sunday-shaped
loser (grepped test_precedence_ef.ml, test_calendar.ml -- which uses
its own synthetic rite unrelated to Precedence_ef.disposition --
test_colitur.ml, test_validate.ml); confirmed by mutation-reverting the
fix and observing exactly the one new test fail, nothing else.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Precedence_ef.privilege_of classifies a commemoration candidate against
RG 109's closed list of privileged commemorations (a Sunday; a I-class
day; a day within the Octave of the Nativity; a September Ember day; a
feria of Advent, Lent or Passiontide; the Major Rogations in Mass), read
entirely off the candidate's own rank/slug/origin, no context needed.
Major Rogations (f) is left unimplemented rather than guessed: no
producer for the Major Litanies exists anywhere in this codebase yet.
disposition's two Commemorate sites now call privilege_of instead of
Task 8's interim_privilege placeholder, which is removed entirely
(binding and .mli export both gone).
Precedence_ef.admit applies RG 111's four admission counts, keyed on
the observed day's own class and Sunday-ness: a I-class day admits none
except one privileged commemoration; a II-class Sunday admits one, but
a privileged commemoration due displaces any ordinary one regardless of
dignity; any other II-class day admits one by dignity alone, with no
such override; III/IV-class days admit at most two by dignity. Ties
break on slug, matching Precedence.compare_by, so the admitted set
never depends on input order. Every admitted candidate is a value taken
unchanged from the input list, never rebuilt, so Precedence.resolve's
physical-equality-based dropped/omitted accounting keeps working --
closing a note left open since Task 2.
Tests: RG 109 category rows (one per reachable category, plus boundary
rows proving Advent/Lent Ember days and Minor Rogations are correctly
excluded), RG 111 admission rows checked on slug identity rather than
count, an order-independence check, and three end-to-end integration
tests proving the admission limit's drop lands in resolution.omitted
rather than vanishing.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Review finding: the comment claimed every RG 91 entry that can outrank a
II-class vigil (entry 21) without being a Sunday is I class 'by the table's
own structure (entries 1-13)'. False -- entries 14 and 16-20 (Feasts of the
Lord II class, universal/proper/indult II-class feasts, days within the
Nativity octave) are all Class2, all outrank entry 21, and none is a Sunday.
The code was always correct: impedes_vigil implements RG 33's own two named
conditions (any Sunday, or a I-class feast) directly, and does not depend on
the band table's numeric ordering at all. Reworded to say so, citing the
counter-example entries the review named instead of appealing to a table
structure that does not guarantee what the old comment claimed.
Comment-only change; no logic, signature, or test changes.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Precedence_ef.disposition decides the loser's fate in an occurrence: a
Commemoration_only celebration is always commemorated (it can never win or
transfer); a I- or II-class vigil impeded by any Sunday or a I-class feast
is entirely omitted (RG 33), checked before the generic rule below or the
Nativity/Pentecost Vigil could wrongly transfer; any other I-class loser
transfers (RG 95 -- only I class has the right of translation); everything
else is commemorated, with the admit-or-omit decision left to RG 108-111's
admission count (Task 9). RG 94 needs no code: resolve always compares a
loser against the day's actual winner, never against a departed sibling, so
no commemoration can ride along with a transferred feast in this design.
This is the branch that completes Task 7's carried All Souls fix: once it
loses to an occurring Sunday, its untouched Class1 rank routes it to
Transfer via the generic rule, not a special case. Landing on 3 November is
Rite.transfer_target's job, not wired up yet.
Commemorate carries an interim Precedence.Ordinary privilege pending Task
9's RG 109 implementation, exposed as interim_privilege for that task to
replace.
Table-driven tests cover each rule, including RG 33's boundary from both
sides and a Commemoration_only loser that is also Class1 and vigil-shaped
to pin the branch ordering. Mutation-tested: disabling RG 33, either
direction of RG 95's rank condition, or the Commemoration_only priority
check each fail exactly the rows built to catch them.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Review of 436ba75 found two calendar defects and one coupling risk.
Entry 8 (All Souls) dropped register line 334's own qualifier,
"(yields to an occurring Sunday)" -- it returned 8 unconditionally,
so on 2 November falling on a Sunday (2025, 2031, 2036, 2042 in the
2005-2050 differential window), All Souls incorrectly outranked and
observed over the Sunday. 2 November is always Time_after_pentecost
and never coincides with any other entry's own date, so the only
rival this exception ever has is an ordinary entry-15 II-class
Sunday; on such a Sunday, band now returns one worse than entry 15's
own value rather than the literal 8 -- strictly worse, not merely
different, since an exact tie would fall to Precedence.resolve's slug
tie-break, which for "ef-all-souls" against a Sunday slug would make
All Souls win the tie anyway. Entry 8's own rank is untouched, so
Task 8's disposition still sees a true I-class candidate to transfer.
Entry 14 (Feasts of the Lord, II class) added a universal-layer
restriction the register's line 341 does not carry -- contrast entry
16 at line 342, which explicitly says "not of the Lord"; RG 37c
(register line 393) also speaks of "II-class feasts of the Lord"
with no universal qualifier. Dropped the layer test: a proper or
indult feast of the Lord now bands 14, not 19/20.
Also exposes vigil_suffix and ember_prefixes from precedence_ef.mli,
matching universal_layer/indult_prefix's existing "colitur convention,
not an RG citation" treatment -- both were previously private literals
duplicated in the test file, so a rename of temporal_ef.ml's slug
format could have drifted silently past both sides agreeing with each
other. Two test rows now build their candidate from Temporal_ef.temporal's
own real output (entry 18's Lent Ember day, entry 21's Ascension Vigil)
instead of a hand-typed slug, closing that specific coupling.
Adds the three cheap rows review named as closing the remaining
unpinned guards (a temporal-origin Class1 candidate on an unnamed
date; a universal Class2 vigil of the Lord; a non-universal Class3
vigil), plus a resolve()-level test proving the Sunday is actually
observed over All Souls, not just that band returns the right integer
in isolation.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Precedence_ef.band transcribes RG 91's 28-entry Table of Precedence
(rules-register.md §4) for the EF rite: given a day's context and a
candidate celebration, returns the table's own entry number, 1-28
(I class 1-13, II class 14-21, III class 22-26, IV class 27-28); lower
wins. Every branch carries its entry number and register citation in a
comment, checked in the table's own numeric order.
Two entries are transcribed as the register states them even though
they invert the pattern the rest of the table follows: at III class,
23 (particular calendars) outranks 24 (universal), the reverse of how
11/12 and 14/16/19/20 rank a universal feast ahead of a proper one at
I and II class.
Sanctoral-origin, layer-decided entries (11-13, 14/16/19/20, 23/24)
follow the brief's structural insight: a celebration whose layer is
not the universal base is an overlay -- proper, or indult if its
layer id also carries the indult prefix. Neither the universal-layer
id nor the indult prefix is an RG citation; both are colitur's own
data-modelling convention, exposed from the module so whichever task
loads the real EF sanctoral overlays can align to them.
Vigils (21, 26) are read off the temporal cycle's own -vigil slug
suffix rather than gated on origin, since a II/III-class vigil can be
either temporal-origin (Ascension, already produced by temporal_ef) or
sanctoral-origin (a saint's vigil, no task has loaded yet); Ember days
(part of entry 18) are read off temporal_ef's own ember slug prefixes
rather than re-derived, since the September anchor is independently
flagged there as one of the more contested dates in the calendar.
A candidate shape the table has no row for (e.g. a Class1 vigil that
is not Nativity or Pentecost, or a Class4 candidate marked as a vigil
-- RG 91 has no IV-class vigil either) returns a dedicated unclassified
sentinel (max_int) rather than being folded into a same-rank entry it
does not belong to.
test_precedence_ef.ml is table-driven: one Alcotest.test_case per RG
91 entry (55 rows total, several entries covered by more than one
named day so a single missed offset cannot hide behind a passing
sibling), each date computed from Computus.gregorian_easter rather
than hand-typed, so an arithmetic slip cannot pass by accident.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Two correctness bugs in Temporal_ef, both only visible across many
years, not a single point assertion:
1. Duplicate slugs within one liturgical year. Christmastide has no
numbered weeks, so the ferial fallback's <season>-<week>-<weekday>
scheme collapsed every feria in it to literal week "0". Since
colitur's Christmastide runs 25 Dec - 13 Jan (RG 72-73, a deliberate
divergence from lectio), the same weekday recurs across that span
and the keys collided (e.g. ef-christmas-0-saturday on three
different dates). Fixed with a dedicated christmastide_feria_slug
that splits the span into four sub-stretches, prioritising
compatibility with lectio's own keys wherever lectio has one:
- 26-28 Dec keeps lectio's existing ef-christmas-0-<weekday>.
- 2-5 Jan becomes ef-christmas-1-<weekday> -- lectio collapses
this indistinguishably into the same key as the stretch above,
so there is nothing to preserve; a colitur-only lectionary gap.
- 7-13 Jan splits at the actual first-Sunday-after-Epiphany
origin: on/after it, this is genuinely week 1 of Time after
Epiphany and takes lectio's own ef-time-after-epiphany-1-<weekday>
(which also can't collide with that season's own later week-1
ferias, since it's the same computation). Before it (0-6 days,
whenever Epiphany doesn't fall on a Saturday), a first attempt
at labelling this "week 1" too, matching a literal reading of
lectio's behaviour, was verified empirically (a throwaway sweep
of the full 1583..9998 domain) to reproduce duplicates in most
years -- so this remainder is its own ef-christmas-2-<weekday>,
a further colitur-only gap.
Verified with the same throwaway sweep: zero duplicate slugs across
1583..9998 after the fix.
2. named's week field was set by hand on some branches (Passion/Palm
Sunday, Easter, Low Sunday, Pentecost and its Vigil, Christ the
King) and left at None on others (Ascension and its Vigil, Corpus
Christi, Sacred Heart) even though all of them sit inside a
numbered season run. named no longer carries a week at all --
temporal now calls week itself for every day, named or not, so "a
named day inside a run carries that run's week" holds by
construction rather than by remembering to set it on each branch.
temporal.mli's week field doc is reworded to state the actual rule.
Covering tests: point assertions for all four Christmastide
sub-stretches; a QCheck property scanning random years for any
duplicate slug within a liturgical year (excluding the deliberate
resumed-Sunday reuse); point assertions for the four previously-None
days now carrying their week (first to fail without the fix: Ascension
Vigil, expected Some 6, got None); a QCheck property asserting
temporal's week equals week for every day of the year, replacing a
prior property whose fallback made it structurally incapable of
detecting an omitted week.
Also: cite RG 91 e18 for the September/Advent Ember days matching
lectio and flag the Lent/Whitsun Ember and Rogation slugs as
colitur-only lectionary gaps inline, matching the existing
Nativity-vigil/octave-day convention; cite RG 117/123/127/128/131 for
season colours and Gaudete/Laetare rose; drop the unreachable
Passiontide arm from the Sunday-rank match (Passiontide has only two
Sundays and both are already named above, so no Passiontide Sunday
ever reaches that fallback).
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
named hardcoded week = None for ef-pentecost-vigil, ef-pentecost and
ef-christ-the-king, unlike the five sibling named Sundays (Easter, Low
Sunday, Passion Sunday, Palm Sunday, Trinity), which already carry the
explicit week number that week computes for the same date. Because these
three sit inside a season run rather than at a run boundary, the omission let
the week number jump on the following Monday without an intervening Sunday
marking the change -- breaking week continuity in every single year in the
domain.
This was found by the new Validate invariant harness (Task 14), which
flagged exactly two failures in every one of the 8416 years 1583..9998, both
on the Monday after one of these days. Season contiguity itself was clean
across the whole domain; only week numbering was affected.
Pentecost and its Vigil are fixed Easter offsets, so they take the literal
values (7 and 8) that week already computes for them. Christ the King's date
varies by year, so the same expression week evaluates is inlined instead,
since week is defined later in the file and cannot be called from named.
Added a general property test, prop_named_week_agrees_with_week, checking
across 200 random years that wherever named gives an explicit week, it
matches what week independently computes for that date -- covering all
sibling entries, not just the three fixed here, so the same drift cannot
silently reappear in a future addition to named.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Ferial ranks per RG 91: I class in Holy Week and the privileged octaves
(entries 7, 10), II class for Advent 17-23 and the Ember days (entry 18), III
class for Advent to 16 December and Lent/Passiontide (entries 22, 25), IV class
per annum (entry 28). Two further divergences from lectio, both from the table:
Advent 17-23 are II class, and the Lenten Ember days are II class rather than
ordinary Lenten ferias. Rogations (RG 80/87) exist at all, which lectio does
not compute. Gaudete and Laetare are rose.
Two corrections against the primary source beyond the task brief's draft.
Entry 7 (verified against the Latin: "feria IV cinerum et II, III et IV
Hebdomadae sanctae") covers only Ash Wednesday and Monday-Wednesday of Holy
Week; Thursday-Saturday are the Sacred Triduum, entry 2, cited separately.
Rogation Monday and Tuesday keep the ordinary ferial rank of their season
(RG 88: "de Litaniis minoribus nihil fit in Officio") rather than a fixed
class, since no RG 91 entry ranks them specially.
A module-type constraint proves Temporal_ef satisfies the kernel RITE contract.
|
| |
|
|
|
|
|
|
|
| |
Task 12 review: add a permanent regression test for floor_div's negative
branch (Ash Wednesday, 4 days before the Lent I origin -- the only date in
the system where it fires), and stop sunday_slug from independently
recomputing the Pentecost-relative week number that week already computes.
A cross-check test pins the two together before the refactor and continues
to guard against future duplication.
|
| |
|
|
|
|
|
|
| |
Week origins are Sundays, so week numbers are constant Sunday-to-Saturday; the
origin is season-specific, which is why Validate must not assume a run starts
at 1. When Easter is early the surplus Sundays after Pentecost resume the
Sundays after Epiphany that Septuagesima cut short, and the last Sunday before
Advent always keeps the 24th (Last) Mass.
|
| |
|
|
|
|
|
|
|
|
|
|
|
|
|
| |
Circumcision (1 Jan) is the Octave Day of the Nativity, RG 91 entry 5, the
same table entry as the Nativity vigil -- not covered by the entries-1-3
group it sat under. Passion Sunday, Palm Sunday and Low Sunday are RG 91
entry 6 (I-class Sundays of Passiontide and Low Sunday); Ash Wednesday is
entry 7 (I-class ferias). All five branches now carry their own citation,
and the function-level comment states the full coverage instead of a
narrower one.
Also corrects the Nativity-octave range from RG 64-70 to RG 63-70, matching
the register's own citation for the octave rules.
Comment-only change; behaviour is unaffected.
|
| |
|
|
|
|
|
|
|
|
| |
The I-class feasts of the Lord (RG 91 entries 1-3), the Nativity, Ascension
and Pentecost vigils (RG 28-34), and the days within the Octave of the
Nativity (RG 64-70). Christ the King is the last Sunday of October per the
1960 calendar, not the OF's last Sunday before Advent.
Rogation Wednesday coincides with the Ascension vigil; with no precedence
framework until Plan 3, temporal emits the higher-ranked vigil.
|
| |
|
|
|
|
|
|
| |
Christmas Time runs to 13 January inclusive (RG 72-73) and time after Epiphany
opens on 14 January (RG 77), diverging from lectio, which starts
time-after-epiphany at 6 January. Holy Saturday stays in Passiontide: the
Easter Vigil is a night Mass, and a per-day calendar assigns a date by the
season governing its day-hours.
|
|
|
Eight seasons in canonical liturgical-year order, each carrying its RG
citation, and the four classes. season_slug_word is deliberately distinct from
season_to_string: slugs are lectionary keys adopted verbatim from lectio,
which calls Paschaltide 'easter' and Christmastide 'christmas'.
|