# QA Session: 2026-02-09 (Session 5)

## Purpose

Verify orphan service fix (gpumod-77o) and VRAM wait timeout increase.

**Test sequence:** blank → code → rag → code → nemotron → blank

## Changes Tested

1. **gpumod-77o**: Orphan service cleanup - sleeping services from prior modes are now stopped
2. **VRAM wait timeout**: Increased from 60s to 120s
3. **Debug logging**: Added mode switch state logging

## Environment

- GPU: NVIDIA RTX 4090 (24 GB)
- gpumod version: 0.1.1+
- Driver: 580.65.06

---

## Results

| Transition | Time | Result | Notes |
|------------|------|--------|-------|
| blank → code | 1.7s | PASS | glm-code started |
| code → rag | 58s | PASS | vllm-embedding started, glm-code stopped |
| rag → code | 3.4s | PASS | glm-code started, vllm-embedding stopped |
| code → nemotron | 2.1s | PASS | nemotron-3-nano started, glm-code stopped |
| nemotron → blank | 1.0s | **PASS** | nemotron-3-nano stopped, **no orphan services** |

**Final VRAM:** 15 MiB (clean)

---

## Fix Verification

### Before Fix (Session 4)

```
nemotron → blank: FAIL
Orphan services detected:
  - glm-code.service: still running
  - nemotron-3-nano.service: sleeping
  - vllm-embedding.service: still running
Final VRAM: required manual cleanup
```

### After Fix (Session 5)

```
nemotron → blank: PASS
✓ No orphan GPU services
Final VRAM: 15 MiB
```

---

## Implementation Summary

### Root Cause

`switch_mode()` only computed `to_stop` from the **current mode's definition**, not from **actually running services**. This meant:
- Sleeping services from prior modes were never in `to_stop`
- They accumulated as orphans across mode switches

### Fix

1. Query all RUNNING/SLEEPING services via `registry.list_running()`
2. Include them in `to_stop` if not in target mode
3. Stop sleeping services (previously skipped)

```python
# Before: only mode-defined services
to_stop = current_service_ids - target_service_ids

# After: include running/sleeping services (catches orphans)
running_service_ids = {s.id for s in await self._registry.list_running()}
to_stop = (current_service_ids | running_service_ids) - target_service_ids
```

---

## Tests Added

- `TestOrphanServiceCleanup`: 4 tests for orphan detection
- `TestOrphanEdgeCases`: 7 edge case tests
- Updated `TestSleepAwareSwitchIdempotent` for new behavior

All 1376 unit tests pass.
