# MBNWEB-20260712-M 실제 PGM 검증 계획

이 문서는 Round L의 명령 송신 전 창 상태 실패를 교정한 새 Gate A 회차를 고정한다.
Round M Gate A는 승인 후 정확히 한 번 실행됐으며, **CONNECT 뒤 PREPARE 전 증거
감시기 회귀로 중단**됐다. Round M은 재실행하지 않으며 현재 앱 연결의 정상 종료는
별도 reconciliation 회차와 별도 승인을 사용한다.

## 실행 결과

| 항목 | 값 |
|---|---|
| Gate A 승인 시각 | `2026-07-12T18:58:03.5845976Z` |
| 승인 파일 | 1,485 bytes, `E893A4D8AB5A7AE4B11FDFEEDFAA210FD60F8A983F0A2EB29696561F3E7E6072` |
| 실행 시작 / 종료 | `2026-07-12T18:58:35.8896597Z` / `2026-07-12T18:59:26.1764949Z` |
| 결과 | `OUTCOME_UNKNOWN_DURING_CLEANUP_NONCOMMAND_CLEANUP_INCOMPLETE` |
| 결과 파일 | 32,877 bytes, `019826B736B80A6C0DB696A5DF55DA68432D314B68EC79A4138E64DDB20870FC` |
| 실행 marker | 20,768 bytes, `7CE1B1E854D66833D8F8AF8DEE1A8DC91FAC4C3B9021D7F86B7DD72271E9384D` |
| CONNECT launch budget | 1회 소비, 앱 PID 37916 |
| PREPARE / TAKE IN / NEXT / Page NEXT | `0 / 0 / 0 / 0` |
| DB write / DISCONNECT / retry | `0 / 0 / 0` |
| PREPARE dispatch journal | 생성되지 않음, `prepareMayHaveBeenIssued=false` |
| Network Monitoring 증가분 | `[R] HELLO Hello`, `[S] SUCCESS HELLO Hello`만 존재 |
| PGM | 검은 화면, scene 출력 없음 |

실패 원인은 K3D 명령이나 capability 변경이 아니다. 설치된 앱은 연결 중 1초마다
`requestId`가 없는 정상 push형 `playout-status`를 WebView에 보낸다. Round M의
증거 감시기는 이 상태 알림까지 요청 응답형 terminal로 분류해
`UNCORRELATED_NATIVE_TERMINAL` 위반을 기록했다. 첫 helper의 연결 확인 시점에는
위반이 0이었지만, 다음 helper 전에 수행한 화면 캡처 동안 상태 알림이 들어왔고 기존
감시기 identity 검사가 실패했다. 따라서 PREPARE 버튼과 K3D LOAD/PREPARE 경계에는
도달하지 않았다.

실행기는 정책대로 Gate A를 재시도하거나 앱을 강제 종료하지 않았다. 결과 생성 뒤
round-local Live 설정과 Gate B capability는 제거됐지만 앱 PID 37916, CDP listener
PID 34988과 `127.0.0.1:23210 -> 127.0.0.1:30001` 연결은 증거 보존을 위해 남았다.
정상 종료와 DISCONNECT는 Round M의 남은 예산으로 추정 실행하지 않고, 현재
Network/PGM/process identity를 다시 결박한 별도 reconciliation 승인 뒤 한 번만
수행한다.

후속 회차용 감시기 후보는 Round M 운영 파일을 건드리지 않고 Git 제외 시험 폴더에
작성했다. 후보는 75,460 bytes,
`B495B2CBD554EA1DC47D91CD6D80E31E42D7D0CC938025937FCCE5E4455563FE`이고,
실제 감시 함수로 수행한 8,635 bytes 오프라인 회귀시험
`41F28F3113EC07B3B36FC9238E753FB5B4467B217F416BAADB3918617DDA240B`이
1초 status push 4회 뒤 재설치와 9개 fail-closed 음성 사례를 통과했다. 이 후보는
새 계획·새 helper 결박·새 승인을 받기 전까지 라이브 실행에 사용하지 않는다.

| 항목 | 고정값 |
|---|---|
| 계획 파일 | `artifacts\pgm-evidence\MBNWEB-20260712-M\round-plan.json` |
| 계획 | 19,042 bytes, `7A1141C5F276729E340227CEEAA48B0E6018632BBA51F43AA94636084AA3C301` |
| schema | `4` |
| 생성 시각 | `2026-07-12T18:44:01.0754197Z` |
| source HEAD / origin main | `4e9ae447897b17862dedb3bc6906963b1793d0cb` |
| 계획 생성 시 실제 명령 | 앱·벤더·창 조작·CONNECT·PREPARE 모두 0건 |

Round M은 Round L의 retry나 남은 예산 사용이 아니다. 새 계획, 새 승인, 새 one-shot
예산을 사용하는 별도 회차다.

## Round L 종료 근거

| 항목 | 값 |
|---|---|
| 상태 | `FAIL_KNOWN_CLEANED`, `outcomeUnknown=false` |
| 계획 | `23E3A6A5400166A47835E146DCC2D19C181E2100D1485DB428F1B10718D89928` |
| Gate A 승인 | `A361843C2E810CEAA2F838F4AA953C4D9910670BD458C3974BBA915DA8B73962` |
| 결과 | 3,421 bytes, `F57BEA9E5F4A215DBB944DCFDC22D8989A5418BDC3910B19B2A11ED9B795FE4D` |
| 실패 | frozen PGM handle 592052가 `visible=true`, `iconic=true` |
| 앱 launch / 벤더 명령 | 0 / 0 |
| CONNECT / PREPARE / DISCONNECT | 0 / 0 / 0 |
| execution marker | 생성되지 않음 |

L 승인은 폐기됐고 재사용하지 않는다. L 종료 뒤 수행한 read-only 확인과 표준 Win32
동기 restore 관측은 후속 설계 근거일 뿐 L 실행 결과로 소급하지 않는다.

## 창 사전복원 교정

Gate A는 실행 marker, capability, 앱, CDP와 벤더 명령보다 앞에서 다음 순서를
강제한다.

1. 설치 package, vendor 등록, Live 설정과 cut을 read-only로 검증한다.
2. MBN 앱과 CDP 9339 listener가 없음을 확인한다.
3. 승인 유효성을 확인한다.
4. Tornado PID/start ticks, 실행 파일·서명, `0.0.0.0:30001` 단일 listener와
   PGM/Network Monitoring의 유일한 exact top-level handle/title/owner를 검증한다.
5. 두 창의 원래 visible/iconic/cloaked/placement를 첫 UI 변경 전에 모두 캡처한다.
6. 필요한 창에만 동기 `ShowWindow`의 `SW_RESTORE` 또는 `SW_SHOW`를 창별 최대 1회
   호출한다.
7. API 반환값을 성공으로 간주하지 않고 최대 5초 동안 실제
   visible/non-iconic/non-cloaked 사후 상태를 확인한다.
8. helper 내부 중간 실패는 두 창을 즉시 원상복구하고 exact placement까지 확인한다.
9. 성공한 원본 상태는 execution marker 전까지 Gate A 메모리에 보존한다. 이후
   `pre-round-window-visibility.json`은 복원 후 상태가 아니라 이 원본을 저장한다.
10. 다시 승인 유효성과 strict desktop target을 검증하고 운영 폴더 closed set을
    확인한 뒤 execution marker를 쓴다. capability는 marker 뒤에 초기화한다.

preflight 자체의 파일 생성, capability, 앱 명령과 벤더 명령은 모두 0건이다. 파일
기반 snapshot 전 실패는 메모리 원본으로, 이후 실패는 authoritative snapshot으로
원복한다. `ShowWindowAsync` fallback과 같은 창에 대한 반복 호출은 없다.

첫 identity 검사 자체가 helper evidence를 반환하기 전에 실패하면 결과의
`windowsRemainArmed`는 실제 mutation 여부를 추정하지 않고 보수적으로 `true`가 될 수
있다. 이는 명령 발행 증거가 아니라 수동 reconciliation 필요 표시로 해석한다.

## 고정 대상과 입력

계획 생성 직전 read-only 관측 시각은 `2026-07-12T18:44:00.9005006Z`다. 이 관측은
정보성 기록이며 실행 시 helper가 전부 다시 검증한다.

| 항목 | 값 |
|---|---|
| Tornado | PID 6972, start ticks `639193655349284515` |
| listener | `0.0.0.0:30001`, 1개, owner 6972 |
| PGM | handle 592052, owner 6972, visible, non-iconic, uncloaked |
| Network Monitoring | handle 79286, owner 6972, visible, non-iconic, uncloaked |
| MBN app / CDP 9339 | 0 / 0 |
| MSIX | `1B0BA713619CC3BD7CB3E03D78FD1EB1CEAF49E7D50F5C00DDFB483917BA5437` |
| installed runtime | `168D1FB8D6487C41C8CEAA828B4D9515A38DB3A970F8EB44FA930ABDD577B8E9` |
| installed manifest | 76,119 bytes, `9631E8188E10F23970F43593B705957A215AE01E2760FE714B08518DB0571A9B` |
| Live 설정 | 895 bytes, `63C6F386D73D8740B7B10994668ED14D95C3D7B68025B0DF034C3F18D660E582` |
| cut | `5001.t2s`, 895,922 bytes, `99CE3B689A42D8C42BEB09A86FA10C2D7C1AEF4F50D324D81276C1A1E4C4D8A7` |
| selector | `KOSPI / 삼성전자 / 1열판기본 / CURRENT / 005930`, page 1, fade 6 |

## 고정 helper와 command-free 시험

| 파일 | bytes | SHA-256 |
|---|---:|---|
| `round-m-gate-a.ps1` | 154,026 | `37340B4B74BE856F109A13D037217951CAF741212CD32F1CEE374647A9AC38EF` |
| `round-m-gate-a-cdp.mjs` | 73,292 | `1D118202CDB9D37315683063BD4DB1083F4EBAC822BE2B3E60A1A08226091BEF` |
| `round-m-gate-b.ps1` | 104,988 | `4DD6F4C7DF1768058E090FA492339EF022A6E6C7A5D1C637C2544E182C44A02C` |
| `round-m-gate-b.mjs` | 98,253 | `FE5CBF1E13004022AA25174BC8828CE5A1953D249CBECD388D4F4AE99AFF41DB` |
| `round-m-window-arm.ps1` | 28,525 | `21D403BC8EA6569C19734E6DE017B4C3DEB5389A9BE0D4E0D17775D2C27D32CD` |
| `round-m-desktop.ps1` | 31,248 | `1E3ABAE50B1337AEA5CCE05CC8125D04F4D6AA0FC2441FD98381B5165032175A` |
| `round-m-monitor.ps1` | 29,900 | `B1CFEBC4A35347ADE5B1B402641EEA19A6975997C05C2726C74D1F4E72694B30` |

| 시험 | bytes | SHA-256 |
|---|---:|---|
| PowerShell 정적·manifest·window 계약 | 22,651 | `A3E425530119FBE758BE96303C4FB256CD1D901B28243571C0D9B815E441B6F5` |
| Node 시간·Int64 계약 | 2,782 | `5141DC0AE0BB3220C7EBB464F4023E838BCF096BE4C11A9B844632C31C8A7935` |
| 계획 생성기 | 17,624 | `F4ABF9E1906EE9AC69140EF534553447DCBAFE0326FD8742D5910775BFADAED8` |

Windows PowerShell 5.1 AST 5개와 Node 구문 3개, identifier-aware 이관,
`backgroundKind` 보존, L iconic 실패, API false여도 사후 상태 성공, already-shown 0회,
5초 timeout, identity drift 0회, 부분 실패 self-rollback, maximized `showCmd=3` 원복과
snapshot 이후 ShowWindow 0회 계약이 통과했다.
K manifest ordinal 역전 41개와 M 기준 0개, 의미 집합 289/289, 3개 문화권 불변성도
통과했다. 계획 원문에는 start ticks가 정확히 한 번 있고 반올림 값은 없다.

## 폐쇄 집합과 명령 예산

승인 전 운영 폴더는 helper 7개, installed manifest, Live 설정, 계획의 정확한 10개
파일이다. `gate-a.json` 생성 뒤 Gate A 시작 시에는 정확한 11개만 허용한다.
preflight는 파일을 만들지 않으므로 두 번째 closed-set 검사도 11개다.

Gate A 예산은 CONNECT 1회, PREPARE 5001/page 1 1회와 명확한 known-outcome
중단 시 정상 DISCONNECT 최대 1회다. TAKE IN, NEXT, Page NEXT, DB write와 retry는
0회다. timeout이나 결과 불명확 상태에서는 어떤 명령도 반복하지 않는다.

## 승인 문구

Gate A는 다음 한 문장을 그대로 승인받은 뒤에만 실행한다.

> 회차 MBNWEB-20260712-M의 계획 SHA-256 7A1141C5F276729E340227CEEAA48B0E6018632BBA51F43AA94636084AA3C301을 승인한다. 현재 K3D 라이선스가 유효함을 확인하며, 현재 PGM 대상 Live CONNECT 1회와 PREPARE 5001 page 1 실행, Gate A가 명확한 known-outcome 상태에서 중단될 때 DISCONNECT 1회를 승인한다. TAKE IN, NEXT, DB write는 아직 승인하지 않는다.

Gate B는 Gate A가 `PASS_PREPARED`로 끝나고 command-free preflight가 새로 통과한
뒤에만 별도로 승인받는다.

> 회차 MBNWEB-20260712-M의 계획 SHA-256 7A1141C5F276729E340227CEEAA48B0E6018632BBA51F43AA94636084AA3C301을 다시 확인했다. 현재 PGM 대상 TAKE IN 5001 page 1 정확히 1회, OnScenePlayed 확인 후 자동 갱신 최대 1회, TAKE OUT All 정확히 1회와 DISCONNECT 1회를 승인한다. NEXT와 DB write 및 결과 불명확 시 재시도는 승인하지 않는다.

source, package, manifest, 설정, cut, selector, PID/start/listener/window, helper, 계획이
바뀌거나 승인 또는 preflight가 허용 시간을 넘으면 승인과 예산을 폐기하고 새 회차로
돌아간다.
