--- id: DEC-0035 ticket: system-run-cart title: Remove Userland system.run_cart and Preserve Direct Boot status: accepted created: 2026-07-03 ref_agenda: AGD-0003 tags: [] --- ## Status Accepted. ## Contexto `system.run_cart` existe na ABI publica, mas nao possui comportamento real de troca de cartucho. Isso cria uma falsa promessa: um guest pode declarar/chamar uma operacao que aparenta iniciar outro cartucho, enquanto o runtime retorna sucesso vazio ou nao executa uma transicao completa. A discussao fechou tres separacoes: - boot direto por host/CLI/debug e necessario e deve permanecer; - apps/userland nao devem iniciar cartuchos diretamente; - troca `Game A -> Home -> Game B` exige um orquestrador de SystemOS proprio, separado em `DSC-0043 / AGD-0044`. `AGD-0041` permanece responsavel por `Game -> Home -> mesmo Game`, foreground, pausa/suspensao e retorno ao mesmo Game. ## Decisao `system.run_cart` MUST be removed from the userland guest ABI. No app, cartridge, Shell app, or other userland guest code MAY directly request cartridge boot through `system.run_cart`. The platform MUST NOT preserve compatibility for the current userland `system.run_cart` surface. It MUST NOT remain as a callable stub, reserved guest syscall that returns success, or capability-gated userland escape hatch. Direct boot MUST remain supported through host/CLI/debug or equivalent single-game launch paths. This direct boot path is a host/system entrypoint, not a guest syscall. Internal cartridge loading MAY continue to use the existing loader path, including directory cartridges and test fixtures. `.pmc` support is not required by this decision. If apps ever need to request navigation in the future, that MUST be designed as a separate SystemOS-mediated surface with different naming and semantics. It MUST NOT reintroduce userland `run_cart` as direct cartridge boot. ## Rationale Direct cartridge boot is essential for development, debugging, automated tests, and future distribution modes where the runtime launches as a single game. That use case does not require a guest-visible syscall. Userland cartridge boot would give app code authority over system navigation, lifecycle, cleanup, target resolution, and failure policy. Those concerns belong to SystemOS/firmware and later to the cartridge switch orchestrator, not to a VM guest syscall. Keeping a stub or compatibility surface would preserve the current ambiguity. The public ABI should not advertise an operation that either does nothing or looks like direct app-controlled navigation. ## Invariantes / Contrato - Guest/userland MUST NOT expose or call `system.run_cart`. - The public syscall registry, declarations, generated bindings, and docs MUST stop presenting `system.run_cart` as an app-callable operation. - Booting a cartridge directly MUST remain available from host/CLI/debug flows. - Direct boot MUST enter the runtime with a selected cartridge target; it MUST NOT depend on a guest syscall issued after VM startup. - Loader code MAY remain reusable by host/firmware/SystemOS internals. - Loader code MUST NOT become lifecycle orchestration authority. - `Game -> Home -> same Game` remains owned by `AGD-0041`. - `Game A -> Home -> Game B` remains owned by `DSC-0043 / AGD-0044`. - `.pmc`, app catalog, launcher UX, marketplace/distribution, and full cartridge replacement under Home are outside this decision. ## Impactos - **Spec / ABI:** remove or retire `system.run_cart` from the userland syscall surface. Any syscall table, PBS declarations, generated metadata, or docs must stop advertising it to apps. - **Runtime / VM:** guest dispatch must no longer treat `system.run_cart` as a valid userland operation. If obsolete bytecode or declarations still reach the runtime during migration, they must fail explicitly rather than report success. - **Firmware / Host:** direct boot remains supported for command-line, debugger, test harness, and future single-game launch flows. - **SystemOS:** no new cart-switch orchestrator is required by this decision. That work is deferred to `DSC-0043 / AGD-0044`. - **Tooling:** tools must continue to support direct cartridge launch for development and test workflows, without relying on a guest syscall. - **Tests:** coverage must prove both sides: userland cannot declare/call `system.run_cart`, and direct boot of a cartridge still works. ## Alternativas Descartadas - **Implement `system.run_cart` as a normal syscall:** rejected because it gives userland direct navigation authority and mixes guest execution with system lifecycle. - **Keep a compatibility stub:** rejected because no compatibility is required and a stub preserves the false contract. - **Make `system.run_cart` privileged but still guest-visible:** rejected for v1 because it keeps the ambiguous idea that some guest profile may directly boot cartuchos. - **Implement full `Home -> another Game` now:** rejected for this decision; it requires SystemOS orchestration after the `AGD-0041` foreground contract. ## Referencias - Agenda: `AGD-0003` - Foreground/pause scope: `AGD-0041` - Future cartridge switch orchestrator: `DSC-0043 / AGD-0044` - Related lessons: `LSN-0041` SystemOS lifecycle authority, `LSN-0042` SystemOS service ownership boundary, `LSN-0043` SystemOS domain facades. ## Propagacao Necessaria - Remove `SystemRunCart` from userland ABI declarations and generated syscall metadata. - Remove or rewrite runtime dispatch paths that return success for `system.run_cart`. - Preserve host/CLI/debug direct boot paths and add regression tests for them. - Add negative tests for guest/userland declaration or call attempts. - Update any documentation/spec text that describes `system.run_cart` as app-callable. ## Revision Log - 2026-07-03: Initial draft from `AGD-0003`.