Skip to content

Part O Iteration 3 — explicit Systems/TPD ventilation route #111

Closed

Description

@michaldengusiak

Status: CLOSED — ITERATION 3 (Systems/TPD foundation + B4 selected-product cooling) ACCEPTED; manufacturer ventilation behaviour MOVED to #123
Integration branch: sow/2026-Q3

Foundation PR1–PR4: COMPLETE
Licensed acceptance: COMPLETE
Persistence/reopen acceptance: COMPLETE
PR5A infrastructure (identity/catalogue/resolver/route policy/orchestration): COMPLETE / MERGED
PR5B selected-product cooling (B4): COMPLETE / ACCEPTED, including real-project acceptance and close/reopen Review (7/7)
PR5A/PR5 manufacturer ventilation behaviour (certified heat recovery, fan SFP/power, B1/B2, bypass/B3): MOVED — see #123

FINAL CLOSEOUT (2026-09-16)

Human programme decision, recorded explicitly per this issue's own closure rule (bottom of this body):
the proven Iteration 3 explicit Systems/TPD route, including the accepted selected-product cooling/B4
route, is complete and accepted. The remaining manufacturer ventilation behaviour — certified heat
recovery, fan SFP/power/heat, B1/B2, and manufacturer bypass/B3 — is deliberately moved to
#123 because its acceptance is blocked on external
manufacturer/EDSL evidence, not on anything implementable in-repo right now. This is the explicit human
decision this issue's closure rule allows, and it satisfies #111's second closure condition.

Final reconciled state:

  • PR1–PR4: COMPLETE / frozen (unchanged from FOUNDATION FROZEN).
  • PR5A infrastructure (SAM#117, SAM_Systems#23, SAM_Tas#56, SAM_UI#102): MERGED.
  • PR5A manufacturer ventilation behaviour (heat recovery, fan SFP/power, B1/B2, bypass/B3): MOVED to
    #123 — blocked on external evidence gates E1/E2 and an open
    EDSL/TAS technical question, not an in-repo blocker.
  • PR5B selected-product cooling (SAM_Systems#24, SAM_Tas#59, SAM_UI#103): COMPLETE + ACCEPTED — B4 =
    B0 Parity MV + the cooling module, 8/8 TM59 Pass on the canonical fixture, 0/8 outcome changes vs B0.
  • Real-project B4 acceptance: COMPLETE — full 1a → 1b → 2 → 2B → 3-B0 → 3-B4 route run on the real
    project; Reference A FAIL, Candidate B FAIL (a valid weather-driven result, not a defect); recirculation
    clamp verified (refusal gone); TM59 NV Criterion 1 seasonal-basis fix (SAM#120) verified not to affect the
    (fully mechanical-route) real-project result.
  • B4 close/reopen Review: COMPLETE, 7/7 acceptance criteria PASS (pairing recovered and restored,
    not rerun; engineering results reproduced exactly; 15/15 ledger stages present; no refusal; zero TAS
    simulation processes during Review; catalogue provenance revalidated). One separate, non-blocking
    evidence-archive finding from this reopen is tracked at
    #122.
  • SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 (TAS Systems sizing order sensitivity): proved a direct PR5B dependency, generically fixed in
    SAM_Tas#57 (native creation order made a deterministic function of the graph alone), CLOSED.
  • SAM_Tas: a 1-day simulation period crashes TSD.exe (0xc0000005) inside Modify.AddResults, surfacing as RPC server unavailable #115 (one-day TSD crash): confirmed separate native debt, not a PR5/Iteration-3 dependency — every
    operating-point and acceptance test uses full-year TSD sources and TPD hour windows. Remains OPEN as its
    own item.
  • TM59 NV Criterion 1 seasonal-basis defect: found and fixed, SAM#120 (Pass/Fail now decided from the
    May–September basis TM59:2017 requires, not the full year).
  • SAM_Tas diagnostic-log seasonal-basis alignment: fixed, SAM_Tas#62 (evidence-log-only, no
    compliance-decision impact).
  • Recirculation-flow clamp: verified on the real project (SAM_Tas#60, re-exercised — the refusal is
    gone).
  • Four-airflow invariant: unchanged and reconfirmed throughout —
    PartFRequiredAirFlow != DesignAirFlow != SelectedEquipmentCapacity != OperatingAirFlow.

Full narrative: see the final closeout comment on this issue, and
SAM/PROJECT_PROGRESS.md, SAM/documentation/PartO-TAS-VALIDATION.md,
SAM/documentation/PartF-HANDOVER.md.


Current programme state (as at FOUNDATION FROZEN + PR5A/PR5B — historical, preserved)

Foundation milestone = PR1–PR4 (frozen, accepted on merged binaries — see the
ITERATION 3 FOUNDATION FROZEN comment).
Manufacturer-aware milestone = PR5 (now split: PR5A infrastructure + PR5B cooling ACCEPTED under this issue;
PR5A/PR5 manufacturer ventilation behaviour MOVED to #123 — see FINAL CLOSEOUT above).

item PR merge into sow/2026-Q3
PR1 — SAM_Systems materialisation SAM-BIM/SAM_Systems#20 89cf139966f4fe426459851d09f052834551792f
PR2 — SAM_Tas no-IZAM source + TPD route SAM-BIM/SAM_Tas#50 5bec3a6df4ac…
PR3 — SAM_Tas ResultantTemperature bridge SAM-BIM/SAM_Tas#51 81d78841de31…
SAM_Tas yearly-profile hour alignment (found in acceptance) SAM-BIM/SAM_Tas#52 1d62f380f0d3f0692b9cf0cc8ecf8b37f93fe375
Generic simulation-result provenance / serialization fix (found in acceptance) #116 553957dc61db876926a5599154770d7aa22f959f
PR4 — SAM_UI orchestration + acceptance SAM-BIM/SAM_UI#100 736e177169db2dd1ab27371dd738443596604c49

SAM #116 is a generic fix discovered during foundation acceptance: an unstated
GroundTemperature round-tripped a .sam save/reload as a stated 0, and a UI presentation-only
parameter was not excluded from the provenance fingerprint, so a reopened Part O run was refused.
It is not a relocation of TAS responsibility into SAM and adds no TPD/TBD/TSD/TAS identifiers.

Related issues: #114 CLOSED (resolved by caller scoping in SAM_UI#100).
#113 CLOSED (proved a direct PR5B dependency; generically fixed in SAM_Tas#57 — see FINAL CLOSEOUT above).
#115 remains OPEN native TAS debt — not encountered on the canonical full-year route and confirmed not a
PR5/Iteration-3 dependency.

Frozen prerequisite:
Iterations 1a / 1b / 2 / 2B

Core invariant:
PartFRequiredAirFlow
!= DesignAirFlow
!= SelectedEquipmentCapacity
!= OperatingAirFlow

REFERENCE ROUTE

SAM
→ existing TBD route / IZAM
→ TSD
→ ResultantTemperature
→ TM59

ITERATION 3 ROUTE

SAM analytical design
│
├─→ SAM_Systems
│ → explicit MVHR systems
│
└─→ SAM_Tas
→ no-IZAM load TBD/TSD

explicit Systems + no-IZAM load
→ TPD
→ Systems simulation
→ ZoneTemperature
→ copy same no-IZAM TBD
→ thermostat bridge
→ second TSD
→ ResultantTemperature
→ TM59

Settled architecture decisions

  • No new TAS-specific references in SAM.
    SAM remains the analytical/design authority.
    TPD/TBD/TSD, TAS identifiers, TAS execution and result extraction belong outside SAM.

  • SAM production changes for the Iteration 3 foundation: none that carry Systems/TAS knowledge.
    The only SAM change (fix: a TAS run's model keeps its simulation-result provenance across .sam save and reopen #116) is the generic simulation-result provenance/serialization fix recorded above.

  • No IZAM contribution in the Iteration 3 Systems route.
    Ventilation is represented by the explicit TPD/TAS Systems network.

  • With the current TAS API semantics:

    • ModelVentilationFlow = true
    • ModelInterzoneFlow = true

    true selects TAS System Modelled behaviour, so corresponding building-model ventilation/interzone flows are ignored.

  • The candidate route must use a newly generated no-IZAM thermal TBD/TSD.
    Do not reuse the frozen Iteration 1a TSD as the Systems load source.

  • The no-IZAM source must:

    • not generate IZAMs;
    • remove inherited IZAMs;
    • remove/zero mechanical ticV contribution;
    • preserve legitimate infiltration and natural-ventilation behaviour;
    • preserve geometry, fabric, shading, weather, occupancy and internal gains.
  • One separate AirSystem per physical analytical AHU/MVHR.
    A SystemEnergyCentre may contain several systems; it is not itself one shared ventilation network.

  • Every room served by an MVHR belongs to that MVHR system:

    • supply-only;
    • extract-only;
    • supply + extract;
    • transfer-only where applicable.
  • Membership and bindings use GUIDs/analytical relationships, never display names.

  • Initial parity operating configuration:

    • continuous operation factor = 1.0;
    • Fan Heat Gain Factor = 0;
    • no active heating treatment;
    • no active cooling treatment;
    • no heat recovery;
    • no manufacturer-specific performance.
  • Heat Gain Factor = 0 is a parity configuration only, not the eventual realistic equipment model.

  • The shipped MV.json is a topology source, not a ready-to-run Part O system.
    It must not be globally modified for this work.

  • Manufacturer-specific MRXBOX/XBC15 behaviour is deferred until the generic Systems route has been proven.
    (The route was proven; PR5A/PR5B built on it; remaining manufacturer ventilation behaviour is now tracked
    at Part O - manufacturer ventilation behaviour: heat recovery, fan performance and bypass #123.)

Temporary ResultantTemperature bridge

Current TAS Systems does not provide the ResultantTemperature required by the Part O assessment.

Temporary SAM_Tas route:

TPD Systems simulation
→ achieved room ZoneTemperature
→ copy of the same validated no-IZAM TBD
→ set both heating and cooling thermostat profiles to the achieved room-air temperature
→ simulate that copied TBD
→ obtain ResultantTemperature
→ existing TM59 calculator

The bridge is entirely a SAM_Tas concern.

When TAS exposes native Systems ResultantTemperature, replace only:

TPD
→ ZoneTemperature
→ TBD thermostat bridge
→ second TSD

with:

TPD
→ native ResultantTemperature

SAM, SAM_Systems materialisation, equipment authority and TM59 assessment must not change.

Implementation plan

PR5 — manufacturer-aware behaviour (final reconciliation)

  • PR5A infrastructure — SAM#117, SAM_Systems#23, SAM_Tas#56, SAM_UI#102 (identity plumbing,
    catalogue v1/v2, COM-free resolver, per-AHU unit settings, fan-heat route policy, exchanger
    ExchCalcType conversion/read-back, selected-product orchestration). MERGED.
  • PR5B selected-product cooling (B4) — SAM_Systems#24, SAM_Tas#59, SAM_UI#103 (same-AirSystem
    recirculation branch, damper-controlled control law, DX gate, clamped table, recirculation-flow clamp
    SAM_Tas#60). MERGED and ACCEPTED — canonical fixture 8/8 TM59 Pass, 0/8 outcome changes vs B0; real-project
    acceptance FAIL→FAIL (valid, weather-driven); B4 close/reopen Review 7/7 PASS.
  • SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 dependency — proved and generically fixed, SAM_Tas#57. CLOSED.
  • PR5A/PR5 manufacturer ventilation behaviour (certified heat recovery, fan SFP/power, B1/B2,
    manufacturer bypass/B3) — MOVED, by explicit human decision, to
    #123.
    Blocked on external evidence gates E1/E2 and an open
    EDSL/TAS technical question — not an in-repo blocker. NOT part of this issue's closure scope.

Potential later work (superseded by #123 for anything manufacturer-ventilation-specific):

The foundation did not wait for PR5. The B0 parity configuration remains reproducible as a diagnostic
control throughout PR5A/PR5B.

PR1 API direction

The SAM_Systems seam must remain generic; Part O is only a caller.

Preferred conceptual API:

MaterialiseMechanicalVentilation(...)

Inputs:

  • analytical design snapshot;
  • explicitly supplied SystemEnergyCentre topology template;
  • generic materialisation settings.

Output:

  • isolated materialised SystemEnergyCentre;
  • explicit refusals;
  • deterministic analytical→Systems GUID bindings.

Important:

  • design terminal airflow is authoritative;
  • do not use Part F requirement as design airflow;
  • do not use equipment capacity as design airflow;
  • do not rebalance or repair the analytical design;
  • no partial-success graph;
  • no TAS identifiers.

The generic API may accept an ordinary YearlySchedule.
The Part O parity fixture supplies an 8760-hour constant 1.0 schedule;
constant operation should not unnecessarily become a permanent restriction
of the generic SAM_Systems API.

Generated identity must be deterministic and enumeration-order independent.
Reuse an established SAM/SAM_Systems deterministic GUID convention if one
exists rather than introducing a new UUID mechanism solely for this feature.

Parity / acceptance reference

Reference A — frozen Iteration 1a

SAM analytical design
→ existing TBD/IZAM route
→ TSD
→ ResultantTemperature
→ TM59

Candidate B — Iteration 3 foundation

same analytical design
→ no-IZAM thermal source
+
explicit SAM_Systems MVHR representation
→ TPD Systems simulation
→ ZoneTemperature
→ no-IZAM ResultantTemperature bridge
→ TM59

The comparison must prove first:

  1. identical engineering inputs;
  2. correct system membership;
  3. correct design flows/balance;
  4. no duplicate ventilation;
  5. complete annual results.

Then compare thermal results using useful diagnostics such as:

  • mean bias;
  • RMSE;
  • maximum absolute difference;
  • relevant exceedance hours;
  • TM59 criteria/verdicts.

Do not require bit-identical temperatures merely because the design
airflow values are identical.

Known narrow blockers/debt

Only address these if they block the new route:

  • ZoneLoads fixed-index enumeration defect — expected PR2 fix. RESOLVED (PR2).
  • TPD Simulate false-positive — PR2 must validate real execution/results. RESOLVED (PR2).
  • SystemSpaceResult name/identity ambiguity — new route must use explicit bindings. RESOLVED (PR2).
  • arbitrary first-related VentilationSystem ZoneGroup issue — do not use that mechanism for Iteration 3 membership; do not broaden this into a general redesign unless required. Not needed by the accepted route.

Progress log

Each merged PR should add a comment here containing:

  • PR link;
  • reviewed head SHA;
  • merge SHA;
  • test results;
  • licensed TAS evidence where applicable;
  • next checklist item.

Do not use Closes #111 on any PR.

See the comment history below for the full progress log through PR5A/PR5B, the real-project acceptance, and
the final closeout comment for the full evidence trail.

Closure rule

PR1–PR4 = foundation milestone (FROZEN). PR5 = manufacturer-aware milestone.

Close this issue only when PR5 / full Iteration 3 is accepted — unless a later
human decision deliberately moves PR5 to a separate tracker.

This condition is now satisfied. The explicit Systems/TPD Iteration 3 route, including the accepted
selected-product cooling/B4 route, is complete and accepted (PR1–PR4 frozen; PR5A infrastructure merged;
PR5B selected-product cooling accepted, including real-project acceptance and the B4 close/reopen Review
7/7). A human decision, recorded above under FINAL CLOSEOUT, deliberately moves the remaining
manufacturer-ventilation behaviour (certified heat recovery, fan SFP/power, B1/B2, bypass/B3) to a
separate tracker, #123, because it is blocked on external
evidence, not on anything left to do in this repository set. #111 is CLOSED.

Activity

  1. michaldengusiak commented on Sep 9, 2026

    @michaldengusiak
    Author

    Final architecture review confirmation — 2026-09-09

    Reviewed the canonical issue against the final Aster architecture report. No material replan is required; the issue body is consistent with the accepted Iteration 3 architecture.

    Two clarifications are worth preserving for implementation:

    1. “No new TAS-specific references in SAM” is the Iteration 3 boundary. Existing SimulationResultProvenance.Path_TSD is acknowledged legacy boundary debt and is outside this Iteration 3 foundation scope; do not use it as precedent for adding new TPD/TBD/TSD/TAS identifiers to SAM.
    2. PR2 must create a genuinely clean no-IZAM source, not merely rely on the TPD System Modelled flags: use the existing no-IZAM workflow seam (AddIZAMs = false), remove inherited IZAMs, neutralise mechanical ticV contribution while preserving infiltration / legitimate natural ventilation, and explicitly pair the generated no-IZAM TBD with its TSD. PR3’s thermostat bridge must start from that explicitly identified same no-IZAM TBD, not from basename/name guessing.

    Everything else in #111 remains the frozen plan. Next implementation item: PR1 — SAM_Systems generic mechanical-ventilation materialisation.

  2. michaldengusiak commented on Sep 9, 2026

    @michaldengusiak
    Author

    Pre-start completeness review — closure and PR gates

    Before PR1 starts, one programme-level clarification is required so this issue truly remains the canonical tracker for all of Iteration 3, not only the foundation.

    Closure semantics

    The current PR1→PR4 sequence is the Iteration 3 foundation milestone. After PR4 + native acceptance, record FOUNDATION FROZEN, but do not close #111 if the intended definition of Iteration 3 includes selected-manufacturer equipment behaviour.

    The issue should remain open through the deferred manufacturer-aware milestone (currently PR5, split further only if implementation evidence proves that necessary): selected product identity remains authoritative; product-specific parameters may affect fan/heat-recovery/bypass/cooling/control behaviour only where supported; capacity must never become operating airflow; no silent product reselection; and topology variants are allowed only where physical topology genuinely differs.

    Close #111 only after either:

    1. that manufacturer-aware milestone is accepted and Iteration 3 is fully frozen; or
    2. a deliberate human decision explicitly defines Iteration 3 as the foundation only and moves manufacturer behaviour to a separately tracked programme.

    PR1 exit gate — SAM_Systems

    In addition to the body contract, PR1 must source-verify before implementation:

    • whether YearlySchedule copy currently truncates an annual schedule to 24 values; fix narrowly only if reproduced and directly blocking materialisation;
    • deep isolation of the supplied SystemEnergyCentre template/output, including mutable SystemSpace/flow objects;
    • reuse of an existing deterministic SAM/SAM_Systems identity convention if available rather than inventing a new GUID scheme;
    • no global modification of shipped MV.json;
    • one separate AirSystem per physical analytical AHU, with all served spaces and explicit transfer topology;
    • 5,000-space structural scaling evidence with no O(n²) model/name scans.

    PR1 completes only when Release build + full SAM_Systems regression + focused materialisation tests + deterministic/scaling tests are green and the source analytical model/template remain unchanged.

    PR2 exit gate — SAM_Tas

    PR2 owns the clean no-IZAM load source and TPD execution. It must also close only the narrow defects that block this route:

    • ZoneLoads fixed-index enumeration;
    • TPD Simulate false-positive success;
    • SystemSpaceResult name/identity ambiguity via explicit GUID bindings.

    Native evidence must prove no IZAM/mechanical ticV contribution, preserved legitimate infiltration/NV, separate AHU systems, correct terminal/transfer/fan flows, complete annual results and API/native agreement for ZoneTemperature.

    PR3 exit gate — SAM_Tas

    The temporary ResultantTemperature bridge must:

    • start from the explicitly paired same no-IZAM TBD, never basename/name guessing;
    • map rooms by explicit identity;
    • require complete finite hourly series for the actual simulation period;
    • write both heating and cooling thermostat limits;
    • verify achieved air temperature follows the imposed series;
    • expose a replaceable SAM_Tas ResultantTemperature-provider seam so future native TAS Systems ResultantTemperature removes only this bridge.

    PR4 exit gate — SAM_UI

    PR4 is orchestration/presentation only: stage execution, refusals, artifact lineage, A/B evidence and the unchanged TM59 authority. It must not create a second engineering authority or move TAS knowledge into SAM.

    After PR4 + licensed acceptance, record ITERATION 3 FOUNDATION FROZEN and then proceed to the manufacturer-aware milestone if full Iteration 3 remains the programme goal.

    This comment supplements the frozen architecture in the issue body; it does not reopen it.

  3. michaldengusiak commented on Sep 9, 2026

    @michaldengusiak
    Author

    PR1 planning complete — READY TO BUILD

    Approved implementation plan for PR1 — SAM_Systems generic deterministic mechanical-ventilation materialisation attached.

    Plan was source-verified against current sow/2026-Q3 in SAM_Systems and SAM and incorporates the final multi-AHU, deterministic lineage, isolation, transfer-topology and 5,000-space scaling decisions.

    Status: READY TO BUILD

    Implementation must treat this attached plan and SAM #111 as the contract. Do not reopen architecture unless BUILD reveals a genuine source contradiction.

    No branch, production edits, commit or PR was created during planning.

    PR1_SAM_Systems_Approved_Plan_2026-09-09.zip

  4. SAM-BIM-AI commented on Sep 11, 2026

    @SAM-BIM-AI

    ITERATION 3 FOUNDATION FROZEN

    PR1 → PR4 (this issue's foundation milestone) are all merged and the licensed acceptance is green on
    merged binaries. Recording the closeout; this issue stays open for the deferred manufacturer-aware
    milestone (PR5).

    SAM PR #116 — simulation-result provenance round trip

    • fix: a TAS run's model keeps its simulation-result provenance across .sam save and reopen #116
    • Reviewed head: d43a4ff92f7ce2996175a5ab2939f4078e34daab
    • Merge commit: 553957dc61db876926a5599154770d7aa22f959f into sow/2026-Q3
    • SAM.Tests: 2120/2120
    • Purpose: an unstated GroundTemperature field round-tripped a .sam save/reload as a stated 0
      instead of staying "not stated", and SAM_UI's own presentation-only "UI Geometry Settings" parameter
      was not excluded from the fingerprint — together these made PartORun.Restore refuse a persisted Part
      O run that had not actually changed. Both fixed; simulation-result provenance is now stable across
      .sam reopen for a model carrying TAS results.

    SAM_UI PR #100 — Iteration 3 (A/B) orchestration foundation

    Licensed merged-state evidence

    Canonical fixture (SHA-256 A7E09A25AE29C7DBB4C690D747A96FCD9F110CA27FB4DC2ABE816755368D7E4B), run
    against the merged SAM and rebuilt SAM_UI:

    • Reference A Pass, Candidate B Pass
    • 0 of 8 TM59 criterion outcomes differ (bias +0.373 K, RMSE 0.834 K, max 2.909 K)
    • 3 physical MVHR air systems, 8 bound rooms, Corridor_1 unbound, 14 directed legs
      (3 supply / 6 extract / 5 transfer)
    • zero design-airflow delta against the prepared design's own terminals
    • complete 8×8760 ZoneTemperature and ResultantTemperature series
    • Review works in-session and after killing and relaunching the application from the same .sam,
      reproducing the same statistics
    • no TAS simulation process (TBD/TPD/TAS3D) observed during either Review — only TSD result
      readers, polled continuously throughout both runs

    Full detail: SAM_UI/documentation/evidence/PR4-ITERATION3-FOUNDATION.md §5.6.1 (SAM_UI, sow/2026-Q3).

    SAM #114

    Closed: #114 (comment) — resolved by
    caller/orchestration identity scoping in PR #100, demonstrated on the canonical fixture above.

    Status

    PR1 MERGED   PR2 MERGED   PR3 MERGED   #52 MERGED   #116 MERGED   PR4 MERGED
    

    ITERATION 3 FOUNDATION FROZEN.

    Next programme item: PR5 — manufacturer-aware behaviour (selected-product parameter overrides, heat
    recovery, fan behaviour/power, bypass/control, trim cooling/cooling modules, and physical topology
    variants only where genuinely required by manufacturer evidence). The frozen invariant still holds and is
    unchanged by anything in this closeout:

    PartFRequiredAirFlow != DesignAirFlow != SelectedEquipmentCapacity != OperatingAirFlow
    

    This issue remains open through PR5.

  5. SAM-BIM-AI commented on Sep 11, 2026

    @SAM-BIM-AI

    PR5 PLANNING — investigation complete (no code)

    ITERATION 3 FOUNDATION FROZEN. PR5 investigation is complete against sow/2026-Q3 (SAM 553957dc, SAM_Systems 89cf1399, SAM_Tas 1d62f380, SAM_UI 736e1771). No branch, commit or PR was made.

    Milestone shape: PR5 splits into two justified slices.

    • PR5A maps the selected product to generic Systems parameters: fan power/heat, heat recovery, and a declared bypass/supply-limit mode. It uses constant airflow (OperatingAirFlow = DesignAirFlow) and switches the topology MV → the existing shipped MVRE.
    • PR5B adds DX trim cooling. It brings a new active component, a room-temperature control loop and variable OperatingAirFlow above design, which extends the four-airflow contract. It depends on native control behaviour nothing yet proves, and it depends on PR5A.

    First canonical product: Nuaire MRXBOXAB-ECO5-AECV (MR-ECO-COOL-V). It is the only domestic entry (150/150 l/s), the smallest capable unit for every canonical dwelling, and the only one carrying cooling-module data.

    Source-verified

    • Selected identity already lives on AirHandlingUnitParameter.VentilationUnitReference and is persisted and reopenable. Candidate B currently carries none of it.
    • It can be carried by GUID: AHU → reference → catalogue Matches → unit settings → PR1 binding. No names are involved.
    • No existing code uses capacity as an airflow. Capacity is only a selection gate or the 2B ceiling.
    • The parity HeatGainFactor = 0 is imposed in SAM_Tas (Modify.GroundVentilationFans), so PR5 needs a route policy there and B0 keeps it as the default.
    • TPD interop (reflected):
      • Exchanger has SensibleEfficiency/BypassFactor/Setpoint as ProfileData, with table modifiers on ODB/EDB/EDB2/EFlow. Flags offers HeatingOnly/AdjustForOptimiser. Calc methods are Simple/NTU/Duty.
      • Fan has HeatGainFactor, Pressure, OverallEfficiency and FixedSpeed/VariableSpeed control. The measured load is Q·dp/η, so SFP maps to dp/η.
      • DXCoil has CoolingSetpoint, a scalar CoolingDuty and Normal/OnOff control.
      • SAM_Tas does not write ExchCalcType, which must be fixed.
    • Manufacturer bypass thresholds are unpublished for both products. B3 is therefore a declared, deterministic mode, not a claimed manufacturer sequence.
    • The manufacturer cooling capacity map cannot be carried by TAS's scalar duty.

    Major fail-closed decisions

    • Evidence gate. Certified MRXBOX heat-recovery efficiency and SFP (PCDB / EN 13141-7) are not in SAM and not retrievable online, where Nuaire states only "up to 95%". B1/B2 on the real product refuse until those values are transcribed with a traceable source.
    • The project test product refuses any behaviour.
    • An undersized unit refuses. There is no reselection.
    • A missing field or an out-of-domain value refuses.
    • A native read-back mismatch refuses.
    • TAS sizing refusal (SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113) refuses. Nothing is reordered to pass sizing.
    • B0 stays byte-identical and hash-pinned, and is paired with every B-variant as the diagnostic control.

    #113 becomes more likely with MVRE, because new template GUIDs change creation order. It stays OPEN and is not fixed in PR5 unless the canonical B-variant is refused. #115 has no dependency: operating-point tests use full-year TSD sources and TPD hour windows, never 1-day periods.

    Next action: PR5A implementation. Merge order is SAM → SAM_Systems → SAM_Tas → SAM_UI. Licensed operating-point tests P0/A–D run before any annual run.

    Plan document: SAM_UI/documentation/plans/PR5-MANUFACTURER-AWARE-PLAN.md. It is committed with PR5A's first SAM_UI commit and reproduced in full below.

    This issue stays OPEN. PR5 stays [ ]. #113 and #115 stay OPEN.

    Full PR5 plan (source map, data model, Systems/TAS mapping, control, four-airflow map, fail-closed rules, test matrix, evidence, UI, PR plan, exit gates, 16 answers)

    SAM #111 — PR5 manufacturer-aware MVHR: implementation plan

    Date: 2026-09-11 · Status: PLAN — no production code · Tracker: #111

    Source-verified against sow/2026-Q3:

    repo SHA
    SAM 553957dc61db876926a5599154770d7aa22f959f
    SAM_Systems 89cf139966f4fe426459851d09f052834551792f
    SAM_Tas 1d62f380f0d3f0692b9cf0cc8ecf8b37f93fe375
    SAM_UI 736e177169db2dd1ab27371dd738443596604c49

    TAS capability claims below are from reflection over SAM_Tas/references_buildonly/Interop.TPD.dll, from
    the SAM_Tas conversion code, and from the licensed PR2 evidence. A property existing on the interop is
    not proof of simulated behaviour; anything that needs proof is marked LICENSED EXPERIMENT.


    0. Decisions in one screen

    1. PR5 splits into two slices, and the split is justified.

      • PR5A: selected product → generic Systems parameters. It covers heat recovery, fan power and heat, and a bypass/supply-limit mode. Airflow is constant and equal to design. There is one existing topology variant, MV → MVRE.
      • PR5B: the trim-cooling module. It adds a new active component (a DX coil), a control loop driven by room temperature, and variable OperatingAirFlow above DesignAirFlow. It also couples a refrigerant plant.

      PR5B is not simply "more parameters". It extends the four-airflow contract, which PR5A must leave untouched, and it depends on native TAS control behaviour that nothing yet proves. PR5B depends on PR5A's identity-to-graph plumbing and on the MVRE route.

    2. First canonical product: Nuaire MRXBOXAB-ECO5-AECV (MR-ECO-COOL-V).

      • It is the only domestic catalogue entry, 150/150 l/s, Rank 10.
      • It is the smallest capable product for every canonical dwelling; each canonical fan runs at 44 l/s.
      • It is the only product carrying cooling-module data.
    3. The certified heat-recovery efficiency and SFP of that product are NOT in SAM and were not retrievable online. Nuaire publishes "up to 95%", and retail pages quote "up to 90%". Both are marketing and are unusable. PR5A therefore opens with an evidence gate (E1/E2). Until those values are transcribed from a certified source, B1/B2 on the real product refuse.

    4. B0 parity stays byte-identical and remains the default control. Manufacturer behaviour is additional configuration over the same route. It is never a replacement.

    5. No manufacturer-name conditionals anywhere. Product data flows as follows:

      • SAM vocabulary.
      • The SAM resolver, which is COM-free.
      • Generic MechanicalVentilationUnitSettings, keyed by AHU GUID.
      • SAM_Systems materialisation.
      • SAM_Tas conversion.
    6. SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 is not fixed in PR5. MVRE makes it more likely, so PR5 keeps failing closed on a TAS sizing refusal. SAM_Tas: a 1-day simulation period crashes TSD.exe (0xc0000005) inside Modify.AddResults, surfacing as RPC server unavailable #115 has no dependency.


    A. Current source map

    Equipment authority (Iteration 2, reused unchanged unless noted)

    concern location notes
    product vocabulary SAM/SAM.Analytical/Classes/System/VentilationUnitTemplate.cs, VentilationUnitReference.cs, VentilationUnitPerformanceTable/Axis/Output.cs, FlowFractionControlCurve.cs, PerformanceJson.cs SAM owns vocabulary; carries no product list
    capacity descriptor VentilationUnitCapacityDescriptor.cs, Query/CapacityDescriptor.cs capacity only
    catalogue file SAM_Systems/files/resources/Analytical/Systems/VentilationUnit/VentilationUnitCatalogue.JSON (VentilationUnitCatalogue:v1) 2 products
    catalogue reader SAM_Systems/.../SAM.Analytical.Systems/Query/VentilationUnitTemplates.cs one bad entry refuses all; exact schema tag
    session wrapper SAM_UI/WPF/.../Classes/PartO/VentilationUnitCatalogue.cs read-only; exposes descriptors, not templates
    selection rule SAM/.../Query/CapableVentilationUnits.cs (SelectSmallestCapableVentilationUnit), Modify/SelectVentilationUnit.cs, called from Modify.PreparePartOIteration the single selection authority
    manual assignment SAM/.../Modify/AssignVentilationUnit.cs engineer authority
    selected identity AirHandlingUnitParameter.VentilationUnitReference on the dwelling's AirHandlingUnit (Enums/Parameter/AirHandlingUnitParameter.cs); read by Query.SelectedVentilationUnitReference (Query/AirHandlingUnitDesignDuty.cs:113) identity, never capacity/duty; persisted in .sam
    feasibility Query.IsVentilationUnitSufficient (AirHandlingUnitDesignDuty.cs:196), AirHandlingUnitDesignDuty gate only
    project preselection PartOEquipmentSelection.cs (mode + allowed pool, identities only) project metadata
    project test product PartOProjectTestVentilationUnit.cs (name + 2 capacities, no performance by design) must refuse any PR5 behaviour
    2B design targeting Modify/ApplyTargetedDesignAirFlow.cs, EvaluateDesignAirFlowCapacityEnvelope.cs capacity is a ceiling on an engineer-targeted change, never assigned

    Iteration 3 foundation (touched as stated)

    repo file / member PR5 action
    SAM_Systems Create/MechanicalVentilation.cs (energy-centre key incl. schedule type/name, :322-323) reuse; B0 key unchanged
    SAM_Systems Create/MechanicalVentilationAirSystem.cs (template subgraph re-key; fans get settings schedule :94) extend: apply per-unit settings to re-keyed fan/exchanger copies
    SAM_Systems Classes/MechanicalVentilationSettings.cs (schedule, name, in-room components) extend: UnitSettings
    SAM_Systems files/.../SystemEnergyCentre/MV.json (2 fans, dampers, no exchanger) / MVRE.json (Exchanger 1: Simple, sensible 0.7, latent 0, AdjustForOptimiser, 2 fans), CapabilityIndex.JSON (MVRE = "SAM's MVHR") read only, never modified
    SAM_Tas SAM.Analytical.Tas.TPD/Create/SystemVentilationRoute.cs extend: route options
    SAM_Tas Modify/GroundVentilationFans.cs (forces HeatGainFactor = 0, reads back; checks 8760 operable hours) extend: policy ClearToZero (B0 default) / FromSystemsGraph
    SAM_Tas Convert/ToTPD/Fan.cs (writes OverallEfficiency, HeatGainFactor, Pressure, flows, Capacity, ControlType, PartLoad, schedule) reuse
    SAM_Tas Convert/ToTPD/Exchanger.cs (writes type, sensible/latent eff., setpoint method/value, electrical load, duty, BypassFactor, flags; does not write ExchCalcType, writes ExchLatType twice) fix: write + read back ExchCalcType
    SAM_Tas Create/SystemVentilationConversionContext.cs, Modify/MaterialiseVentilationDutyCarriers extend: exchanger as pass-through in intent/reconciliation
    SAM_Tas Convert/ToTPD/DXCoil.cs, CoolingCoil.cs, Controller.cs PR5B
    SAM_UI WPF/.../Classes/PartO/PartOIteration3Pipeline.cs (Ventilation_Template = "MV"; "no heat recovery, fan heat, equipment selection… configured") extend: behaviour mode
    SAM_UI WPF/.../Query/PartOIteration3OperatingSchedule.cs ("Part O continuous operation", 8760×1.0) reuse unchanged
    SAM_UI WPF/.../Modify/RunPartOIteration3.cs, SAM_UI/SAM.Analytical.UI/Classes/PartO/PartOIteration3{Record,Ledger,Comparison,Result,Artifacts}.cs, PartORun.cs extend: B-variant + equipment evidence
    SAM_UI PartOIteration3SystemScope.cs (#114 scoping) reuse unchanged

    No Iteration 3 file references VentilationUnitReference today, so Candidate B carries no product identity. That is the core gap PR5 fills.


    B. Equipment data model

    Existing fields (catalogue v1)

    field MRXBOXAB-ECO5-AECV (MR-ECO-COOL-V) XBC15 used by engineering today
    VentilationUnitReference (Manufacturer/Model/Reference) Nuaire / MRXBOXAB-ECO5-AECV / MR-ECO-COOL-V Nuaire / XBC15 / – yes — identity
    CoolingModuleModel MR-ECO-COOL-V – display
    Source MRXBOX Hybrid Cooling brochure v.1 Jul 2022 pp.6-7 XBOXER XBC catalogue 029 2085 82002 (2024) p.18 validity gate
    Maximum{Supply,Extract}FlowRate_Lps 150/150 (fan curve 1 free-air) 190/190 (100% row, 0 Pa) yes — selection + 2B ceiling
    Rank 10 20 yes — tie-break
    PerformanceTable ExternalDB {29,32,34} °C × EnteringDB {23..26} °C × AirFlow {50..120} l/s → SupplyAirTemperature °C, CombinedCoolingCapacity kW ("TYPICAL") ESP {0..700} Pa → AirFlowRate m³/s, SFP W/(l/s) (both fans, 100% speed) dormant
    FlowFractionByControlTemperature 22→26 °C : 0.3→1.0, ClampToDomain absent dormant
    electrical (text only, in Source) curves 319/167/77 W 340 W input w/o heater none

    Required new fields (catalogue schema VentilationUnitCatalogue:v2; reader accepts v1 = "no behaviour data")

    All fields are optional. An absent field means not stated, and a behaviour needing it refuses. Every table uses the existing
    VentilationUnitPerformanceTable grammar: raw published units, no conversion on the way in, interpolation
    only at use under an explicit PerformanceDomainPolicy.

    new field (SAM vocabulary) shape needed for authority / evidence
    HeatRecoveryPerformance table: AirFlowRate [l/s] → SensibleHeatRecoveryEfficiency [-]; + EfficiencyBasis enum (SupplyTemperatureEfficiency only, first slice) + Standard text B2 certified (SAP PCDB / EN 13141-7 / Eurovent). MRXBOX: UNKNOWN. XBC15: UNKNOWN (curves only)
    FanPerformance table: AirFlowRate [l/s] → SpecificFanPower [W/(l/s)], SfpBasis = TotalBothFans B1 certified PCDB SFP (domestic) or manufacturer table. MRXBOX: UNKNOWN. XBC15: published, but indexed on ESP, not airflow, so it is unusable without a stated design ESP and refuses in PR5A
    SummerBypass { Kind: None / Automatic100Percent / Modulating, PublishedThresholds: nullable, ControlDescription } B3 labelling MRXBOX: "automatic 100% bypass", thresholds UNKNOWN. XBC15: "100% integrated summer bypass… integrated temperature sensors and pre-defined algorithm", thresholds UNKNOWN
    CoolingModulePerformance (PR5B) move/alias of the existing cooling PerformanceTable + CoolingControl { SetpointDefault_C, SetpointRange_C, AirflowOnCooling } B4 MR-ECO-COOL-V user guide (manuals.plus, 26 Jun 2024): setpoint default 23 °C, range 20–40 °C, "ventilation rate will increase to a level above the boost rate", min on 1 min / off 5 min. Capacity map: brochure (TYPICAL). EER, sensible/latent split, humidity basis: UNKNOWN

    Identity and persistence semantics

    • Identity stays where it is. The authority is AirHandlingUnitParameter.VentilationUnitReference, which is already persisted and reopenable, as PartOEquipmentSelectionPersistenceTests pins. No identity moves into Systems or TAS.

    • Carriage into Candidate B is by identity, never by name. The chain runs as follows:

      1. The analytical AHU GUID gives its reference.
      2. The reference resolves the catalogue template through VentilationUnitReference.Matches, the existing identity comparison.
      3. The AHU GUID keys the unit settings.
      4. PR1's MechanicalVentilationBinding maps the AHU GUID to the AirSystem GUID.

      No space, system or unit display name takes part.

    • The capacity number is never persisted beside the identity, as today. Each run persists the resolved behaviour values it used as run evidence. Those values are not model engineering; see section I.

    • The project test product has no behaviour data, by design. B1+ refuses for an AHU assigned to it; B0 still runs.


    C. Systems mapping (selected unit → generic SAM_Systems)

    New generic type, SAM_Systems, no product names:

    MechanicalVentilationUnitSettings            (per analytical AHU GUID)
      HeatRecoverySensibleEfficiency   double   NaN = leave template exchanger untouched
      HeatRecoverySupplyLimit_C        double?  B3 only (see E)
      SupplyFanPressure_Pa, ExtractFanPressure_Pa, FanOverallEfficiency
      SupplyFanHeatGainFactor, ExtractFanHeatGainFactor
    MechanicalVentilationSettings.UnitSettings : IReadOnlyDictionary<Guid, MechanicalVentilationUnitSettings>
    
    resolved product value (SAM resolver) generic setting applied to (re-keyed copy)
    ε(OperatingAirFlow) from HeatRecoveryPerformance HeatRecoverySensibleEfficiency the unit's single SystemExchanger.SensibleEfficiency; LatentEfficiency = 0; ExchangerType = Simple; ExchangerCalculationMethod = Simple; HeatingOnly = false; AdjustForOptimiser = false (MVRE has no optimiser)
    SFP_total(OperatingAirFlow) from FanPerformance SupplyFanPressure_Pa = ExtractFanPressure_Pa = 1000 × SFP_total / 2, FanOverallEfficiency = 1 the unit's supply and extract SystemFan.Pressure / OverallEfficiency. TAS fan load is Q·dp/η, measured in PR2-FAN-OPERATION.md §4, so the two fans' load sum is Q·SFP_total. The equal split is a declared simplification: the source publishes the total only. It is recorded as such in evidence
    declared fan-heat fraction (see F) Supply/ExtractFanHeatGainFactor SystemFan.HeatGainFactor
    capacity nothing not written into the graph; SystemFan.Capacity keeps the template value and is asserted equal to B0

    Rules

    • The template is chosen by the caller. B0 uses MV, unchanged. B1+ uses the shipped MVRE, the existing SAM MVHR topology per CapabilityIndex.JSON. That is a genuine physical topology variant: an MVHR has a heat exchanger. MV.json and MVRE.json are both read-only.
    • The materialiser refuses in each of these cases:
      • a unit setting requests heat recovery and the unit's air-system copy does not contain exactly one SystemExchanger;
      • the supply and extract fan cannot each be identified as exactly one fan by graph position, meaning the supply path to the prototype space's connector 0 versus the extract path from connector 1. Names such as "Fresh Air Fan" are never used;
      • a unit setting keys an AHU that is not materialised, or a materialised AHU has no setting while UnitSettings is non-empty. That second case prevents a partially configured graph.
    • B0 invariance. When UnitSettings is empty, the code path, the energy-centre key and every derived GUID are identical to PR1. This is asserted by hashing the serialised graph against PR1's output.

    D. TAS mapping

    generic Systems property SAM_Tas native TPD (reflected) status
    SystemFan.HeatGainFactor Convert.ToTPD(SystemFan) writes it; GroundVentilationFans overwrites to 0 Fan.HeatGainFactor : double SUPPORTED — needs SAM_Tas policy (FromSystemsGraph)
    SystemFan.Pressure, OverallEfficiency written Fan.Pressure, Fan.OverallEfficiency : ProfileData SUPPORTED NOW (load = Q·dp/η measured)
    SystemFan.FanControlType, MinimumFlowFraction, PartLoad written ControlType (FixedSpeed/VariableSpeed), MinimumFlowFraction, PartLoad : ProfileData SUPPORTED; variable-speed control = LICENSED EXPERIMENT (PR5B)
    fan schedule Modify.SetSchedule by name SetSchedule, yearly table SUPPORTED NOW (8760 read-back)
    SystemExchanger.SensibleEfficiency written Exchanger.SensibleEfficiency : ProfileData (modifiers: Yearly/Schedule/Table/Curve/Lua) SUPPORTED — needs reconciliation + ε semantics experiment
    ExchangerCalculationMethod not written Exchanger.ExchCalcType (Simple/NTU/Duty) NEEDS SAM_Tas CONVERSION
    SystemExchanger.BypassFactor written Exchanger.BypassFactor : ProfileData SUPPORTED as a property; control by table modifier on ODB/EDB/EDB2 = LICENSED EXPERIMENT
    SetpointMode + Setpoint written SetpointMethod (None/On), Setpoint : ProfileData SUPPORTED as a property; supply-limit semantics = LICENSED EXPERIMENT
    HeatingOnly flag written tpdExchangerFlagHeatingOnly SUPPORTED; not summer bypass (it disables coolth recovery, the wrong direction for overheating) — not used
    heating treatment DisplaySystemHeatingCoil → HeatingCoil Setpoint, Duty, Efficiency, MaximumOffcoil SUPPORTED, but no heating treatment is physically present on either product in scope, so it is not used (XBC LPHW/electric heater is an option not in the catalogue)
    DX trim cooling DisplaySystemDXCoil → DXCoil (needs refrigerant group) CoolingSetpoint : ProfileData, CoolingDuty : SizedVariable, ControlMethod (Normal/OnOff), BypassFactor, Min/MaxOffcoil NEEDS SAM_Systems topology + SAM_Tas mapping; behaviour = LICENSED EXPERIMENT (PR5B)
    chilled-water cooling CoolingCoil (needs cooling group/chiller) Setpoint, Duty, BypassFactor, MinimumOffcoil not the physical product — not used
    capacity-limited cooling – CoolingDuty is a scalar SizedVariable (Value/Size), with no modifiers the manufacturer capacity map is NOT REPRESENTABLE directly; a fixed rated duty is
    off-coil target from the manufacturer's supply-temperature map – CoolingSetpoint ProfileData table modifier on ODB, EDB, EFlow (axes count unverified) LICENSED EXPERIMENT
    sensible vs latent cooling – BypassFactor (coil contact), latent implicit UNCERTAIN; no manufacturer latent data
    room-temperature control Convert/ToTPD/Controller.cs Controller with SensorType incl. tpdThermostatSensor, tpdTempSensor; ControlType Normal/Max/Min/If/Outdoor… LICENSED EXPERIMENT (per-system ISystem.Simulate, multi-room unit)
    variable operating airflow – fan VariableSpeed + controller, or zone FlowRate ProfileData LICENSED EXPERIMENT; four-airflow extension (PR5B)
    native results for evidence fan: GetResultsData var 9 (Load) only, measured in PR2 exchanger/coil variables unmapped LICENSED EXPERIMENT P0 (probe, as PR2 did for fans)
    native ResultantTemperature – – NOT SUPPORTED (the PR3 bridge remains)

    E. Control semantics

    behaviour PR5A (B1–B3) PR5B (B4)
    normal operation fan schedule "Part O continuous operation", 8760×1.0, constant speed; fans derive duty from attached zones (AllAttachedZonesFlowRate), i.e. OperatingAirFlow = DesignAirFlow unchanged baseline, overridden by cooling mode only
    heat recovery constant ε at the design operating airflow, from certified data; Simple exchanger; latent 0 same
    bypass B3 = a declared, deterministic mode, NOT a manufacturer sequence, because neither product publishes its thresholds. Mode SupplyLimit: exchanger SetpointMethod = On, Setpoint = HeatRecoverySupplyLimit_C, stated by the engineer as a scenario parameter and recorded as an assumption, not as manufacturer data. Its intended physics is a modulating bypass holding supply air at or below the limit. If licensed experiment X2 shows TAS's setpoint means something else, B3 uses a BypassFactor table modifier on (ODB, EDB2) instead. If neither is proven, B3 is dropped from PR5A and B1/B2 still ship if the manufacturer supplies thresholds, replace the declared mode
    fan behaviour fixed speed, SFP at design airflow, declared heat fractions speed rises in cooling mode
    cooling none DX coil after the exchanger on the supply path. Enabled when a declared control temperature exceeds setpoint (default 23 °C, manufacturer). Off-coil setpoint from the manufacturer's supply-temperature map, duty capped at the rated capacity. Airflow rises to a stated cooling airflow ≤ capacity. Which room's temperature controls a multi-room unit is an explicit, recorded choice; the catalogue itself says nothing answers it
    frost protection not modelled; stated in evidence as out of scope (overheating assessment) same

    F. Four-airflow contract

    quantity lives in PR5A PR5B
    PartFRequiredAirFlow PartFSpaceData.Terminals[].ContinuousDesignFlowRate_Lps (SAM space parameter) read-only, reported read-only
    DesignAirFlow VentilationTerminal.DesignFlowRate_Lps (SAM), then PR1 SystemSpace.FlowRate/FreshAir + leg flows (lineage bindings), then TPD SystemZone.FlowRate/damper design flows unchanged at every terminal; the existing zero-delta reconciliation (PartOIteration3ReconciliationRefusals) is re-run for every B-variant unchanged at terminals; cooling-mode flow is operating, not design
    SelectedEquipmentCapacity catalogue Maximum{Supply,Extract}FlowRate_Lps, reached via AHU VentilationUnitReference feasibility gate (IsVentilationUnitSufficient) + evidence only; never written into the Systems graph or TPD also an upper bound on cooling-mode operating flow; a cooling airflow above it refuses
    OperatingAirFlow TPD simulation (fan delivered flow = Load·η/dp) = DesignAirFlow × 1.0, asserted per hour from native fan load = f(control) ∈ [design, capacity], with each hour evidenced

    Existing misuse check (question 4): none found. Capacity is used only as:

    • a selection criterion;
    • the 2B ceiling on an engineer-targeted change (ApplyTargetedDesignAirFlow, EvaluateDesignAirFlowCapacityEnvelope);
    • a sufficiency check.

    No production assignment of Maximum*FlowRate_Lps to a design flow exists. Iteration 3 reads no capacity at all. The MV.json fan prototype DesignFlowRate 277.33 l/s is a template figure that TAS replaces from the attached zones. It is not capacity.


    G. Fail-closed rules

    Each rule is one refusal with an actionable sentence, and none produces a partial graph.

    1. No selected product. B1+ refuses for any in-scope AHU without a VentilationUnitReference. It names the dwelling and offers B0.
    2. The selected reference does not resolve in the catalogue read for this run. Refuse; do not reselect.
    3. Project test product selected. B1+ refuses, because it has no behaviour data by design.
    4. The product is undersized for design duty, meaning IsVentilationUnitSufficient is false. Refuse; never reselect silently.
    5. A required behaviour field is absent. B1 needs FanPerformance; B2 needs HeatRecoveryPerformance. Refuse by name and field.
    6. The operating airflow lies outside the published table domain. Refuse unless the field states ClampToDomain; extrapolation is never allowed.
    7. The fan table is not indexed on airflow, as with XBC15's ESP table. Refuse in PR5A.
    8. The template lacks exactly one exchanger per unit when HR is requested, or the supply/extract fan cannot be identified by graph position. Refuse.
    9. TAS read-back differs. Refuse when the native HeatGainFactor, Pressure, OverallEfficiency, SensibleEfficiency, LatentEfficiency, ExchCalcType, SetpointMethod, Setpoint or BypassFactor differs from the graph.
    10. Unsupported behaviour requested. For example, the B3 mode has not been proven by X2, or cooling is requested in PR5A. Refuse.
    11. TAS sizing refuses ("Flow Sizing Failed", SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113). Refuse, and never reorder to get past it.
    12. Capacity/control inconsistency. A cooling airflow above capacity, or a cooling setpoint outside the manufacturer range, refuses (PR5B).
    13. The catalogue schema tag is unknown, or a v2 field is present but invalid. The whole catalogue refuses, as today.
    14. The mechanism is not evidenced. When the operating-point evidence P0/X1 cannot read a supply-side temperature, B2+ acceptance does not pass.

    H. Acceptance test matrix

    COM-free unit tests (SAM.Tests)

    • v2 template round trip: absent ≠ null ≠ invalid; the raw-unit rule holds.
    • HeatRecoveryPerformance and FanPerformance validation: strictly increasing axes, efficiency in [0, 1], SFP > 0.
    • Resolver Query.VentilationUnitOperatingParameters(template, supplyDuty, extractDuty):
      • interpolation;
      • domain policy;
      • each refusal in G1–G7;
      • an order-independence check.
    • Query.SelectedVentilationUnitTemplate(AHU, templates): identity match, and no name matching.
    • The project test product refuses.
    • The four-airflow invariant: no resolver output is a design flow.

    SAM_Systems deterministic tests

    • Catalogue reader v1 + v2, and an unknown tag refusing.
    • A shipped-catalogue test pinning every transcribed value against its Source.
    • UnitSettings applied to the correct copy by AHU GUID.
    • Supply/extract fan role by graph position.
    • Exactly one exchanger per unit on MVRE.
    • B0 hash equality with PR1's output when UnitSettings is empty.
    • Determinism under enumeration shuffle.
    • Deep isolation: the template and the settings object are unmutated.
    • Refusals G8, plus the partial-settings case.
    • JSON round trip of MechanicalVentilationSettings including UnitSettings.

    SAM_Tas focused conversion tests

    • COM-free: the route-options default is ClearToZero, and the B0 path is unchanged.
    • Licensed:
      • ExchCalcType written and read back;
      • FromSystemsGraph preserves the graph's HeatGainFactor;
      • the exchanger is accepted by reconciliation and the duty carriers;
      • native read-back mismatch refuses (G9).

    Licensed native TAS operating-point tests

    These run against the full-year canonical no-IZAM TSD, with TPD SimulateSystems windows (startHour..endHour, already supported). Never a 1-day TBD/TSD (#115). Each test is hand-calculated from TAS's own reported ODB/EDB and flows.

    id configuration expected proves
    P0 probe map exchanger/coil GetResultsData variables (as PR2 did for fans) results are readable
    A MVRE, ε = 0, HGF = 0 supply-off-exchanger T = ODB; zone T equals B0 to tolerance exchanger at 0 is inert (B0 ≡ MVRE@0)
    B ε = 0.8 (test value, not product) T_sup = T_o + ε(T_e − T_o) each hour; the balanced-flow case; then an imbalanced case to reveal TAS's C_min handling ε semantics (X1)
    C B + SetpointMethod = On, Setpoint 18 °C T_sup = min(T_o + ε(T_e − T_o), 18) in heating direction; unchanged below supply-limit bypass semantics (X2)
    C′ B + BypassFactor table on ODB × EDB2 → 1 above threshold ε_eff → 0 above threshold alternative bypass (X2b)
    D ε = 0, dp = 750 Pa, η = 1, HGF = 1 on supply fan ΔT_supply = HGF·(dp/η)/(ρ·c_p) = 750/(1.2·1005) ≈ 0.62 K; extract-fan heat position relative to the exchanger read from the native graph HeatGainFactor = fraction of Q·dp/η into the air at the fan position (X3)
    E (PR5B) DX coil, fixed duty, setpoint T_off = max(setpoint, T_on − Q_duty/(ρ c_p V̇)) trim-cooling component (X4)
    F (PR5B) thermostat controller on one room + fan speed cooling and airflow switch with room T; flow ≤ capacity control loop (X5)

    Full annual Part O acceptance (canonical fixture SHA-256 A7E09A25…368D7E4B)

    • Reference A, B0, B1, B2 and B3 (if proven) are each Pass/Fail recorded. B0 must reproduce the frozen foundation result (0/8 TM59 outcomes differ vs A; same statistics).

    • Per variant:

      • 3 systems / 8 rooms / 14 legs;
      • design-airflow delta 0;
      • 8×8760 finite ZoneTemperature and ResultantTemperature;
      • per-unit product identity and resolved values in evidence;
      • native read-back of every mapped property.
    • Attribution:

      • ΔB1−B0 attributed to fan heat;
      • ΔB2−B1 to heat recovery;
      • ΔB3−B2 to bypass.

      Each delta is reported as mean bias, RMSE, max |Δ|, and TM59 exceedance hours.

    • Review in-session and after close/reopen, with no TAS simulation process during Review.

    Negative tests

    Every G-rule is exercised with a dedicated fixture or harness case:

    • no product;
    • test product;
    • undersized;
    • missing field;
    • out-of-domain;
    • ESP-indexed SFP;
    • MV template with HR requested;
    • tampered native value;
    • unknown schema.

    5,000-space scaling

    • The SAM_Systems structural test extends PR1's scaling test to 5,000 spaces / ~1,667 AHUs, with UnitSettings for every AHU. It asserts:
      • linear time ratio 1k → 5k;
      • no name scans;
      • one catalogue read;
      • one resolver call per distinct (reference, duty pair), memoised;
      • no per-unit 8760 arrays (one named schedule).
    • The SAM_UI assignment/evidence view is grouped by product, and the list is virtualised.

    I. Persisted evidence (per run, in the Iteration 3 ledger/record)

    • Variant: B0 | SelectedProduct{FanHeat, HeatRecovery, Bypass[, Cooling]}, which names exactly which layers were on.
    • Catalogue identity: schema tag, file SHA-256, and resolved directory.
    • Per analytical AHU GUID:
      • VentilationUnitReference;
      • the template Source string;
      • capacity;
      • supply/extract design duty;
      • Part F requirement sum;
      • OperatingAirFlow basis;
      • every resolved value (ε, SFP_total, the split rule, the HeatGainFactor values, the bypass mode and limit) with its table point or interpolation and its domain policy;
      • declared assumptions, stated as assumptions;
      • the AirSystem GUID;
      • native read-back values.
    • Pairing: B-variant results are always paired with a B0 run of the same model and fixture, as the diagnostic control.
    • Not persisted: no duplicated 8760 arrays beyond what PR4 already stores. Scalars only per unit.

    J. UI (minimum)

    • Iteration 3 run option: "Ventilation equipment behaviour: Parity (foundation control) | Selected product".
      • Parity is the default and is exactly B0.
      • Selected product runs B0 plus the full PR5A layer set, as a paired comparison.
    • Ladder variants B1/B2 are run by the licensed acceptance through IPartOIteration3Pipeline. They are not permanent UI scenarios.
    • The result window shows, per system: product, resolved values, assumptions, and refusals. The rows are grouped and virtualised.
    • No new selection UI. Iteration 2's equipment-selection workflow (SAM_UI#98) stays the only place a product is chosen.

    K. PR / repository plan

    PR5A (one PR per repo, merge order strictly as listed)

    1. SAM. v2 vocabulary: HeatRecoveryPerformance, FanPerformance, SummerBypass; Query.SelectedVentilationUnitTemplate; Query.VentilationUnitOperatingParameters (COM-free resolver); tests. No Systems/TAS knowledge.
    2. SAM_Systems. Catalogue reader v1+v2; transcription of certified MRXBOX data (evidence gate E1/E2); MechanicalVentilationUnitSettings + application in MechanicalVentilationAirSystem; B0-hash, determinism, refusal and scaling tests.
    3. SAM_Tas. SystemVentilationRouteOptions (fan-heat policy, exchanger grounding); Convert.ToTPD(Exchanger) writes ExchCalcType (and drops the duplicate ExchLatType write); exchanger in intent/duty-carrier reconciliation; GroundVentilationExchangers read-back; P0 result probe; licensed operating-point evidence A–D (Documentation/evidence/PR5A-*.md).
    4. SAM_UI. Pipeline behaviour mode; per-AHU resolution from VentilationUnitCatalogue (extended to expose templates); template MV/MVRE choice; paired B0/B-selected ledger + evidence; minimal UI; annual acceptance (documentation/evidence/PR5A-*.md).

    PR5B (after PR5A merged and X4/X5 feasible)

    Same four-repo order, covering:

    • the cooling-module vocabulary and control (SAM);
    • DX coil + refrigerant plant + operating-airflow control in a cooling topology variant (SAM_Systems);
    • DXCoil/controller conversion, read-back and native tests E–F (SAM_Tas);
    • the B4 variant and the evidence for it (SAM_UI).

    If X4/X5 prove infeasible through the current API, PR5B stops with a recorded NOT REPRESENTABLE finding. A human then decides the next step.

    Evidence gates (before the relevant licensed acceptance)

    • E1: MRXBOXAB-ECO5 certified sensible heat-recovery efficiency vs airflow, with basis and configuration (SAP PCDB entry / EN 13141-7 report).
    • E2: MRXBOXAB-ECO5 certified SFP vs airflow, with configuration.
    • E3 (PR5B): MR-ECO-COOL-V airflow in cooling mode (l/s), EER, sensible/latent, rating humidity, and the reference quantity of the 22→26 °C flow ramp. The user guide instead says a 23 °C setpoint with airflow above boost; that conflict must be resolved.

    L. Exit gates

    PR5A accepted when ALL are true

    • E1 and E2 transcribed into the shipped catalogue with traceable Source; catalogue tests pin them
    • B0 graph hash equals PR1 output; B0 annual result reproduces the frozen foundation (A vs B0: 0/8 TM59 outcomes differ, same statistics)
    • Operating-point tests A, B, D pass with hand-calculated agreement; C (or C′) passes, or B3 is explicitly dropped with its reason recorded
    • Annual canonical run for B1 and B2 (and B3 if kept): Pass/Fail recorded, 3/8/14 topology, 0 design-airflow delta, complete 8×8760 series, native read-back of every mapped property
    • Per-layer attribution deltas reported and physically plausible in sign and magnitude (fan heat warms; HR in summer changes supply temperature toward extract; bypass removes that)
    • Every G-rule negative test green
    • 5,000-space scaling evidence green
    • Review in-session and after close/reopen reproduces results; no TAS simulation process during Review
    • Release builds and full regressions green in all four repos; PRs merged in order
    • SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 / SAM_Tas: a 1-day simulation period crashes TSD.exe (0xc0000005) inside Modify.AddResults, surfacing as RPC server unavailable #115 still open; nothing reordered to pass sizing

    PR5 (full Iteration 3) accepted, allowing #111 to close, when PR5A is accepted AND

    • PR5B accepted with the same classes of evidence (E, F operating points; annual B4 with cooling duty/energy evidence and OperatingAirFlow ≤ capacity every hour); or
    • a human records that trim cooling is NOT REPRESENTABLE through the current TAS API (with the X4/X5 evidence) and decides to close or move it

    16 questions — answers

    1. First canonical manufacturer-aware MVHR. Nuaire MRXBOXAB-ECO5-AECV (MR-ECO-COOL-V), the catalogue entry "Nuaire MRXBOXAB-ECO5-AECV (MR-ECO-COOL-V)".
    2. Values already in SAM's catalogue.
      • Identity.
      • Source.
      • 150/150 l/s capacity.
      • Rank 10.
      • The cooling-module map (supply-air temperature and combined cooling capacity over ExternalDB × EnteringDB × airflow, "typical").
      • The 22→26 °C flow ramp (0.3→1.0).
      • Fan power draws, as text only.
    3. Values still missing.
      • Certified sensible HR efficiency vs airflow.
      • Certified SFP vs airflow.
      • Bypass thresholds and mode.
      • Frost behaviour.
      • Cooling-mode airflow.
      • EER and electrical input for cooling.
      • Sensible/latent split and rating humidity.
      • The ramp's reference quantity and control-temperature source.
    4. Is capacity misused as airflow? No. Capacity is a gate or ceiling only.
    5. OperatingAirFlow in PR5A. DesignAirFlow × 1.0, continuous, derived by TAS from the attached zones, and evidenced hourly.
    6. How DesignAirFlow reaches the terminals unchanged. It uses the same PR1 lineage and zone/damper duties. PR5A changes only fan and exchanger parameters and swaps MV for MVRE; the zero-delta reconciliation is re-run for every variant.
    7. Heat recovery in TAS. A TPD.Exchanger on the MVRE air path, with SensibleEfficiency (ProfileData), ExchCalcType = Simple and latent 0. The exact ε definition and the imbalance handling are licensed experiment X1.
    8. What Fan HeatGainFactor means. It is the fraction of the fan's simulated load (Q·dp/η, measured) that enters the air stream at the fan's position. Zeroing it moved zone temperature by up to 2.80 K in PR2. The quantitative check is operating-point test D.
    9. Realistic summer bypass. The manufacturer's sequence is not representable because it is unpublished. A declared deterministic supply-limit or bypass-factor mode is representable subject to X2.
    10. Realistic trim cooling.
      • The component is there: DXCoil has a setpoint, a scalar duty and On/Off control.
      • The manufacturer's capacity map is not representable directly.
      • Room-temperature control with airflow increase is unproven and needs X4/X5.
    11. Topology trim cooling needs. A DX coil downstream of the exchanger on the supply path, a refrigerant group and an ASHP plant (the MVRE template already carries an ASHP), and a controller with a thermostat sensor.
    12. Parameters only, or topology too? Both, but only by switching MV to MVRE, an existing shipped MVHR topology. PR5B adds a coil and a controller.
    13. Can B0 remain available? Yes: it is the default, hash-pinned, and paired with every B-variant.
    14. Is SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 more likely? Yes. MVRE has different template GUIDs, so every derived GUID changes and so does creation order. It also adds an exchanger coupling the supply and exhaust paths. PR5 fails closed. If the canonical B-variant is refused by sizing, SAM_Tas: TAS Systems flow sizing is sensitive to component creation order on the explicit Part O ventilation route #113 becomes a direct blocker and is fixed in its own PR, not in PR5.
    15. Does PR5 depend on SAM_Tas: a 1-day simulation period crashes TSD.exe (0xc0000005) inside Modify.AddResults, surfacing as RPC server unavailable #115? No. All tests use full-year TSD sources and TPD hour windows, and never a 1-day workflow period.
    16. Smallest deterministic licensed tests. Tests A–D, plus P0 (and E–F in PR5B), are TPD windows over the full-year canonical source, each checked against the stated hand calculation.
  6. michaldengusiak commented on Sep 11, 2026

    @michaldengusiak
    Author

    POST-FREEZE FOLLOW-UP — manual licensed testing findings

    ITERATION 3 FOUNDATION REMAINS FROZEN. Nothing below reopens the architecture, begins PR5, tunes Candidate B, or changes the accepted B0 ventilation physics. No engineering behaviour changed in any repository.

    Three findings from manual licensed TAS testing of a generated Iteration 3 document, investigated against sow/2026-Q3 (SAM 553957dc, SAM_Systems 89cf1399, SAM_Tas 1d62f380, SAM_UI 736e1771).

    1. PlantRoom sizing — shipped template data, not a defect in the route

    IPlantRoom.Simulate refuses with Unknown design flow rate into component Multi Boiler 1. Reproduced and bisected on the acceptance run's own Candidate B TPD, one fresh copy per variant:

    variant DHW group dT Multi Boiler 1 dT IsDHW answer
    as produced 0 0 false "Sizing Flow Failed"
    the DHW duty flag only 0 0 true "Sizing Flow Failed"
    DHW group dT = 11 11 0 false "Done"
    DHW group dT = 5 5 0 false "Done"
    Multi Boiler 1 dT = 11 0 11 false "Done"
    • The exact missing object/property: a non-zero design flow delta-T on the DHW circuit. The multi-boiler's DHW duty flag is neither necessary nor sufficient, and the boiler's own delta-T may stay unstated — matching the manual finding exactly.
    • Nothing is lost in copy, materialisation or conversion. Convert.ToTPD writes exactly the zero the SAM graph states, and the SAM graph states exactly what the shipped MV.json states. The value was never there.
    • The authority for it already exists in SAM_Systems: MVRE.json and Plantroom-Only.json — the two templates refreshed through a working TAS plant room — both carry 11 on DHW Circuit Group, and every template carries 11 on the heating boiler. Before that refresh MVRE carried 0 too. Any non-zero value unblocks sizing, so the magnitude is engineering data, not a switch, and 11 K is not invented here.
    • No fix was applied, because applying it means editing shipped template data that every SAM workflow shares — explicitly out of scope for this task, and the template owner's call. The one-property correction and its provenance are recorded so it can be made deliberately.
    • Effect on B0: none. With and without DHW Circuit Group.DesignDeltaT = 11, all three air systems answer "Done" and every one of the eight rooms' ZoneTemperature series is identical to six decimals over 168 hours. The DHW circuit is a disjoint liquid loop. No annual rerun would be required.

    2. Leeds + London design conditions — two sources, no accumulation

    # name type design days
    1-2 Leeds_TRY ANN HTG / CLG … heating / cooling 1 each
    3-4 London_LHR_DSY1 ANN HTG / CLG … systems 0
    5 Annual Design Condition systems 0
    • Leeds is TAS's own, derived from the attached TSD by AddTSDData. Those two carry the only real design days and name the canonical fixture's annual weather.
    • London is shipped template data — MV.json declares it in AnalyticalSystemsProperties.DesignConditions, and the conversion re-creates each by name. It arrives with no design day at all: authoring residue, not a statement by the analytical model.
    • The conversion does not append across runs. ToTPD deletes any existing TPD first and Modify.Add is an upsert by name. The duplication is between two sources, not between runs.
    • Which conditions each stage uses: the annual thermal simulation uses the building's own weather (Leeds_TRY, CIBSE Weather 2021.twd) and no TPD design condition; the Systems simulation uses the hour range and consults none, because every ventilation duty carrier Part O writes is Value-typed with zero design conditions attached; plant-room sizing (not used by Part O) uses whatever each sized variable names.
    • The two Leeds conditions are referenced by nothing in the document. The only variable in the whole TPD sized against a London condition is the unused DHW boiler's duty — and because that condition carries no design day, its duty reads 0, which is finding 1 seen from the other end.
    • Nothing removed. Filtering would mean either editing shipped template data or making the conversion drop conditions a template deliberately declared, which would break the template's own plant.

    3. The successful A/B review is now persisted

    Every completed pairing writes its whole review beside the pairing record: <run>-Iteration3-Review.txt and -Review.json. Composed by one authority that the window also renders and Copy All also writes, so the file and the screen cannot drift apart; every number copied from the comparison the review already produced, with the pairing's full identity and provenance added so it reads on its own a year later.

    The provenance refusal is untouched. A refusal writes nothing at all, so the last report describing a real comparison survives it byte for byte. The window then offers it as "Open Last Successful Report" and says — in the button, the tooltip and the refusal text — that it is HISTORICAL and does not describe the model in front of the user. Verified across two processes: one writes, a fresh one finds it, labels it historical, and still presents no Candidate B number.

    4. Window visibility and click smoke test

    The window asked for 1400x820 — taller than a 1920x1080 desktop at 125% (825 DIP) or 150% (688 DIP) scaling, and a window taller than the desktop cannot be dragged back into view. Now clamped to the work area and re-centred; the summary and the refusal are bounded and scrollable so long evidence cannot push the action bar off the bottom; the refusal and the comparison grid share one space; the action bar wraps. Measured on the real shown window against the OS client rect at 1920x1080 @100/125/150%, 1366x768 @100% and the window minimum, over complete / refused / refused-with-history: content fits in all 15, no control outside the window.

    Every user-accessible control clicked in the state where it has least to work with: all refuse cleanly. One genuine crash fixed — Close threw when the window was shown non-modally.

    Manual UI acceptance configuration: Windows 11 26200, primary display 1920x1080, work area 1920x1032, 96 DPI (100% scaling). 125% and 150% were exercised by driving the window at the device-independent work area those scales produce, which is the quantity the layout actually sees.

    Changes

    repo PR content
    SAM_UI SAM-BIM/SAM_UI#101 report persistence, historical access, window geometry, robustness
    SAM_Tas SAM-BIM/SAM_Tas#53 the licensed measurement record; documentation only
    SAM_Systems SAM-BIM/SAM_Systems#21 regression tests pinning verbatim template carriage
    SAM — no change

    Verification

    • SAM.Analytical.UI.WPF.Tests 979/979 (was 961; +18), Release 0 errors — every pre-existing provenance and refusal test green.
    • SAM.Analytical.Systems.Tests 149/149 (was 146; +3), Release 0 errors.
    • SAM.Analytical.Tas.TM59.Tests 890/890, Release 0 errors.
    • Licensed TAS: ISystem.Simulate still answers "Done" for all three air systems and all eight rooms; the full 8760-hour A/B acceptance was not rerun, because nothing that reaches it changed.

    B0 engineering behaviour: unchanged. The frozen invariant still holds:

    PartFRequiredAirFlow != DesignAirFlow != SelectedEquipmentCapacity != OperatingAirFlow
    

    Nothing here contradicts the frozen foundation. This issue stays OPEN through PR5; #113 and #115 stay OPEN.

    One decision is left to a human: whether to state DHW Circuit Group.DesignTemperatureDifference = 11 in the seven shipped templates that carry 0, so that a native plant-room sizing of a generated document succeeds. It is one property, its value is already shipped in two other templates, and it provably cannot change a Part O result.

  7. SAM-BIM-AI commented on Sep 11, 2026

    @SAM-BIM-AI

    PR5A Phase 0: licensed TAS capability evidence (measured, no production change)

    This is an evidence update to the frozen PR5 plan. The architecture is unchanged. These findings are inputs to the plan, not a re-plan.

    • Baseline: SAM 553957dc, SAM_Systems 89cf1399, SAM_Tas 1d62f380, SAM_UI 736e1771. All clean.
    • Record: C:\TasOut\p0\PR5A-PHASE0-EVIDENCE.md on the acceptance machine. The harness, TPDs and hourly CSVs are in C:\TasOut\p0, outside every repository.

    Method.

    item measured verdict consequence for PR5A
    X1 balanced Simple exchanger PASS at ε 0.5 / 0.7 / 0.9, heating and cooling: T_sup,out = T_o + ε(T_e,in − T_o), i.e. the supply-temperature-efficiency basis ε maps directly
    X1-C unbalanced MVHR UNKNOWN. TAS refused every unbalanced route before simulating, including the production route from an unbalanced design (Sizing Flow Failed / Main PlantRoom Has Errors) Product-aware heat recovery fails closed when supply ≠ extract design flow. No C_min rule is assumed
    X1-D ExchCalcType Simple applies today only because it is TAS's default for a new exchanger. NTU refuses (zero UA); Duty ignores ε SAM_Tas must write ExchCalcType = Simple explicitly and read it back
    X2-A BypassFactor No effect at 0 / 0.5 / 1, with or without a setpoint, and under an ODB table Dropped from the B3 design and from alternative C′
    X2-B exchanger Setpoint PASS. A direction-aware supply target: recovery runs only when it moves supply toward the setpoint, modulates to stop exactly at it, and does nothing when it would move supply away. Hot-weather coolth recovery is retained. One rule reproduces 1152 system-hours B3 = SetpointMethod On + Setpoint, as a declared mode. Manufacturer bypass thresholds remain unknown and are not invented
    X2-C modifiers ODB / EDB / EDB2 (same hour) / EFlow table modifiers are live, one table per component, no 8760 arrays optional seasonal cap
    D fan P = Q·dp/η, independent of HGF. ΔT = HGF·dp/(η·1214.4), linear: 0.6176 K at 750 Pa, η 1, HGF 1. Supply and extract fans behave the same input to the SAM_Tas fan-heat policy
    D2 native MVRE topology Outdoor → exchanger → supply fan → room; room → extract fan → exchanger → exhaust the supply fan's heat reaches the room in full; the extract fan's heat is ε-recovered
    Test A B0 ≡ MVRE@ε0 FAILS as generated, PASSES once the zone flag is stated. MV.json's zone prototype has DisplacementVentilation = true and MVRE.json's has false, so MV → MVRE silently changes it: up to 3.7 K difference in wet rooms at ε 0. With the flag aligned, MVRE@ε0 reproduces B0 exactly over 384 room-hours The PR5A Systems/TAS materialisation must normalise the flag explicitly. It is not a SAM setting
    P0 result read-back Full exchanger, duct and fan-state results answer only after a plant-room SimulateEx(simdata ⊇ Load|Duct, hWnd 0) (same physics as ISystem.Simulate). No native outlet temperature or recovery load exists, and exchanger var 15 is not a load needs a new SAM_Tas duct-by-port evidence reader

    Ownership note (B3). The supply-limit setpoint is a declared scenario/route parameter, not manufacturer data. It belongs downstream (plan §C, HeatRecoverySupplyLimit_C), not on VentilationUnitTemplate.

    Phase 0 production changes: NONE. No repository was changed, and nothing was committed or pushed.

    Next: PR5A SAM slice #117 (generic catalogue vocabulary + COM-free resolver). E1 and E2 are still absent, so it fails closed. It is followed by the SAM_Systems slice.

    This issue stays OPEN. PR5 stays [ ]. #113 and #115 stay OPEN.

  8. michaldengusiak commented on Sep 12, 2026

    @michaldengusiak
    Author

    Post-freeze acceptance closeout — three PRs merged, DHW plant-room template fix merged and licensed-validated

    Independent review (not taken on trust from prior summaries), merge, and licensed-TAS validation of the three post-freeze PRs plus the deferred DHW plant-room template fix. ITERATION 3 FOUNDATION remains FROZEN — nothing below reopens architecture, touches B0, or starts PR5.

    SAM_Systems #21 — plant-carriage regression tests

    • Reviewed head c0a7076e91643e2f1dc518cb3559e1e8c6a92ca0 — merge 007a58d52909821cf7e900f5041c8a08ec1cd8d8
    • Test-only (253 insertions, one file). Confirmed the crucial property by reading the test source: all three new facts read expected DHW/plant values from the template at test time, never hard-coded literals — so they stay meaningful (and green, for the right reason) after the template fix below.
    • SAM.Analytical.Systems.Tests: 149/149, Release 0 errors.

    SAM_Tas #53 — licensed plant-room/design-condition evidence

    • Reviewed head fcda9156f7259f1c28c49df09b1af2fcb5a43545 — merge 51edbf1fa898a634d99054bc9f5a5edd5f9b1dd4
    • Doc/evidence-only, verified line-by-line against the actual diff. Cross-checked its central claim directly against the shipped JSON (independently reparsed, not text-matched) — confirmed accurate.
    • SAM.Analytical.Tas.TM59.Tests: 890/890, Release 0 errors.

    SAM_UI #101 — Iteration 3 report persistence + window fixes

    • Reviewed head (pre-fix) 6d3683eb0ba013f4b959eaceaada043d67d7ecb3 -> fixed head 6a75c3eb7f70ffe41f01a6ac669f65afb053d7b7 — merge 95d200051bc228e624ca108d5391e774b0aa9b02
    • Genuine defect found and fixed during review: the persisted .txt/.json report pair was written with two independent File.WriteAllText calls. A mid-write IO failure (locked file, permissions, disk full) could leave the pair describing two different reviews, silently corrupting the exact provenance pairing this PR exists to protect. Rewrote the writer as stage, backup existing pair, install, full rollback on any failure at any stage; added a regression test proven to fail on the original code and pass on the fix.
    • SAM.Analytical.UI.WPF.Tests: 980/980 (979 + 1 new), Release 0 errors.
    • Two open non-blocking P2 items from the PR's own automated review, left as fast-follow: Fit() reads the primary monitor's work area rather than the eventual owner's; a work area smaller than 820x460 DIP clamps to minimum size rather than the smaller area.

    DHW plant-room template fix — SAM_Systems #22 (SAM-BIM/SAM_Systems#22)

    Root cause: native PlantRoom.Simulate(1,24,0) answers "Sizing Flow Failed" whenever a DHW circuit's design-flow temperature difference is zero — the IsDHW boolean is irrelevant, only a non-zero dT magnitude matters (SAM_Tas #53).

    Templates inspected: all ten shipped SystemEnergyCentre templates (CAV, DISP, EOC, EOL, MV, MVRE, NV, Plantroom-Only, UV, VAV). Correction to the original estimate: eight carried the gap, not seven.

    Templates changed (DHW Circuit Group.DesignTemperatureDifference 0 to 11, .MinimumReturnTemperature 0 to 50): CAV.json, DISP.json, EOC.json, EOL.json, MV.json, NV.json, UV.json, VAV.json.

    Engineering authority for 11 K: MVRE.json and Plantroom-Only.json already stated 11/50 on the identical component, both round-tripped through a native TAS plant-room refresh (commit a571080, "MVRE template refresh") — the preferred in-repo, native-refreshed authority. All eight changed templates share byte-identical DHW topology with those two siblings (verified relation-graph walk, not just filename similarity).

    Templates/fields deliberately NOT changed:

    • MVRE.json / Plantroom-Only.json — already correct.
    • Multi Boiler 1 on all ten templates — still 0, unchanged, matching the two native-refreshed siblings where the group-level fix alone was sufficient.
    • Heating Circuit Group / Cooling Circuit Group — 0 there is not a gap; the boiler (11) and chiller (6) components already state those circuits' design dT.
    • London_LHR_DSY1 design conditions — load-bearing (referenced by name from every sized variable in all nine ventilation templates); insufficient evidence to call them stale; left alone. (MVRE's two unreferenced London_TRY entries are more plausibly stale authoring residue from the same refresh commit, but touching them means re-authoring the very file the 11 K authority depends on — flagged, not touched, pending template-owner review.)

    Known debt flagged, not fixed in this PR:

    • SAM_Tas/SAM.Analytical.Tas/Create/TPD.cs's standalone Create.TPD(...) builder hard-codes a disagreeing DHW authority (DesignDeltaT = 50, MinimumReturnTemp = 10, modelling the cold-feed raise rather than the secondary-circulation flow/return the templates use). It has zero references to SystemEnergyCentre/MechanicalVentilation/ToTPD — a disconnected legacy route (Grasshopper + an older UI Simulate command), not part of the Iteration 3 pipeline — so reconciling the two authorities is a separate decision.
    • A new environment trap: SAM.Core resource resolution checks a user-profile Documents\SAM\resources\... override before the repo's own files/resources of the same name. Didn't bite this validation run (it happened to hold identical corrected data) but is a silent staleness risk for future sessions.
    • No test in SAM_Systems exercises MVRE.json/Plantroom-Only.json's DHW carriage directly (only MV.json is loaded by the plant-carriage suite) — their "already 11 K" status is confirmed by direct file inspection here, not by CI.
    • SAM_Tas's PROJECT_PROGRESS.md continuity log is several PRs stale (last describes PR refactor(gh): modernise legacy Grasshopper components using variable parameter architecture #40/ticV work); flagged by two independent review passes, not touched in this closeout to avoid scope creep into unrelated repo hygiene.

    Verification

    • Release build + full regression suite, all four repos: green (counts above).
    • Native licensed PlantRoom.Simulate(1,24,0) on the corrected Flat-It3B.tpd: Done (was "Sizing Flow Failed").
    • Native Iteration 3 Systems route on the same canonical fixture (SHA-256 A7E09A25AE29C7DBB4C690D747A96FCD9F110CA27FB4DC2ABE816755368D7E4B): 3/3 MVHR AirSystems simulate, 8/8 room ZoneTemperature series complete.
    • Before/after comparison: 168 h per-room sums identical to 6 decimal places (max diff 0.000000); the full annual TM59 comparison this run produced reproduces the pre-fix acceptance record exactly, including the argmax hour (Ensuite_8, hour 5491, max 2.909 K). No separate 8760 h rerun was needed — the production route performs it intrinsically as part of validation, and it matches.
    • Iteration 3 report-persistence end-to-end check: PASS (files on disk, full evidence sections present, survives close/reopen, refusal writes nothing, persisted report untouched, exposed only as HISTORICAL).
    • UI click/visibility smoke pass at 100%/125%/150% DIP: PASS (no crash, no clipped controls, scrolling/resize/Close/Copy All/TM59 buttons all correct).
    • Candidate B0 confirmed unchanged — byte-identical ventilation results before and after the plant-room fix, as required.

    Status

    SAM_Systems #21 MERGED   SAM_Tas #53 MERGED   SAM_UI #101 MERGED
    SAM_Systems #22 (DHW template fix) MERGED   SAM_Tas #54 (doc addendum) MERGED
    

    All four repositories (SAM, SAM_Systems, SAM_Tas, SAM_UI) are on sow/2026-Q3, clean, fetched, and in sync with origin.

    ITERATION 3 FOUNDATION remains FROZEN.

    PR5 — manufacturer-aware behaviour remains the next physics milestone. This issue stays open.

  9. michaldengusiak commented on Sep 12, 2026

    @michaldengusiak
    Author

    ITERATION 3 B0 A/B PARITY DECOMPOSITION — CLOSED

    Forensic decomposition of the frozen Candidate B0 / Reference A residual. Evidence only — no
    production change in any repository, and Candidate B0 is byte-for-byte the frozen control.

    Classification: B — no B0 implementation defect; the residual is a representation difference

    Between the legacy TBD/IZAM route and the explicit TAS Systems route. Every defect candidate in
    the study brief was tested against native TAS evidence, not argued. The one inherited default
    that was found cannot be changed in the direction of parity.

    Baseline and pairing

    • SAM 553957dc61db876926a5599154770d7aa22f959f
    • SAM_Systems a0395dc96ecb085c9b74c350c68234e00e005371
    • SAM_Tas c1cc91981efdcbe6735c415feaa3e04f8e704998 (before this PR)
    • SAM_UI 95d200051bc228e624ca108d5391e774b0aa9b02

    Pairing: the post-DHW-template-fix production run, attempt GUID
    a28813f0-1811-464f-ab2b-3f0b53d70a11
    , written 2026-09-12 05:41:00Z, in C:\TasOut\pr9out.
    Reference A design fingerprint 207dbb4ced02f556, scenario fingerprint 008beb0b6213be29.
    Canonical fixture SHA-256 A7E09A25AE29C7DBB4C690D747A96FCD9F110CA27FB4DC2ABE816755368D7E4B.
    Resource-shadowing trap checked: the user-profile MV.json override and the repository copy are
    identical (b0160e2b1757…), so nothing stale was analysed.

    artefact bytes SHA-256
    Flat.tsd (Reference A) 17864876 E42B48C54939A4C0BDE076C40C314AA065E69EEDEBBB3A83D60E2234E569E3F3
    Flat.tbd 424707 EFFC4CAC8F6EEEFB26F6479A16F724665D0D6BAA62C6DE3B31B399C1DFE7B758
    Flat-It3B.tsd (no-IZAM source) 15987792 E6BAA4E2FB72F07A017BA8683E2EA7D63A85456FA4196B3DB3215EBE9A3BE55F
    Flat-It3B.tbd 402234 F5458E7A700BD8FDB7B5B250F9AFD9FC932336297FD04ECF6F56C16F2BA82E8A
    Flat-It3B.tpd 120259 80067D2468B697B21226EECFCCB19C48777EA05239DEBBE765BCA3847633FED2
    Flat-It3B-Bridge.tsd 16360279 0BE6B3B693287F936CE88217B7F04F60FDE8E2BDE990F61DF9C8051C02B1580C
    Flat-It3B-Bridge.tbd 2325212 6C9D54F853179B55AFCAAFDD8EBA62674D395B06757661CECDEE3F255568DA27
    hourly-dataset.csv (70 080 rows, kept outside the repo) 30345875 9689CECB55AA5FDE2E0EB8F17A857B861E7A5A439A1B09126697A54300040B13

    Were the annual simulations re-run? No.

    Both annual TSDs were read as frozen and reproduce every published statistic exactly. Two short
    licensed re-computations on copies were needed because TAS does not persist Systems/plant
    results in a saved .tpd (every component result series answers NullReferenceException):
    per-system ISystem.Simulate(1, 8760, 0) to recover B0's native ZoneTemperature, and
    IPlantRoom.SimulateEx(1, 8760, 15, …, Load|Pipe|Duct|SimEvents|Cont, 1, 0) to recover the
    per-duct hourly state. The per-system control reproduces frozen B0 to pooled RMSE 0.000874 K,
    max 0.001001 K
    — the bridge's own thermostat resolution.

    Findings

    Time shift — none. A(t) vs B(t+k) for k in −3…+3: k = 0 is the RMSE minimum for all 8
    rooms and both quantities
    , monotonically worse either side, correlation peaking at k = 0
    (0.982 air / 0.989 resultant). SAM_Tas #52 was the only alignment defect there was.

    A-air vs B-ZoneTemperature: bias +0.3853 K, RMSE 0.9840 K, max 4.1304 K.
    A-resultant vs B-resultant: bias +0.3726 K, RMSE 0.8335 K, max 2.9086 K.

    Bridge contribution — none; it subtracts. RMSE falls 0.9840 → 0.8335 K across the bridge.
    resultant = (air + MRT)/2 holds to max |diff| = 1e-6 K in all three documents, and the
    bridge's achieved air equals the Systems ZoneTemperature to ≤ 0.001001 K per room. The
    temporary bridge is not a material contributor; replacing it with a native Systems resultant
    would remove at most 0.001 K and would probably increase the reported difference.

    Supply air — B0 supplies outdoor air, exactly. Read off the native fresh-air duct after
    SimulateEx: max |T_freshair − T_outdoor| = 0.000000000 K on all three units. No exchanger, no
    heating coil, no cooling coil and no active setpoint exists in any air system; both fans state
    HeatGainFactor = 0, efficiency 1. Exchanger effect, fan heat, coils, hidden setpoint, plant
    coupling and default component behaviour are each ruled out individually.

    Reference A does not supply outdoor air. Modify.UpdateIZAMs writes one 3 × 3 × 2 m
    MVHR plant zone per AirHandlingUnit (MVHR-01/02/03, 18 m³ / 9 m², absent from the 9-space
    .sam) to stage the FROM OUTSIDE movement. It is a full thermal zone: against outdoor dry bulb
    it runs RMSE 1.468 / 0.848 K, max 6.32 K, +1.0 K in January and −1.2 K in August.

    Transfer air. SystemZone.DisplacementVent = true on all eight B0 zones (inherited from the
    MV.json prototype) makes TAS hand the stratified upper-layer air to the next component: an
    8 l/s wet-room outlet reaches 79.8 °C while the room reports 17.4 °C. So on the three supply
    legs the two routes deliver identical air (to 0.002 K) and on the five transfer legs B0 hands
    on air +0.67 … +2.54 K warmer in the annual mean. Reference A's IZAM physics was confirmed
    independently: hand-calculating Q = rho·cp·V·(T_source − T_room) reproduces A's native
    airMovementGain at correlation ≥ 0.99979, implied rho·cp 1224.3–1224.9 J/m³K.

    Bathroom_2's 12 extra >26 °C hours. Its transfer inlet is Studio 1_0's stratified outlet at
    31.6–42.2 °C versus A's mixed 22.3–26.0 °C. All 12 are narrow-margin crossings: B0 exceeds by
    0.076–0.850 K (mean 0.466 K) where A already sits at 25.38–25.99 °C, and B0's 16 hours are
    a strict superset of A's 4 (0 hours the other way). Limit 262 h; both routes pass by 16×.

    Hour 2968 is rank 1 of 8760 for the pooled mean |B−A| (1.7895 K). Day 124, 16:00, outdoor
    21.1 °C — only the 290th warmest hour. A's plant zones still lag the heating season (MVHR-01
    17.43 °C, MVHR-02/03 19.05 °C) so A supplies 2.05–3.67 K cooler air on the 63 l/s legs; the
    four rooms on those legs all take their annual maximum there.

    5491 vs 5299 — a 0.000303 K tie. Ensuite_8: |delta| = 2.908573 at 5491 and 2.908270 at
    5299 (4819 is third at 2.903435). Both round to 2.909 K. Not a pairing, indexing, timestamp or
    stale artefact. Canonical convention recorded: 0-based hour of year 0…8759; argmax is Ensuite_8
    at hour 5491.

    Ruled out with zero contribution: DesignAirFlow mismatch (all 43 duct flow series constant at
    design over 8760 h, every unit balanced 30/30, 63/63, 63/63); duplicate ventilation and residual
    IZAM/ticV (airMovementGain identically 0.000000000, IZAM count = 0, ticV = 0,
    AHUGain = 0, infiltration identical); schedules (fans operable 8760/8760 at factor 1.0); weather
    and internal gains (every series identical to 0.000000); identity/result mapping (GUID-keyed
    both sides, control rerun reproduces to 0.001 K).

    Is there any legitimate B0 correction? No. Clearing DisplacementVent on all eight zones and
    re-simulating gives fully-mixed behaviour like A's — and makes parity worse: pooled bias
    +0.386 → +0.986 K, RMSE 0.984 → 1.282 K. Turning it off would be tuning away from A.

    Final frozen B0 statistics — unchanged

    8 rooms, 70 080 hourly values
    resultant               bias +0.3726 K   RMSE 0.8335 K   max 2.9086 K (Ensuite_8, hour 5491)
    air / ZoneTemperature   bias +0.3853 K   RMSE 0.9840 K   max 4.1304 K
    TM59 criterion outcome differences: 0 of 8
    

    Irreducible residual. Seasonal, not a level offset: +0.74…+1.07 K Nov–Apr, −0.30…−0.39 K
    Jun–Sep. It tracks the two-pass route's own load-evaluation offset — the gap between the
    free-running no-IZAM TBD the zone loads were computed in and the temperature the Systems solver
    achieves — at r = 0.932 across the twelve months, and it is visible in its cleanest form on
    the three supply rooms, which receive identical air at identical flow through identical fabric
    and still sit +0.29…+0.52 K above A. By outdoor condition:

    regime room-hours bias RMSE
    ODB ≥ 20 °C 3 480 −0.048 K 0.490 K
    10 ≤ ODB < 20 °C 31 648 +0.001 K 0.777 K
    ODB < 10 °C 34 952 +0.751 K 0.907 K

    In the regime Part O actually assesses the pooled bias is −0.048 K and the RMSE 0.490 K. The
    zero TM59 outcome differences are not luck. The residual is physically and numerically acceptable
    as the difference between the legacy IZAM representation and explicit TAS Systems.

    PR

    Evidence location

    SAM_Tas/Documentation/evidence/PARTO-ITERATION3-B0-PARITY-DECOMPOSITION.md, with
    PARTO-B0-PARITY-summary.csv (machine-readable), the per-room / shift / monthly / critical-hour /
    threshold tables, native Reference-A IZAM and B0 TPD topology dumps, native duct results with and
    without the displacement flag, every analysis log, and the licensed harness and analysis scripts.
    The 70 080-row dataset and five plots are kept beside the acceptance artefacts and hashed in
    PARTO-B0-PARITY-artefacts.csv.

    Input for PR5A (recorded, not acted on)

    PR5A Phase 0 required the DisplacementVentilation flag to be normalised explicitly. This study
    measures the direction, which Phase 0 could not: Candidate B0 runs with it true, and
    normalising to false moves B0 away from Reference A (pooled bias +0.386 → +0.986 K, wet rooms
    moving 1.6–1.8 K). MVRE should be normalised to true so that MVRE at epsilon 0 still
    reproduces B0; normalising both to false would silently change the frozen B0 control and
    invalidate the comparison.

    Remaining narrow debt (unchanged by this study)

    • No native Systems ResultantTemperature — the thermostat bridge stays until TAS exposes one.
      Measured here as a non-contributor, so its replacement is a simplification, not a fix.
    • SAM_Tas's PROJECT_PROGRESS.md continuity log is still several PRs stale.
    • SAM_Systems has no test exercising MVRE.json / Plantroom-Only.json DHW carriage directly.

    ITERATION 3 FOUNDATION remains FROZEN.

    B0 forensic study is CLOSED.

    PR5A may now resume.

    PR #117 has NOT been merged or modified by this study — it remains OPEN at head
    f6b0d3f93a73c91a9e44c728e5476afe7d7f82f8, unrebased and un-built-on.

    #113 and #115 retain their existing states; this study produced no new evidence touching either.
    This issue stays OPEN.

  10. michaldengusiak commented on Sep 12, 2026

    @michaldengusiak
    Author

    PR5A resumed — SAM slice (#117) independently reviewed and merged

    Independent review (not taken on trust), full local build, and full local test run of PR #117 before merging.

    Review

    • Confirmed OPEN, MERGEABLE, CLEAN, head f6b0d3f93a73c91a9e44c728e5476afe7d7f82f8 (matched the expected head).
    • Diff confined to 11 files, all under SAM.Analytical/SAM.Tests (no SAM_Systems/SAM_Tas/SAM_UI knowledge leaked into SAM).
    • No manufacturer-name conditionals anywhere in code (grepped the whole diff — the only "MRXBOX" hit is prose in PROJECT_PROGRESS.md).
    • Identity resolution is by VentilationUnitReference.Matches only — a dedicated test (ResolutionIgnoresDisplayNames) proves display names are ignored and an ambiguous/duplicate match refuses rather than picking one.
    • Missing E1/E2 fields refuse rather than defaulting: HeatRecoveryPerformance/FanPerformance absent → IsHeatRecoveryResolved/IsFanPerformanceResolved false, NaN, never 0 and never MVRE's 0.7 (MissingData_StaysMissingThroughARoundTrip).
    • Capacity is never read as airflow: ResolvingAtTheDesignDuty_NeverMovesItAndNeverReadsTheCapacity resolves at the AHU's actual 30 l/s design duty on a 150 l/s-capacity product and asserts the two give different figures.
    • Old v1 catalogue JSON round-trips unchanged; new keys are omitted from serialization when null (TheNewFields_AddKeysAndChangeNothingElse).
    • Unbalanced duty refuses both quantities deterministically (matches Phase 0 X1-C).
    • Domain policy defaults to Refuse; only Refuse/ClampToDomain accepted; a mistyped policy refuses rather than silently clamping.
    • Determinism/no-mutation/isolation covered explicitly (own-copy references, catalogue order independence).

    Independent build/test verification (not just re-quoting the PR's own CI)

    • Fetched feature/parto-pr5a-ventilation-unit-performance, built a fresh worktree at the reviewed head.
    • dotnet build SAM.sln -c Release: 0 errors.
    • dotnet test SAM/SAM.Tests -c Release: 2151/2151 passed.
    • PR's own GitHub Actions checks (build (Release), test (Release), spdx) all green.

    No genuine defect found. No fix was needed on this PR.

    Merge

    • Merged via merge commit (not squash) — merge SHA b4a1283f8f5a805b637943fedc0b2a7f493d7b9a into sow/2026-Q3.
    • Local SAM sow/2026-Q3 fast-forwarded to b4a1283f cleanly.

    Status

    SAM #117 (PR5A SAM slice) MERGED -> sow/2026-Q3 @ b4a1283f
    

    Next: SAM_Systems PR5A slice — catalogue reader v1+v2, E1/E2 evidence gate (transcription only from a certified source; still absent, so behaviour stays fail-closed for the real product), MechanicalVentilationUnitSettings keyed by AHU GUID, DisplacementVentilation normalisation on MV -> MVRE per Phase 0 finding "Test A" (normalise to true, per the B0 A/B parity decomposition's direction evidence).

    E1/E2 remain unsourced. B0 is untouched by this slice (SAM has no TAS/Systems concept). This issue stays OPEN.

  11. michaldengusiak commented on Sep 12, 2026

    @michaldengusiak
    Author

    PR5A resumed — SAM_Systems slice (#23) reviewed, one genuine defect found and fixed, merged

    Implementation

    • Added MechanicalVentilationUnitSettings (per-AHU-GUID resolved heat recovery efficiency, fan pressure/efficiency/heat-gain-factor; every field NaN/null = "leave the template untouched") and MechanicalVentilationSettings.UnitSettings, keyed by analytical AirHandlingUnit.Guid, all-or-nothing across the units one call materialises.
    • Create.MechanicalVentilation/MechanicalVentilationAirSystem apply the settings onto the unit's own re-keyed fan/exchanger copies; capacity is never written; the energy-centre identity key folds in every unit's settings only when UnitSettings is non-empty, so B0 stays byte-identical to PR1.
    • DisplacementVentilation normalised to true unconditionally on every materialised zone, per Phase 0 "Test A" and the licensed B0/A parity decomposition (MV.json already true; MVRE.json's false is authoring residue that measurably moves B0 away from Reference A). Templates are read-only per the frozen plan, so this is a code-level correction, not a data edit.
    • Catalogue reader accepts VentilationUnitCatalogue:v2 alongside v1, validating SAM#117's HeatRecoveryPerformance/FanPerformance the same way every other optional field is. Shipped catalogue untouched — E1/E2 still unsourced.

    Genuine defect found during implementation (self-caught, before any review)

    The settings-application logic originally ran after the unit's fan/exchanger copies were added to the plant room. SystemPlantRoom.Add() clones its argument on the way in, so every override silently had no effect on the materialised graph — caught by a failing test assertion (exchanger stayed at the shipped 0.7 instead of the requested override). Fixed by moving the whole block earlier, identifying roles on the template's own untouched connectivity (still intact at that point in each unit's pass) rather than the already-added copies, then mapping through to the copies before Add().

    A related discovery while diagnosing that bug: neither shipped template attaches the supply fan directly to the room. Connector 0 of the prototype room is a damper in both MV.json and MVRE.json; only connector 1 (extract) is a direct fan attachment. The supply fan is identified by elimination — the unit's other fan, among exactly two — never by name.

    Independent review (a fresh agent, not the implementer)

    No correctness defects found (no O(n²) scans, no NRE paths, no manufacturer-name leakage, B0 identity-fold traced and confirmed empty-safe, fan-role test coverage confirmed to genuinely catch a supply/extract swap). One architectural question raised: whether the unconditional DisplacementVentilation = true normalisation belongs in generic code. Resolved: it's a deliberate, plan-mandated, two-template correction (§ frozen plan explicitly requires this normalisation and states the templates are read-only, so a data-layer fix is not available) — strengthened the code comment to make that scope explicit, and added an ambiguity check to the prototype-room lookup for defence in depth.

    Validation

    • SAM.Analytical.Systems.Tests: 176/176 (was 149; +27 — B0 invariance, zone-flag normalisation on MV vs MVRE, fan settings applied to the structurally-correct fan, heat-recovery mapping with the "exactly one exchanger" refusal, capacity-never-written, all-or-nothing partial-configuration refusal, determinism/isolation, JSON round trip, and a 5,000-space/50-air-handling-unit scaling test).
    • dotnet build SAM_Systems.sln -c Release: 0 errors.
    • CI (build — includes the same test run — and spdx): both green.

    Merge

    Status

    SAM #117 (PR5A SAM slice) MERGED -> sow/2026-Q3 @ b4a1283f
    SAM_Systems #23 (PR5A SAM_Systems slice) MERGED -> sow/2026-Q3 @ 5213ba9c
    

    E1/E2 remain unsourced; the real MRXBOX product still fails closed. HeatRecoverySupplyLimit_C (B3) is carried on the new settings type but not yet interpreted anywhere — that's SAM_Tas's job.

    Next: SAM_Tas PR5A slice — route options (ClearToZero B0 default / FromSystemsGraph), Convert.ToTPD(Exchanger) writing ExchCalcType and dropping the duplicate ExchLatType write (both confirmed present in the current code by direct read), exchanger reconciliation/duty-carrier handling, a P0 result-read-back probe, and the licensed operating-point evidence A–D against the full-year canonical no-IZAM TSD. This issue stays OPEN.

  12. michaldengusiak commented on Sep 12, 2026

    @michaldengusiak
    Author

    PR5A resumed — SAM_Tas slice (#56) reviewed, licensed-verified, merged

    Implementation

    • Convert.ToTPD(DisplaySystemExchanger, …) now writes ExchCalcType explicitly (previously never written — it only ever applied as Simple because that happens to be TAS's own default for a new exchanger; Phase 0 X1-D measured NTU refuses with zero heat transfer area and Duty ignores the stated efficiency). Also drops a duplicate ExchLatType write (the identical line appeared twice).
    • New SystemVentilationFanHeatGainPolicy (ClearToZero default / FromSystemsGraph), threaded Create.SystemVentilationConversionContext → SystemVentilationConversionContext.FanHeatGainPolicy → Create.SystemVentilationRoute → Modify.GroundVentilationFans. ClearToZero is byte-for-byte the pre-PR5A behaviour (every existing caller's default, unchanged). FromSystemsGraph writes nothing and only reads back, so a resolved manufacturer fan-heat figure SAM_Systems already wrote onto the graph is never silently discarded.
    • New Modify.GroundVentilationExchangers, modelled on GroundVentilationFans: reads back ExchCalcType, refuses if not Simple. No-op wherever no exchanger exists (every B0 system).

    Licensed verification

    No COM-free test coverage exists for this (the repo's only test project has fakes for TPD.SystemComponent/TPD.ZoneLoad, not Fan/Exchanger, and building those from scratch was judged higher-risk than exercising the real interop). Instead, a throwaway harness (outside any repository) drove the actual production path — Create.MechanicalVentilation → Create.SystemVentilationConversionContext → Convert.ToTPD — against real TAS, using the shipped MVRE.json and two deliberately different fan heat-gain factors (0.5/1.0):

    • ExchCalcType writes and reads back as tpdExchangerCalcSimple in every run.
    • FromSystemsGraph preserves both fan figures distinctly (native notes: HeatGainFactor 0.5 and HeatGainFactor 1).
    • The regression check that matters most: the same model, same non-zero source settings, converted again with ClearToZero — both native fans still read back HeatGainFactor 0. The B0 default path is unchanged for every existing caller.

    Full narrative and exact native notes: SAM_Tas/Documentation/evidence/PARTO-PR5A-SAMTAS-CONVERSION-EVIDENCE.md.

    Not covered by this licensed check (disclosed in the evidence doc itself): the full operating-point evidence A–D, and any refusal path through the new code (no genuinely non-Simple exchanger or native write rejection was driven — verified by code inspection only, matching a pre-existing gap in GroundVentilationFans itself).

    Independent review (a fresh agent, not the implementer)

    No genuine defects found. Confirmed end-to-end that the new optional parameter's default reaches byte-for-byte the same ClearToZero code path as before this PR for every existing caller; confirmed Create.SystemVentilationConversionContext/Create.SystemVentilationRoute are the only construction/entry sites repo-wide (no second path silently reverts to the enum default); confirmed the duplicate ExchLatType removal is genuinely inert; confirmed documentation matches the code.

    Validation

    • SAM.Analytical.Tas.TM59.Tests: 890/890, unchanged from baseline.
    • SAM_Tas.sln Release (VS MSBuild, full .NET Framework — dotnet build cannot build the COM interop projects): 0 errors, both before opening the PR and again after syncing the merged sow/2026-Q3.
    • CI (build, spdx): both green. One fix mid-review: a pre-existing file (Exchanger.cs) predated the SPDX-header convention and was missing it; added (no behaviour change), confirmed by CI.

    Merge

    Status

    SAM #117 (PR5A SAM slice) MERGED -> sow/2026-Q3 @ b4a1283f
    SAM_Systems #23 (PR5A SAM_Systems slice) MERGED -> sow/2026-Q3 @ 5213ba9c
    SAM_Tas #56 (PR5A SAM_Tas slice) MERGED -> sow/2026-Q3 @ 0f7f59e0
    

    E1/E2 remain unsourced; the real MRXBOX product still fails closed. HeatRecoverySupplyLimit_C (B3) is carried on the SAM_Systems settings type but still not interpreted anywhere. The licensed operating-point evidence A–D and any annual acceptance remain gated on the SAM_UI slice (a zone-identity-matched model and the full-year canonical TSD/TPD route are Phase 5 territory).

    Next: SAM_UI PR5A slice — orchestration/behaviour-mode (parity vs selected-product), per-AHU resolution from the extended catalogue, paired B0/selected-product ledger and evidence, minimal UI. Only after that: the licensed operating-point evidence A–D and any annual acceptance. This issue stays OPEN.

  13. SAM-BIM-AI commented on Sep 12, 2026

    @SAM-BIM-AI

    PR5A resumed — SAM_UI slice (#102) audited against Phase 0, amended, merged

    Sync / collision audit (before touching anything)

    Genuine defect found and fixed on #102: pre-PR5A pairings became unreviewable

    #102 bumped the record to PartOIteration3Record:v2. That broke review of existing v1 pairings in two ways:

    • Eligibility and review required the exact current schema.
    • Review's ledger replay dropped every stage after the new EquipmentResolution stage, which a v1 record never had.

    So both acceptance pairings on disk (C:\TasOut\pr4h, C:\TasOut\pr5a, both v1) would have lost their HISTORICAL review.

    Amendment 7ea2f704:

    • Writers still write v2 only. Review and eligibility read exactly v1 and v2.
    • A v1 record with no mode is the historical Parity / Candidate B0 route.
    • A v1 record carrying selected-product behaviour, equipment or catalogue evidence is refused as contradictory.
    • v0 / unknown schemas and v2 without a valid explicit mode still refuse.
    • For v1 only, the missing EquipmentResolution stage is replayed as the Parity no-op, so the ledger is shown whole. Review stays simulation-free.
    • Docs: a labelled "Phase 0 supersession — current state" note in the plan companion and the evidence doc. Historical text is kept.

    Three further defects, raised by the automated review of the amended head — fixed (eae90881)

    CI was green on 7ea2f704, but the merge was held because Codex posted two P1s and one P2 against #102's own code:

    Validation

    • Built against the merged SAM b4a1283f, SAM_Systems 5213ba9c and SAM_Tas 0f7f59e0 outputs.
    • SAM.Analytical.UI.WPF.Tests: 1012/1012 (1002 + 10 new).
    • SAM_UI.sln Release (VS MSBuild): 0 errors. git diff --check clean.
    • CI on the final head eae90881: build success, spdx success. New automated review comments on it: none new — the three existing threads (P1 scope, P1 lineage, P2 completeness) are the ones fixed in this commit.

    Merge

    Status

    SAM #117 MERGED @ b4a1283f   SAM_Systems #23 MERGED @ 5213ba9c   SAM_Tas #56 MERGED @ 0f7f59e0
    SAM_UI #102 MERGED @ 0daa072dbe8b4bf4ebc2cf51571b7c55fbd11b65
    

    E1/E2 remain unsourced, so the real MRXBOX product still fails closed, and no values were invented. PR5B has not started.

    Remaining PR5A gates (ownership fixed to avoid parallel collisions):

    • SAM_Tas, other laptop, evidence first; no production reader/API commit until the shape is proven. Plant-room SimulateEx detailed read-back, exchanger ducts found by native port, inlet/outlet temperatures and effective ε, var1/var2 balance, G9 exchanger read-back, fan HGF compared with the graph, and Test A (MVRE@ε0 with the zone flag true == B0) on the merged heads.
    • SAM_UI, after E1/E2: a B1 mode (fans only, ε set to 0 explicitly).
    • SAM_Systems + SAM_Tas, later: B3 as SetpointMethod On + Setpoint.
    • SAM, later: index the name-joined VentilationSystems(airHandlingUnit) query for 5,000-space scaling.

    This issue stays OPEN. #113 and #115 are unchanged.

  14. michaldengusiak commented on Sep 14, 2026

    @michaldengusiak
    Author

    PR5A external evidence gates — Nuaire + EDSL

    Current state remains unchanged: Iteration 3 foundation is FROZEN and PR5 manufacturer-aware behaviour remains open.

    Two external dependencies now gate the next manufacturer-aware acceptance steps:

    1. Nuaire product/performance evidence

    Canonical product: MRXBOXAB-ECO5-AECV used with MR-ECO-COOL-V.

    Public evidence found so far:

    • PCDB record 500625 is for base MRXBOXAB-ECO5; no public record or manufacturer statement has been found proving that it applies unchanged to the -AECV / -AE(OH)CV variant.
    • The PCDB/SAP heat-recovery figure is a package supply-temperature ratio, measured without correcting for fan/component heat. It therefore must not be written directly as TAS exchanger-only SensibleEfficiency while TAS also models separate fan heat.
    • Whole-unit SFP basis is compatible with SAM's TotalBothFans representation, but canonical product identity/equivalence remains unresolved.

    Current readiness:

    • B1 (fans only, explicit ε = 0): BLOCKED pending canonical E2 / written product equivalence.
    • B2: EVIDENCE BLOCKED by (a) product identity/equivalence and (b) package supply-temperature ratio -> TAS exchanger+fan decomposition.

    A technical request to Nuaire has been prepared asking which exact PCDB/test data applies to MRXBOXAB-ECO5-AECV, for certified SFP vs airflow, and for either exchanger-only sensible efficiency corrected for fan/component heat or sufficient certified data to reproduce the package supply-air temperature without double counting fan heat.

    2. EDSL / TAS displacement + active-HR clarification

    Licensed evidence shows the merged route is correct at ε = 0 and B0 parity remains exact. With DisplacementVentilation = true and active HR, TAS exhibits a genuine simulated discontinuity: the exchanger internally uses an extract state that can differ from the reported extract duct state, and that changed supply condition propagates to zone results. Displacement OFF restores smooth/exact behaviour; fan heat and optimiser flags were ruled out.

    A minimal TAS reproduction package has been prepared for EDSL. Until clarified:

    • keep DisplacementVentilation = true (B0 parity depends on it);
    • do not change PR5A production configuration;
    • do not accept quantitative B2 thermal deltas as final;
    • B3 and PR5B remain on hold.

    External acceptance target

    For Part O manufacturer validation, the certified package supply-air temperature / supply-temperature ratio is the external performance target. TAS exchanger ε is only an internal modelling parameter; any exchanger+fan decomposition must ultimately reproduce the certified downstream supply-air temperature.

    No production code change is authorised by this comment. No B0 architecture is reopened.

  15. SAM-BIM-AI commented on Sep 15, 2026

    @SAM-BIM-AI

    PR5B status - SAM#113 became a direct PR5 dependency, fix in review, first valid annual B4 complete

    Correction to this issue's tracker text

    The body classified #113 as native TAS debt "not part of PR5 unless PR5 proves a direct dependency". PR5B has now proved that dependency.

    • The all-three-dwelling B4 document (same-zone recirculation cooling in every MVHR) failed Flow Sizing Failed or never terminated, depending only on generation.
    • Each dwelling's branch simulated on its own.
    • The engineering graph was identical; only native creation order differed.

    #113 is therefore a PR5 prerequisite.

    Resolution in review

    SAM-BIM/SAM_Tas#57 (head 800bc885, base sow/2026-Q3, not merged) makes native creation order a function of the graph alone:

    • air-path order;
    • guid-independent;
    • explicit route only;
    • no Part O or manufacturer code, no retries, no seed/guid manipulation.

    Evidence, A/B on the same build:

    • The air-path order gives one native sequence for identity sets s1, s2, s3, s4 and random, all Done.
    • The old guid order with s1 reproduces the known hang (killed at 900 s).
    • 897/897 SAM_Tas tests locally, including a schedule-rename / guid re-key regression.

    Details are on #113.

    First valid annual manufacturer-aware B4

    Route: all three dwellings, full year, frozen Iteration 3 route - Systems -> ZoneTemperature -> ResultantTemperature bridge -> unchanged TM59 (SAM_UI PartOTM59Assessment).

    B0 and B4 were regenerated together under the same (air-path) order. The configuration is unchanged from the accepted PR5B design:

    • 22 C DX gate (HeatingSetpoint 22, HeatingDuty 0);
    • manufacturer table, Extrapolate false;
    • recirculation 36..120 l/s;
    • DesignAirFlow untouched.

    Results:

    • Runtime: B4 generation 17.5 s, annual Systems simulation 167 s.

    • Reproducible: s1 vs s2 annual ZoneTemperature and ResultantTemperature are bit-identical (8 x 8760), TM59 identical.

    • Systems validity PASS in all three dwellings (plant-room re-simulation):

      check MVHR-02 / MVHR-01 / MVHR-03
      DX cooling below the 22 C mixed-return gate 0 h
      heating 0 h
      recirculation 36..120 l/s
      canonical legs at design, max deviation 0.024 / 0.002 / 0.027 l/s
      outdoor air 63 / 30 / 63 l/s
      DX outlet vs clamped table max 0 K
      cooling 582 / 1003 / 529 kWh
    • TM59: 8/8 rooms PASS.

      room B0 h > 26 C B4 h > 26 C
      Studio 1_0 18 8
      Bathroom_2 2 0
      Kitchen_4 4 3
      Kitchen_7 4 3
      Bedroom 2_6 3 2
      Bedroom 2_3 3 3
      Ensuites 0 0

    Scope of this result. The canonical fixture demonstrates correctness and room coupling of manufacturer-aware cooling through the frozen route. It cannot demonstrate fail -> pass, because its B0 already passes TM59.

    New native constraint for all further comparisons

    Creation order is part of TAS's effective numerical state:

    • the canonical B0 under the air-path order keeps topology, bindings, DesignAirFlow and TM59 identical;
    • but hourly room temperatures move by up to 2.07 K in isolated hours (mean <= 0.0013 K).

    From here on, B0 and B4 are always regenerated together under the same ordering. Nothing is compared against an archived old-order B0.

    Next

    1. Review Fix deterministic native TAS creation order (SAM#113) SAM_Tas#57 -> CI green -> merge into sow/2026-Q3 -> post-merge verification (B0 + B4 regenerated together on merged binaries).
    2. Then the known real project that fails TM59, for final Iteration 3 programme acceptance (fail -> pass evidence).

    PR5B evidence and progress: SAM_Tas codex/pr5b-generic-table-roundtrip @ b1569692 (not merged). #113 and this issue remain OPEN.

  16. SAM-BIM-AI commented on Sep 15, 2026

    @SAM-BIM-AI

    Checkpoint - SAM#113 ordering fix merged; PR5B infrastructure blocker cleared

    • Fix deterministic native TAS creation order (SAM#113) SAM_Tas#57 merged into sow/2026-Q3 as 5d8cfad0c62d36746d6f98cf62ac38e78e63daa1.
    • PR5B's native-TAS infrastructure blocker is cleared. The all-three-dwelling B4 is no longer at the mercy of generated identities.
    • Remaining prerequisite before regenerating on sow/2026-Q3: PR5B's generic multidimensional table round-trip fix (SAM_Tas 495000a1, PR5B branch, unmerged) must reach sow/2026-Q3.
      • Without it, the B4 DX table crashes the TPD server at generation (RPC_E_SERVERFAULT).
      • With it applied locally on top of the merge, B4 generates in the canonical order.
    • Next task: regenerate Iteration 3 B0 and B4 together from the new canonical-order integration branch.
    • Archived guid-order B0 artefacts must not be used as comparison baselines. Creation order is part of TAS's numerical state: identical TM59, but isolated hours move up to ~2 K.

    This issue stays OPEN.

  17. SAM-BIM-AI commented on Sep 15, 2026

    @SAM-BIM-AI

    Checkpoint - both generic PR5B prerequisites merged; infrastructure blocker cleared

    Post-merge verification (merged integration branch)

    • SAM_Tas.sln Release: 0 errors.
    • SAM.Analytical.Tas.TM59.Tests: 906/906.
      • Table round-trip tests: 9/9.
      • SAM#113 creation-order tests: 7/7.
    • Licensed - 3-D table close/reopen: 3 x 4 x 8 equality table, SAM JSON reload -> production write -> save/close/reopen -> production read. For Extrapolate false and true alike:
      • native sizes 3 x 4 x 8;
      • axes ODB / EDB / EFlow;
      • raw flag 0 / -1;
      • 96/96 cells, 0 mismatches.
    • Licensed - PR5B B4 generation, identity seed s1:
      • generates and reconciles (8 room / 14 leg bindings, every design flow matched);
      • no longer faults the TPD server;
      • native component and duct order is byte-identical to the canonical SAM#113 order in all 3 air systems.

    The PR5B infrastructure blocker is cleared.

    Next

    PR5B consolidation. On the merged integration baseline, regenerate B0 and B4 together, then run:

    annual Systems -> ZoneTemperature -> ResultantTemperature bridge -> unchanged TM59 -> PR5 completion.

    Archived guid-order B0 artefacts remain invalid comparison baselines. Creation order is part of TAS's numerical state: identical TM59, but isolated hours move up to ~2 K.

    This issue stays OPEN.

  18. SAM-BIM-AI commented on Sep 15, 2026

    @SAM-BIM-AI

    PR5B production acceptance - B4 = B0 + selected-product cooling module; PRs open, not merged

    PRs against sow/2026-Q3

    Merge order: SAM_Systems -> SAM_Tas -> SAM_UI. SAM is unchanged.

    repo PR implementation commit base tests (re-run 2026-09-15)
    SAM_Systems SAM-BIM/SAM_Systems#24 c36ba11 (+ docs f6523d5) 5213ba9 203/203 (+27)
    SAM_Tas SAM-BIM/SAM_Tas#59 220ea11f (+ docs ae91066d) 00f51520 (#57 + #58) 922/922 (+16)
    SAM_UI SAM-BIM/SAM_UI#103 0d1833ed (+ evidence/docs 569ad882) 0daa072d 1027/1027 (+15)
    • SAM_Tas builds on SAM_Systems' new cooling types, and SAM_UI on both. Each CI clones the same-named dependency branch until merge.
    • Evidence: SAM_UI/documentation/evidence/PR5B-PRODUCTION-ACCEPTANCE.md.
    • The frozen PR5B architecture is unchanged:
      • same-AirSystem recirculation branch;
      • damper-controlled linear law 22 C -> 0.30, 26 C -> 1.0;
      • DX HeatingSetpoint 22 C + HeatingDuty 0 as the gate;
      • surrogate recirculation fan, HGF 0;
      • 3x4x8 equality table, Extrapolate false;
      • 120 l/s validated ceiling.

    MV vs MVRE - reconciled; production B4 is deliberately the B0 Parity MV + cooling

    1. The HR/fan layers are evidence-blocked.
      • B1 is blocked, and B2 is evidence-blocked (E1/E2; the package-ratio issue).
      • The EDSL displacement + active-HR question is open.
      • The PR5A SelectedProduct mode therefore fails closed for the canonical product.
      • A cumulative MVRE B4 would refuse, or would run on MVRE.json's uncertified ε 0.7, which is forbidden.
    2. The branch no longer needs MVRE. The plan's "DX after the exchanger on the MVRE supply path" was found NOT representable and was replaced by the frozen same-AirSystem branch, which is independent of any exchanger.
    3. The contract is layered. Plan §I names variants by layer and pairs every B-variant with B0, so B4 - B0 is the cooling layer's attribution.

    Correction to the 2026-09-15 13:24 comment on this issue. Its "B0" and "B4" (a-B0c / a-B4c-s1) were both generated on MVRE with no unit settings, so both carried the template's uncertified ε 0.7. Its "B0" hours (Studio 18, Bathroom 2) are not the Parity B0. Those numbers are historical architecture evidence only, and are superseded below. A cumulative B2 + cooling variant waits on E1/E2 and EDSL.

    Gate 1 (generation / native order)

    • B4 converts and reconciles:
      • 3 air systems, 8 rooms;
      • 14 legs (3 supply / 6 extract / 5 transfer), every design flow matched;
      • the same SystemZone count as B0.
    • The branch is grounded in all 3 systems:
      • 96-cell table read back, extrapolation off;
      • gate 22 C, HeatingDuty 0;
      • controller on the mixed return acting on 6 / 6 / 4 dampers.
    • Floor-area shares: Kitchen 42.857 / Bedroom 60 / Ensuite 17.143; Studio 90 / Bathroom 30 l/s.
    • Native order:
      • B4 and identity-re-keyed B4 have identical logical-graph, component-order and duct-order hashes in all 3 systems.
      • Against the archived proven MVRE dump, the only difference is Exchanger 1.

    Paired annual result

    Production route, full year, B0 and B4 regenerated together on the same binaries. B4 is resolved through SAM_UI's production PartOIteration3CoolingResolution.

    room B0 h > 26 C B4 h > 26 C mean dRT (K) max abs dRT (K)
    Bathroom_2 16 0 -0.261 3.85
    Studio 1_0 12 7 +0.172 1.65
    Bedroom 2_3 3 2 +0.132 0.60
    Bedroom 2_6 3 2 +0.148 0.55
    Kitchen_4 4 3 +0.062 0.93
    Kitchen_7 4 3 +0.072 0.76
    Ensuite_5 0 0 +0.015 2.72
    Ensuite_8 0 0 +0.039 2.85
    • TM59: 8/8 Pass on both sides, 0/8 outcome changes.
    • B0 reproduces PR4's frozen Candidate B per-room hours exactly.
    • Room coupling, known and reported.
      • The law's 36 l/s floor recirculates year-round and mixes each dwelling's rooms.
      • The warmest room cools, and the occupied dry rooms warm by +0.06..+0.17 K on the annual mean while their exceedance falls.

    Systems validity (route's own plant-room evidence pass on a disposable copy; MVHR-03 / MVHR-02 / MVHR-01):

    check MVHR-03 / MVHR-02 / MVHR-01
    DX cooling below the 22 C gate 0 / 0 / 0 h
    heating 0 h
    cooling 655 / 833 / 1664 h
    air-side sensible 397.9 / 485.2 / 929.8 kWh
    OperatingAirFlow 36..120 l/s (max 120.013), 0 h out of range
    always <= 150 l/s capacity
    DX vs clamped table <= 2e-6 K
    canonical ventilation from design <= 0.0263 l/s
    route room temperatures reproduced to 0 K
    off the ideal law by > 0.5 l/s (reported only) 235 / 137 / 743 h
    inside the published table domain 0 h (ODB >= 29 C only 3 h/yr)

    Reproducibility, B4 vs identity-re-keyed B4:

    • ZoneTemperature and ResultantTemperature bit-identical (8 x 8760);
    • TM59 identical;
    • cooling series identical.

    Limitations

    • The cooling module is an aggregate thermal surrogate. There is no compressor, COP/EER, electrical, latent or humidity behaviour.
    • The surrogate recirculation fan is not a manufacturer fan.
    • Product assignment: the canonical fixture has no Iteration 2 selection, so the harness stamped the smallest capable catalogue unit through VentilationUnitReference.
    • Fail -> pass is not demonstrated, because the canonical B0 already passes TM59.
    • The full RunPartOIteration3 cooling mode is covered by fake-pipeline tests plus the harness via SAM_UI resolution. There was no UI-driven licensed run.
    • One pairing record per Reference A (B4 documents under -It3B4).

    Next

    1. Review / CI / merge the three PRs in order.
    2. Post-merge B0 + B4 regeneration on merged binaries.
    3. Then the known failing real project, for fail -> pass.

    PR5A's E1/E2 gate and the EDSL question remain open. This issue stays OPEN.

  19. SAM-BIM-AI commented on Sep 15, 2026

    @SAM-BIM-AI

    Checkpoint - PR5B merged into sow/2026-Q3

    The PRs were merged in strict order, each as a merge commit pinned to its reviewed head. Before each merge I confirmed:

    • head unchanged;
    • MERGEABLE / CLEAN;
    • build + spdx green;
    • no reviews or comments;
    • base unmoved.
    order PR reviewed head merge (= new sow/2026-Q3)
    1 SAM-BIM/SAM_Systems#24 f6523d5 05ca0c1
    2 SAM-BIM/SAM_Tas#59 ae91066d ac85b5c3
    3 SAM-BIM/SAM_UI#103 569ad882 9f515c4c

    Each merged tree is byte-identical to its reviewed head (empty git diff). No source differs from what was reviewed and licensed-tested.

    Post-merge verification (local, VS MSBuild Release)

    • SAM_Tas against merged SAM_Systems 05ca0c1:
      • SAM_Systems.sln and SAM_Tas.sln Release rebuilds: 0 errors.
      • SAM.Analytical.Tas.TM59.Tests 922/922.
      • SAM.Analytical.Tas.Benchmark.Tests 16/16.
    • SAM_UI against merged SAM_Systems 05ca0c1 + SAM_Tas ac85b5c3:
      • SAM_UI.sln Release rebuild: 0 errors.
      • SAM.Analytical.UI.WPF.Tests 1027/1027.
    • SAM_Systems SAM.Analytical.Systems.Tests 203/203. That was on the reviewed head, whose tree is identical to merge 05ca0c1.

    PR5B is integrated

    • SAM_Systems:
      • MechanicalVentilationCoolingSettings;
      • MechanicalVentilationSettings.CoolingSettings;
      • the same-AirSystem recirculation branch materialisation.
    • SAM_Tas:
      • native grounding (Modify.GroundRecirculationCooling);
      • the plant-room evidence route (Modify.RecirculationCoolingResults, SystemVentilationRoute.RecirculationCoolingResults).
    • SAM_UI:
      • PartOIteration3BehaviourMode.SelectedProductCooling (B4 = B0 Parity MV + the cooling module);
      • Parity/B0 remains the default;
      • evidence in documentation/evidence/PR5B-PRODUCTION-ACCEPTANCE.md.

    The annual licensed B0/B4 acceptance was not re-run, because the merged sources are byte-identical to the accepted heads. The canonical acceptance therefore stands:

    • TM59 8/8 Pass for both B0 and B4;
    • 0 h heating;
    • 0 h cooling below the 22 C gate;
    • recirculation 36-120 l/s;
    • ventilation within ~0.027 l/s of design;
    • identity-re-keyed B4 bit-identical.

    Remaining programme gate

    The only remaining Iteration 3 programme gate is the known failing real-project run:

    1a -> 1b -> 2 -> 2B -> 3-B0 -> 3-B4

    It has not been started. PR5A's E1/E2 evidence gate and the EDSL displacement + active-HR question also remain open. This issue stays OPEN.

  20. michaldengusiak commented on Sep 16, 2026

    @michaldengusiak
    Author

    Progress log — 2026-09-16, Part O real-project acceptance + Criterion 1 seasonal-basis closeout

    Four PRs merged into sow/2026-Q3 today, in dependency order:

    PR Reviewed head Merge SHA What
    SAM#119 ad81b21e 17af3245 Docs: records the 3-B4 real-project rerun on the merged recirculation clamp, and the (at-the-time) newly-found Criterion 1 defect
    SAM_Tas#61 f7dbedf0 ff862201 Docs: same 3-B4 rerun, SAM_Tas side
    SAM#120 443f2557, reconciled to 1271d919 against #119 e2c0e2c0 Fix: natural-ventilation TM59 Criterion 1 decided from summer (May–Sep) occupied hours, not annual — SAM.Tests 2154/2154
    SAM_Tas#62 a17ed01 c267f52f Fix: PartODiagnosticLog's hoursExceedingComfortRange aligned to the same summer basis (diagnostic evidence only, no Pass/Fail impact) — SAM.Analytical.Tas.TM59.Tests 931/931

    Evidence position, distinguished:

    1. B4 real-project acceptance: verified (Iteration 3 end-to-end, recirculation clamp in place).
    2. Recirculation-flow clamp: verified (SAM_Tas#60, re-exercised on the real project — refusal gone).
    3. TM59 NV Criterion 1 seasonal basis: fixed and regression-covered (SAM#120).
    4. SAM_Tas diagnostic representation: aligned to the same summer basis (SAM_Tas#62).
    5. Iteration 1b (authored mechanical air, investigation-only), Iteration 2 (acoustic restriction/bypass/boost placeholder), and the reopen-path investigation remain separate, un-started follow-ups — not touched by this work.

    Full detail: SAM/documentation/PartO-TAS-VALIDATION.md, SAM/PROJECT_PROGRESS.md, SAM/documentation/PartF-HANDOVER.md §0 (all updated in SAM#121).

    This issue is not being closed. Per this issue's own closure rule above ("Close this issue only when PR5 / full Iteration 3 is accepted — unless a later human decision deliberately moves PR5 to a separate tracker"): PR5 ("manufacturer-aware behaviour") is listed above as an open, unchecked milestone with an unfinished "Potential later work" list. Items 1–4 above are verified evidence within PR5's line of work (PR5A, PR5B, and this Criterion 1 slice), not the whole of it. No human decision has been made to move PR5 elsewhere, so #111 stays open pending PR5.

  21. added a commit that references this issue on Sep 16, 2026
  22. michaldengusiak commented on Sep 16, 2026

    @michaldengusiak
    Author

    FINAL CLOSEOUT — SAM Part O Iteration 3

    Foundation

    PR1–PR4 frozen and accepted (SAM_Systems#20, SAM_Tas#50/#51/#52, SAM#116, SAM_UI#100).

    PR5B — selected-product cooling: ACCEPTED

    • Canonical fixture acceptance: B4 = B0 Parity MV + the cooling module, 8/8 TM59 Pass, 0/8 outcome
      changes
      vs B0 (SAM_Systems#24, SAM_Tas#59, SAM_UI#103).
    • Real-project acceptance: full 1a → 1b → 2 → 2B → 3-B0 → 3-B4 route run end to end on the real project
      (SHA-256 a7e09a25ae29c7dbb4c690d747a96fcd9f110ca27fb4dc2abe816755368d7e4b). 15/15 ledger stages
      COMPLETED. Candidate B is a genuine engineering TM59 FAIL (3 of 8 rooms), not a refusal — the
      building is a weather-driven failing case by construction, and this is a valid acceptance result.
    • Recirculation clamp verified on the real project — SAM_Tas#60's RecirculationCoolingClamp_Lps
      re-exercised; the prior refusal is gone.
    • Four-airflow invariant preserved throughout: PartFRequiredAirFlow != DesignAirFlow != SelectedEquipmentCapacity != OperatingAirFlow.

    Reopen — B4 close/reopen Review acceptance: PASS 7/7

    A fresh SAM process reopened the preserved real-project B4 pairing on the merged binaries:

    1. restored, not rerun (IsRestored = true, no behaviour-mode picker);
    2. identical engineering result (Reference A FAIL, Candidate B FAIL, same statistics, same TM59 outcomes,
      zero engineering violations on a deep Record/Comparison diff);
    3. 15/15 ledger stages restored, COMPLETED;
    4. no refusal;
    5. zero TAS simulation processes during Review — only TSD result-readers, and the pre-existing
      TAS-process baseline was empty;
    6. catalogue provenance revalidated (VentilationUnitCatalogue:v1, expected SHA matched disk);
    7. seconds, not the ~20-minute annual simulation.

    No production code was changed to obtain this. Full detail:
    SAM/documentation/PartO-TAS-VALIDATION.md
    § B4 close/reopen Review acceptance.

    Correctness fixes

    • TM59 NV Criterion 1 seasonal basis, fixed: SAM#120 — Pass/Fail
      now decided from the May–September basis TM59:2017 requires, not the full year. Verified not to affect the
      (fully mechanical-route) real-project B4 result above.
    • SAM_Tas diagnostic representation aligned: SAM_Tas#62 —
      the identical basis defect in the diagnostic log only, no Pass/Fail impact.

    Dependencies

    Human programme decision

    The proven Iteration 3 explicit Systems/TPD route, including the accepted selected-product cooling/B4
    route, is complete. The remaining manufacturer ventilation behaviour — certified heat recovery, fan
    SFP/power/heat, B1/B2, and manufacturer bypass/B3 — is deliberately moved to a separate tracker:

    #123 — Part O — manufacturer ventilation behaviour: heat recovery, fan performance and bypass

    because its acceptance is blocked on external manufacturer/EDSL evidence (PCDB product-variant equivalence
    for the MRXBOX -AECV variant, certified airflow-indexed SFP, and an open EDSL/TAS technical question about
    displacement + active heat-recovery behaviour) — not on anything left to implement in this repository set.

    PR5A infrastructure (identity plumbing, catalogue v1/v2, the COM-free resolver, per-AHU unit settings, the
    fan-heat route policy, exchanger ExchCalcType conversion/read-back, selected-product orchestration) is
    merged and fail-closed for the real product pending that evidence. PR5A was not technically accepted for
    manufacturer heat-recovery/fan behaviour — that behaviour's external-evidence-dependent acceptance is
    transferred to #123. PR5B (selected-product cooling) is accepted, as recorded above.

    Non-blocking evidence issue

    The B4 reopen exposed one separate, non-blocking finding: a restored Review does not preserve the original
    session's full run-time narration (52 notes reconstructed as 1; the standard archive file is overwritten
    with the thinner version). All engineering data — calculations, pairing identity, ledger, TM59, comparison
    statistics — are unaffected. Tracked at:

    #122 — Part O Iteration 3 — restored Review must preserve original evidence narration

    Closure

    The explicit Systems/TPD Iteration 3 route tracked by #111 is accepted. The only remaining
    manufacturer-ventilation work has deliberately been transferred to a separate tracker (#123). Therefore
    #111's second closure condition is satisfied.

    Closing this issue.

  23. michaldengusiak commented on Sep 16, 2026

    @michaldengusiak
    Author

    Closed per the FINAL CLOSEOUT comment above: the explicit Systems/TPD Iteration 3 route (PR1-PR4 foundation, PR5A infrastructure, PR5B selected-product cooling/B4, real-project acceptance, and the B4 close/reopen Review 7/7) is accepted. Remaining manufacturer-ventilation behaviour is transferred to #123; the non-blocking restored-Review evidence finding is tracked at #122.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Labels

No labels
No labels

Type

No type

Projects

No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions