This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
OASIS_OS is an embeddable operating system framework in Rust (edition 2024). It provides a skinnable shell with a scene-graph UI, command interpreter, virtual file system, browser engine (HTML/CSS/Gemini), plugin system, and remote terminal. It renders to any pixel buffer + input stream. Built from scratch in Rust starting early 2026, inspired by PSP homebrew shells like PSIX. Sixteen built-in skins are implemented; 13 of them also ship as external TOML files in skins/ (the other 3 — corrupted, desktop, modern — are built-in only).
Default virtual resolution is 480x272 (PSP native). Skins may override this (e.g. modern=800x600, xp=1024x768); the backend canvas/window scales to match.
All CI commands run inside Docker containers. For local development you can run cargo directly (SDL3 is compiled from source automatically via the build-from-source feature), or use the Docker wrapper.
# Build (desktop)
cargo build --release -p oasis-app
# Build via Docker (matches CI exactly)
docker compose --profile ci run --rm rust-ci cargo build --workspace --release
# Run tests
cargo test --workspace
# Run a single test
cargo test --workspace -- test_name
# Run tests in a specific crate
cargo test -p oasis-core
# Format check
cargo fmt --all -- --check
# Apply formatting
cargo fmt --all
# Lint (CI treats warnings as errors)
cargo clippy --workspace -- -D warnings
# Lint exactly as CI does — ALWAYS run this before opening a PR. The CI image
# pins a specific Rust version (rust:1.93-slim), so a locally newer/older
# toolchain can pass clippy while CI fails (lints change between releases).
docker compose --profile ci run --rm rust-ci cargo clippy --workspace -- -D warnings
# License/advisory audit
cargo deny check
# Build PSP backend (excluded from workspace, requires nightly + cargo-psp)
cd crates/oasis-backend-psp && RUST_PSP_BUILD_STD=1 cargo psp --release
# Build PSP overlay plugin PRX (excluded from workspace, kernel mode)
cd crates/oasis-plugin-psp && RUST_PSP_BUILD_STD=1 cargo psp --release
# Build UE5 FFI shared library
cargo build --release -p oasis-ffi
# Build WASM backend (requires wasm-pack)
./scripts/build-wasm.sh # debug build
./scripts/build-wasm.sh --release # release (smaller + faster)
# Serve: python3 -m http.server 8080 → http://localhost:8080/www/
# Take screenshots
cargo run -p oasis-app --bin oasis-screenshotformat check -> clippy -> nightly clippy (advisory) -> doc build -> markdown link check -> test -> release build -> screenshot regression -> cargo-deny -> benchmarks -> PSP EBOOT build -> PPSSPP headless test -> code coverage -> GitHub Pages deploy (WASM)
All steps run via docker compose --profile ci run --rm rust-ci.
Memory analysis (memory-ci.yml, separate non-blocking workflow):
- ASAN (AddressSanitizer) -- catches use-after-free, buffer overflow, leaks (~2x slowdown)
- Valgrind massif -- heap profiling with peak memory assertions for video decode
Both jobs use continue-on-error: true and run on pushes to main, PRs touching crates/oasis-video/** or crates/oasis-core/**, and workflow_dispatch.
Nightly streaming (nightly-streaming.yml, separate workflow):
- End-to-end streaming validation for TV Guide video playback
oasis-types (foundation: Color, Button, InputEvent, backend traits, error types, geometry)
├── oasis-vfs (virtual file system: MemoryVfs, RealVfs, GameAssetVfs)
├── oasis-platform (platform service traits: Power, Time, USB, Network, OSK)
├── oasis-sdi (scene display interface: named object registry, z-order)
├── oasis-net (TCP networking, PSK auth, remote terminal, FTP)
├── oasis-mcp (optional MCP control server: Streamable HTTP + JSON-RPC, agent tool dispatch)
├── oasis-audio (audio manager, playlist, MP3 ID3 parsing)
├── oasis-ui (32 widgets: Button, Card, TabBar, ListView, flex layout, etc.)
├── oasis-wm (window manager: drag/resize, hit testing, decorations)
├── oasis-skin (TOML skin engine, 16 skins, theme derivation)
├── oasis-terminal (90+ commands across 17+ modules, shell features)
├── oasis-browser (HTML/CSS/Gemini: DOM, CSS cascade+@media, layout engine, @font-face web fonts (fontdue TTF/OTF rasterizer, font registry, glyph texture cache), full 2D CSS transforms + 3D transform functions (rotateX/Y/Z, translate3d, scale3d, rotate3d, matrix3d, perspective()) with screen-space perspective projection from ancestor `perspective:`, transform-style: preserve-3d propagation, transform-origin Z, perspective-origin, and backface-visibility culling, Canvas 2D path API, SVG paths/groups, light compositor, z-index stacking contexts, nested scroll containers, form elements with select dropdown + label association, hover-triggered CSS transitions, soft hyphens, bidi text, JS DOM bindings)
├── oasis-js (JavaScript engine: QuickJS-NG via rquickjs on all backends incl. PSP)
├── oasis-video (MP4/H.264+AAC decode; StreamingBuffer sliding-window; features: h264, no-std-demux, video-decode)
├── oasis-vector (vector graphics: scene graph, path ops, icons, frame-driven animations)
├── oasis-shader (animated shader wallpapers: Shadertoy-style fragment shaders)
├── oasis-rasterize (software rasterizer for CPU-side rendering)
├── oasis-i18n (internationalization support)
├── oasis-test-backend (mock backend for testing)
├── oasis-app-core (shared app framework: AppTrait, common utilities)
├── oasis-app-games (Games app)
├── oasis-app-paint (Paint app)
├── oasis-app-text-editor (Text Editor app)
├── oasis-app-calculator (Calculator app)
├── oasis-app-media (Music Player + Photo Viewer apps)
├── oasis-app-tv-guide (TV Guide app)
├── oasis-app-radio (Internet Radio app)
├── oasis-app-settings (Settings app)
├── oasis-app-file-manager (File Manager app)
├── oasis-app-browser (Browser launcher placeholder)
├── oasis-app-network (Network status app)
├── oasis-app-package-manager (Package Manager app)
├── oasis-app-system-monitor (System Monitor app)
└── oasis-core (coordination only: dashboard, agent, plugin, script, terminal; all apps live in oasis-app-* crates)
├── oasis-backend-sdl (SDL3 desktop/Pi rendering + input + audio)
│ └── oasis-app (binary entry points: oasis-app, oasis-screenshot; oasis-video[video-decode])
├── oasis-backend-wasm (Canvas 2D + DOM input + Web Audio; iframe overlay drives a Browser pane and a YouTube embed; YouTube search + thumbnail grid via Invidious; feature: wasm-youtube)
├── oasis-backend-ue5 (software RGBA framebuffer for Unreal Engine 5)
│ └── oasis-ffi (cdylib C-ABI for UE5 integration; oasis-video[video-decode])
├── oasis-backend-psp (excluded from workspace, PSP hardware; oasis-video[no-std-demux])
└── oasis-plugin-psp (excluded from workspace, kernel-mode PRX overlay)
PSP has meaningful enough constraints that the detail lives in
docs/psp-architecture.md. Summary:
- Two binaries —
oasis-backend-psp(EBOOT.PBP, the shell) andoasis-plugin-psp(PRX overlay loaded by CFW, <64 KB, nooasis-coredependency). See ADR 004. - GU command buffer (1 MB) overflows with dense pages. Don't
double-start GU frames after
swap_buffers_inner(). - QuickJS-NG built through pspdev's
psp-gccwith-msingle-float, linked viapsp-ld, libc provided byoasis-backend-psp/src/quickjs_shim.rs— seedocs/javascript-engine.md. - TLS 1.3 via
embedded-tls+UnsecureProviderbecause PSP firmware ships 2008-vintage CAs. - Video streaming via ME hardware decode (
sceMpegNAL direct path) +sceAudiocodec, ≤480p only. Seedocs/video-streaming.md.
Progressive streaming via StreamingBuffer (sliding-window over an
Arc<StreamingInner> while symphonia decodes from the same buffer
via Read + Seek). Probe-mode reads return zeros, deferred tail
probe for moov-at-end files, CDN failover through the archive.org
URL for fresh 302 redirects. Full details in
docs/video-streaming.md.
oasis-types/src/backend/ defines the only abstraction boundary between core and platform (re-exported by oasis-core):
SdiCore-- required rendering (13 methods: init, clear, blit, fill_rect, draw_text, swap_buffers, load_texture, destroy_texture, set_clip_rect, reset_clip_rect, measure_text, read_pixels, shutdown)SdiBackend-- a marker super-trait with no methods of its own. A blanket impl satisfies it for any type that implementsSdiCoreplus all nine extension traits:SdiShapes,SdiGradients,SdiAlpha,SdiText,SdiTextures,SdiClipTransform,SdiVector,SdiBatch,SdiRenderTarget. The extensions live underoasis-types/src/backend/extensions/(one file per trait, re-exported viaextensions/mod.rs) and total ~55 default-impl methods (shapes, gradients, alpha/blend, text styling, texture management, clipping/transforms, vector path ops, batched submission, offscreen render targets).SdiBatchin particular providesbegin_batch/flush_batchplussubmit_rect_batch/submit_text_batchfor batched rect and text geometry submission (backends can override with GPU geometry calls).InputBackend-- input polling (returnsVec<InputEvent>)NetworkBackend-- TCP networkingAudioBackend-- audio playback
Core code never calls platform APIs directly. All platform interaction goes through these traits.
The framework lives in 50 crate directories under crates/:
- 40 workspace members (the desktop / WASM / UE5 build surface — what
cargo build --workspacecompiles) - 1 explicitly excluded crate (
oasis-backend-psp, on themipsel-sony-psptarget) - 9 standalone PSP-target crates that are not mentioned in the workspace
Cargo.tomlat all and are built individually viacargo psp:oasis-plugin-psp,oasis-devloop-psp,oasis-me-boot,oasis-prx-decrypt-psp,oasis-recovery-psp,oasis-usb-client-psp,oasis-usb-debug-psp,oasis-usb-trace-psp,oasis-usb-vbus-psp
Each module below is its own crate (previously all in oasis-core):
- oasis-types -- Foundation types:
Color,Button,InputEvent, backend traits (SdiCore,SdiBackend,InputBackend,NetworkBackend,AudioBackend), error types, TLS, bitmap font metrics,geometry.rs(shared shape algorithms) - oasis-sdi -- Scene Display Interface: named objects with position, size, color, texture, text, z-order, gradients, rounded corners, shadows
- oasis-skin -- Data-driven TOML skin system with 16 built-in skins (13 of which also ship as external TOML in
skins/; the other 3 —corrupted,desktop,modern— are built-in only). Theme derivation from 9 base colors. - oasis-browser -- Embeddable HTML/CSS/Gemini rendering engine: WHATWG HTML, full CSS cascade with
@media/@container/@layer/@supports/@scope/ CSS Nesting /:has(), viewport-aware stylesheet parsing, 2D + 3D transforms,@font-faceweb fonts, canvas + SVG, HTTP/1.1 + HTTP/2 over rustls, cookies, CSP, reader mode, forms, bookmarks. Feature catalogue:docs/browser-engine.md. Backlog:docs/browser-backlog.md. - oasis-js -- QuickJS-NG via
rquickjson every target (desktop / WASM / UE5 / PSP). DOM bindings (getElementById,querySelector,fetch,setTimeout,localStorage, event bubbling, …) feature-gated asjavascript. PSP cross-compile is non-trivial (pspdev toolchain,-msingle-float,psp-ld, hand-rolled libc shim) — seedocs/javascript-engine.md. - oasis-ui -- 32 reusable widgets: Button, Card, TabBar, Panel, InputField, ListView, ScrollView, ProgressBar, Toggle, NinePatch, flex layout, Accordion, Avatar, Badge, Checkbox, ColorPicker, ContextMenu, DatePicker, Divider, Dropdown, Icon, Modal, Radio, RichText, Slider, SpinBox, Spinner, SplitPane, Table, Toast, Tooltip, TreeView
- oasis-vfs -- Virtual file system:
MemoryVfs(in-RAM),RealVfs(disk),GameAssetVfs(UE5 with overlay writes) - oasis-terminal -- Command interpreter with 90+ commands across 17 modules (core, text, file, system, dev, fun, security, doc, audio, network, skin, UI, plus agent/plugin/script/transfer/update registered by oasis-core). Shell features: variable expansion, glob expansion, aliases, history, piping
- oasis-wm -- Window manager (window configs, hit testing, drag/resize, minimize/maximize/close)
- oasis-net -- TCP networking with PSK authentication, remote terminal, FTP transfer
- oasis-mcp -- Optional MCP control server (off by default). Minimal Streamable-HTTP transport + JSON-RPC 2.0 / MCP dispatch over a non-blocking
NetworkStream; app-agnostic (depends only onoasis-types) with aToolDispatchercallback the app implements incrates/oasis-app/src/mcp_tools.rs. Lets an on-device agent drive the shell. Seedocs/mcp-server.md - oasis-audio -- Audio manager with playlist, shuffle/repeat modes, MP3 ID3 tag parsing
- oasis-platform -- Platform service traits: PowerService, TimeService, UsbService, NetworkService, OskService
- oasis-video -- MP4 / H.264 + AAC decode pipeline. Feature flags:
h264(openh264 + symphonia demux/AAC),no-std-demux(PSP-safedemux_lite::Mp4Lite),video-decode(re-exportsSoftwareVideoDecoderfor desktop/UE5). Desktop progressive streaming + PSP in-memory ME-hardware pipeline are documented indocs/video-streaming.mdanddocs/psp-architecture.md§Video Streaming. - oasis-vector -- Resolution-independent vector graphics: scene graph with path-based drawing operations (fill, stroke, arcs, beziers), Altimit-style dashboard icons, and frame-driven animations. Integrates via
SdiBackendvector graphics trait extensions - oasis-shader -- Animated shader wallpapers: Shadertoy-style fragment shaders (voronoi, city lights, ocean waves, calm waves, Balatro)
- oasis-app-core -- Shared app framework:
AppTrait, common utilities for extracted app crates - oasis-app-* -- 13 extracted app crates:
oasis-app-games,oasis-app-paint,oasis-app-text-editor,oasis-app-calculator,oasis-app-media(Music Player + Photo Viewer),oasis-app-tv-guide,oasis-app-radio,oasis-app-settings,oasis-app-file-manager,oasis-app-browser,oasis-app-network,oasis-app-package-manager,oasis-app-system-monitor - oasis-core -- Coordination layer: dashboard, agent/MCP, plugin, scripting, status/bottom bars, desktop taskbar, in-core Terminal app. All other apps live in
oasis-app-*crates;oasis-coreno longer ships any app implementations beyond the Terminal delegate (which the desktop input pipeline pumpsset_linesinto) and theSimpleAppplaceholder used by the plugin system for dynamically registered apps.
Proportional bitmap font rendering from glyph ink bounds. oasis-types provides glyph_advance() with variable per-character widths (3-8px). Each backend has its own glyph table in font.rs. The PSP backend additionally uses system TrueType fonts via psp::font with a VRAM glyph atlas. No external font dependencies for desktop/UE5.
Exports C-ABI functions: oasis_create, oasis_destroy, oasis_tick, oasis_send_input, oasis_get_buffer, oasis_get_dirty, oasis_send_command, oasis_free_string, oasis_set_vfs_root, oasis_register_callback, oasis_add_vfs_file. This is how UE5 (or any C-compatible host) embeds OASIS_OS.
- MSRV: 1.91.0 (uses
str::floor_char_boundary) - Max line width: 100 characters
- Clippy warnings are CI errors (
-D warnings) - Workspace lints:
clone_on_ref_ptr,dbg_macro,todo,unimplemented= warn;unsafe_op_in_unsafe_fn= warn;unwrap_used= deny - All unsafe blocks require
// SAFETY:comments - Tests are in-module (
#[cfg(test)] mod tests), not in a separatetests/directory - Dual-licensed: Unlicense + MIT
docker-compose.yml profiles:
ci-- rust-ci container (rust:1.93-slim + cmake + X11/audio dev libs + nightly + cargo-deny)psp-- PPSSPP emulator (multi-stage build, NVIDIA GPU passthrough)services-- MCP server containers (code-quality, content-creation, gemini, etc.)
Key documentation files for agents and contributors. Read these for deeper context on specific topics rather than loading everything into every conversation.
docs/design.md-- Technical design document v2.4 (~1500 lines, comprehensive architecture)docs/browser-engine.md-- Browser feature catalogue (HTTP, HTML, CSS, layout, fonts, chrome, JS bindings)docs/javascript-engine.md-- QuickJS-NG integration and PSP cross-compiledocs/psp-architecture.md-- PSP two-binary split, GU, TLS 1.3, ME video decodedocs/video-streaming.md-- DesktopStreamingBufferprogressive playbackdocs/boot-splash.md-- Functional boot splash: BIOS phase probes, splash-phase warm-up,BootSplashAPIdocs/adr/001-arena-based-dom.md-- ADR: Arena-based DOM allocationdocs/adr/002-vfs-abstraction.md-- ADR: Virtual file system designdocs/adr/003-backend-trait-design.md-- ADR: Backend trait hierarchydocs/adr/004-psp-two-binary-architecture.md-- ADR: PSP EBOOT + PRX splitdocs/adr/005-toml-skin-system.md-- ADR: TOML skin engine
docs/getting-started.md-- Getting started guidedocs/adding-commands.md-- How to add terminal commandsdocs/terminal-commands.md-- Catalog of built-in terminal commands grouped by moduledocs/skin-authoring.md-- Skin creation with full TOML referencedocs/plugin-development.md-- Plugin development guidedocs/ffi-integration.md-- UE5 / C-ABI integration guidedocs/psp-plugin.md-- PSP kernel plugin (PRX) documentationdocs/browser-backlog.md-- Browser engine backlog and roadmapdocs/theming-desktop-plan.md-- Advanced theming + PSIX-style desktop metaphor plan (asset pipeline, free icons, shaped chrome, perf)
docs/oasis-js.md-- JavaScript engine desktop API + DOM bindings catalog (PSP cross-compile lives injavascript-engine.md)docs/networking.md-- TCP transport, PSK auth, remote terminal protocol, TLS, FTP-like file transferdocs/mcp-server.md-- Optional MCP control server: enabling, transport, tool catalog, security, agent (Claude Code) integrationdocs/audio-engine.md-- AudioManager, playlist/repeat/shuffle, radio sources, streaming back-pressuredocs/vector-graphics.md-- VectorOp/VectorScene, icon catalog, AnimClock, SdiVector integrationdocs/shaders.md-- Built-in shader wallpapers, GPU + software backends, extension guide
docs/psp-autorun.md-- Boot-time script runner for deterministic PSP/PPSSPP integration testsdocs/troubleshooting.md-- Troubleshooting common issuesdocs/security.md-- Security policy and advisoriesAGENTS.md-- Multi-agent system configuration and CI workflowCONTRIBUTING.md-- Contribution policy (AI-authored only)scripts/psp-scenarios.md-- PSP test scenario documentation