|
| 1 | +# Formal Test Plan (v0.3.x) |
| 2 | + |
| 3 | +This document defines a **reproducible** test plan for the *Distributed Mutual Exclusion Explorer* (Variant 3). |
| 4 | +It is designed to support: |
| 5 | +- correctness arguments (especially **mutual exclusion / safety**), |
| 6 | +- fault + recovery demonstrations, |
| 7 | +- repeatable evidence capture for the final report. |
| 8 | + |
| 9 | +> Scope: UI + core simulation behaviour for Token Ring (implemented) and Ricart–Agrawala (prototype). |
| 10 | +
|
| 11 | +--- |
| 12 | + |
| 13 | +## 1. Test environment |
| 14 | + |
| 15 | +- Browser: Chrome / Edge latest (desktop). |
| 16 | +- Local server: `python -m http.server 5500` (or VS Code Live Server). |
| 17 | +- URL: `http://localhost:5500/ds-mutex/index.html` |
| 18 | +- Run speed: 350ms (default) unless stated. |
| 19 | + |
| 20 | +--- |
| 21 | + |
| 22 | +## 2. Definitions / expected properties |
| 23 | + |
| 24 | +### 2.1 Safety (must hold) |
| 25 | +- **Mutual exclusion**: at most one process is in the critical section (CS) at any time. |
| 26 | +- Safety indicator in UI should remain **OK** in normal runs. |
| 27 | + |
| 28 | +### 2.2 Liveness (may not hold under faults) |
| 29 | +- In fault-free runs, requesting processes should eventually enter CS. |
| 30 | +- Under **message loss** (RA), liveness may fail (expected teaching outcome). |
| 31 | + |
| 32 | +--- |
| 33 | + |
| 34 | +## 3. Evidence policy |
| 35 | + |
| 36 | +For each test: |
| 37 | +1. Capture a short trace segment (copy/paste or export). |
| 38 | +2. Export evidence when relevant: |
| 39 | + - **Export evidence (JSON+trace+PNG)**. |
| 40 | +3. Use curated PNGs in `report/figures/` (not `report/figures/export/`). |
| 41 | + |
| 42 | +--- |
| 43 | + |
| 44 | +## 4. Manual UI test cases |
| 45 | + |
| 46 | +### TR-01: Token Ring — basic mutual exclusion |
| 47 | +**Setup** |
| 48 | +- Algorithm: Token Ring |
| 49 | +- Processes: 4 |
| 50 | +- Mode: interactive |
| 51 | + |
| 52 | +**Steps** |
| 53 | +1. Click `Request CS` on P1. |
| 54 | +2. Click `Run` until P1 enters CS (or `Step` until it happens). |
| 55 | +3. While P1 is in CS, click `Request CS` on P2. |
| 56 | +4. Click `Step` 3–5 times (do not release P1 yet). |
| 57 | +5. Confirm P2 does **not** enter CS while P1 is still in CS. |
| 58 | +6. Click `Release CS` on P1. |
| 59 | +7. Click `Run` / `Step` until P2 enters CS. |
| 60 | + |
| 61 | +**Expected** |
| 62 | +- Safety: OK throughout. |
| 63 | +- Exactly one process in CS at a time. |
| 64 | +- Trace includes entries and token passes. |
| 65 | + |
| 66 | +--- |
| 67 | + |
| 68 | +### TR-02: Token Ring — token loss stalls progress, regeneration recovers |
| 69 | +**Setup** |
| 70 | +- Algorithm: Token Ring |
| 71 | +- Processes: 4 |
| 72 | + |
| 73 | +**Steps** |
| 74 | +1. Click `Drop token`. |
| 75 | +2. Click `Request CS` on P1. |
| 76 | +3. Click `Step` 2–3 times (no entry should occur). |
| 77 | +4. Click `Regenerate token`. |
| 78 | +5. Click `Step` / `Run` until P1 enters CS. |
| 79 | + |
| 80 | +**Expected** |
| 81 | +- Before regeneration: no progress due to lost token. |
| 82 | +- After regeneration: progress resumes and P1 can enter CS. |
| 83 | +- Safety: OK. |
| 84 | + |
| 85 | +--- |
| 86 | + |
| 87 | +### TR-03: Token Ring — crash + recovery (demonstration) |
| 88 | +**Setup** |
| 89 | +- Algorithm: Token Ring |
| 90 | +- Processes: 4 |
| 91 | + |
| 92 | +**Steps** |
| 93 | +1. Click `Crash` on the current token holder (commonly P1 after reset). |
| 94 | +2. Observe token loss / stalled behaviour. |
| 95 | +3. Click `Recover` for the crashed process. |
| 96 | +4. Click `Regenerate token`. |
| 97 | +5. Click `Request CS` on any live process and confirm the system can progress again. |
| 98 | + |
| 99 | +**Expected** |
| 100 | +- Demonstrates fault + recovery path. |
| 101 | +- Safety: OK (or clearly explained if crash in CS produces a warning/violation state in your implementation). |
| 102 | + |
| 103 | +--- |
| 104 | + |
| 105 | +### RA-01: Ricart–Agrawala — basic request/reply and CS entry |
| 106 | +**Setup** |
| 107 | +- Algorithm: Ricart–Agrawala |
| 108 | +- Processes: 4 |
| 109 | +- Mode: interactive |
| 110 | + |
| 111 | +**Steps** |
| 112 | +1. Click `Request CS` on P1. |
| 113 | +2. Click `Step` repeatedly to deliver messages until P1 enters CS. |
| 114 | +3. Click `Release CS` on P1. |
| 115 | +4. Confirm deferred replies (if any) are sent and the queue drains. |
| 116 | + |
| 117 | +**Expected** |
| 118 | +- Trace shows REQUEST broadcast, REPLY messages, and CS entry. |
| 119 | +- Safety: OK. |
| 120 | + |
| 121 | +--- |
| 122 | + |
| 123 | +### RA-02: Ricart–Agrawala — tie-break by process ID (same timestamp) |
| 124 | +**Setup** |
| 125 | +- Algorithm: Ricart–Agrawala |
| 126 | +- Processes: 2 |
| 127 | +- Mode: interactive |
| 128 | + |
| 129 | +**Steps** |
| 130 | +1. Click `Request CS` on P1. |
| 131 | +2. Immediately click `Request CS` on P2. |
| 132 | +3. Click `Step` until one process enters CS. |
| 133 | + |
| 134 | +**Expected** |
| 135 | +- With same logical timestamp, smaller numeric PID wins: **P1 enters before P2**. |
| 136 | +- Safety: OK. |
| 137 | +- Trace makes the tie-break visible (or is explained in report). |
| 138 | + |
| 139 | +--- |
| 140 | + |
| 141 | +### RA-03: RA fault — Drop next in-flight message (queue head) |
| 142 | +**Purpose** |
| 143 | +Demonstrate that message loss can break liveness without breaking safety. |
| 144 | + |
| 145 | +**Setup** |
| 146 | +- Algorithm: Ricart–Agrawala |
| 147 | +- Processes: 4 |
| 148 | + |
| 149 | +**Steps** |
| 150 | +1. Click `Request CS` on P1. |
| 151 | +2. Click `Step` once or twice until queue is non-empty. |
| 152 | +3. Click `Drop next in-flight msg`. |
| 153 | +4. Continue clicking `Step` until the queue becomes empty. |
| 154 | + |
| 155 | +**Expected** |
| 156 | +- Safety: OK. |
| 157 | +- If the dropped message was a required REQUEST/REPLY, P1 may never enter CS. |
| 158 | +- Trace should explicitly explain who is waiting for whom (stalled reason). |
| 159 | + |
| 160 | +--- |
| 161 | + |
| 162 | +### RA-04: RA fault — drop-next-send (drop next outgoing message) |
| 163 | +**Setup** |
| 164 | +- Algorithm: Ricart–Agrawala |
| 165 | +- Processes: 4 |
| 166 | + |
| 167 | +**Steps** |
| 168 | +1. Click `Arm drop-next-send`. |
| 169 | +2. Click `Request CS` on P1. |
| 170 | +3. Click `Step` until queue drains. |
| 171 | + |
| 172 | +**Expected** |
| 173 | +- Safety: OK. |
| 174 | +- Progress may stall due to a missing message. |
| 175 | +- Trace clearly states the waiting condition (e.g., “P1 is waiting for REPLY from P2”). |
| 176 | + |
| 177 | +--- |
| 178 | + |
| 179 | +## 5. Optional automated smoke tests (recommended) |
| 180 | + |
| 181 | +Run locally: |
| 182 | +```bash |
| 183 | +cd ds-mutex |
| 184 | +npm test |
| 185 | +``` |
| 186 | + |
| 187 | +This runs `tools/smoke_tests.mjs` (no dependencies) and validates: |
| 188 | +- basic mutual exclusion sequences for Token Ring, |
| 189 | +- RA tie-break ordering (2 processes), |
| 190 | +- RA “drop-next-send” produces a stalled state (expected). |
| 191 | + |
| 192 | +CI runs the same tests via GitHub Actions (see `.github/workflows/ci.yml`). |
0 commit comments