Fix Wave-2 review findings: FX union on re-park, per-project reconcile memo, shared undo mask, decayed test oracle

This commit is contained in:
2026-08-06 17:50:49 -04:00
parent c4038a9e9c
commit 024c619884
9 changed files with 244 additions and 105 deletions
+46
View File
@@ -11,6 +11,7 @@
#include "../src/shell/view/view_reconcile.h"
#include <cstdio>
#include <map>
#include <string>
#include <vector>
@@ -144,6 +145,48 @@ static void testASpentFlagHalfIsNotARecordToRepairFrom() {
CHECK(planReconcile(view::appliedState(applied), view::appliedState(reloaded)).empty());
}
// -- the per-project memo: a tab switch must not erase another project's account --
static void testASecondProjectNotedInBetweenDoesNotEraseTheFirstProjectsMemo() {
// The bug this replaced: a single global slot meant noting project B's applied
// state overwrote project A's entirely, so a repair for A run afterward found no
// memo to compare against and silently skipped -- exactly what a tab-switch then
// an undo on the ORIGINAL project produces within one timer period.
ReaProject* const projA = reinterpret_cast<ReaProject*>(1);
ReaProject* const projB = reinterpret_cast<ReaProject*>(2);
ViewModeModel appliedA;
appliedA.setActiveMode(kDesignModeId);
appliedA.storeSnapshot("{A}", captured(1, 1, 1, 1));
const ViewModeModel appliedB; // untouched — B has nothing driven
std::map<ReaProject*, view::AppliedState> memo;
memo[projA] = view::appliedState(appliedA);
memo[projB] = view::appliedState(appliedB); // noted in between; must not clobber A
const ViewModeModel reloadedA; // A's park record dropped, as an undo would leave it
const ProjectReconcileResult result =
planReconcilePerProject(memo, projA, view::appliedState(reloadedA));
CHECK(result.ops.size() == 4);
CHECK(hasOp(result.ops, "{A}", Flag::MainSend, 1));
}
static void testAProjectWithNoPriorMemoGetsNoRepair() {
// "A project we hold no memo for gets no repair" -- the tool has no account of
// driving anything there, so it has no opinion (see the header's SCOPE note).
ReaProject* const projC = reinterpret_cast<ReaProject*>(3);
const std::map<ReaProject*, view::AppliedState> memo; // never noted
const ViewModeModel reloaded;
const ProjectReconcileResult result =
planReconcilePerProject(memo, projC, view::appliedState(reloaded));
CHECK(result.ops.empty());
}
int main() {
testAnUndoThatLeftOurAppliedOutputAloneRepairsNothing();
testADriftedActiveModeAloneIsNotAReasonToDriveATrack();
@@ -153,6 +196,9 @@ int main() {
testATrackNeitherStateRecordsIsNeverDrivenAtAll();
testASpentFlagHalfIsNotARecordToRepairFrom();
testASecondProjectNotedInBetweenDoesNotEraseTheFirstProjectsMemo();
testAProjectWithNoPriorMemoGetsNoRepair();
if (g_fail == 0) std::printf("All tests passed.\n");
return g_fail ? 1 : 0;
}