Introduction
Forge OS is an on-device, agentic Android operating-system layer for Large Language Models. You bring your own provider key and the app gives the model a persistent memory system, a sandboxed file workspace, a real Python 3.11 runtime, a headless browser, schedulable jobs, plugins, sub-agents, MCP client, Android device tools, Companion mode, git integration, and more โ all running on the phone with no server.
Built on Jetpack Compose, Hilt, and Chaquopy. Designed to keep working on flaky networks, dead provider keys, or while the screen is off. Version: 1.0.0-alpha.
Installation
Requires Android API 26+ (Android 8.0). Targets API 34. Runs on 64-bit ARM (arm64-v8a) only.
- Download the APK from the download page or GitHub Releases.
- Enable unknown sources: Settings โ Security โ Install unknown apps.
- Install the APK.
- Grant permissions when prompted (notifications, exact alarm, storage).
- Follow the onboarding wizard to add your first provider key.
Provider Setup
Add a key in Settings โ Providers. Supported providers:
- OpenAI
- Anthropic
- Groq
- Google Gemini
- OpenRouter
- xAI, DeepSeek, Mistral, Together, Cerebras
- Local Ollama (self-hosted, no key required)
- Any OpenAI-compatible custom endpoint
Keys are stored in EncryptedSharedPreferences. You can add multiple providers and configure a fallback chain in Settings โ Model Routing. When the primary provider rate-limits or errors, the agent walks the chain automatically. Optional integrations (Composio, Tavily, Brave Search, RAGFlow) can also be added from Settings.
The default fallback chain is: Groq (llama-3.3-70b-versatile) โ OpenRouter (claude-3.5-sonnet) โ Gemini (gemini-2.0-flash).
Architecture
The agent loop (ReActAgent) emits an AgentEvent flow consumed by the UI. Tool calls are routed through ToolRegistry, which dispatches to the appropriate manager. Provider calls go through AiApiManager, which exposes both chat() and chatWithFallback().
Compose UI โโโ AgentEvent flow โโโ ReActAgent
โ โ
โ user prompt โ chatWithFallback()
โผ โผ
ToolRegistry โโโ tool calls โโโ AiApiManager
โ
โโโ MemoryManager ยท SandboxManager ยท CronManager ยท AlarmManager
โโโ HeadlessBrowser ยท BrowserSessionManager
โโโ PluginManager ยท DelegationManager ยท McpClient
โโโ AndroidController ยท SnapshotManager ยท ChannelManager
โโโ GitRunner ยท DownloadManager ยท AgentNotificationBuilder
Five main tabs: Chat, Workspace, Browser, Hub, Settings. Companion mode is a separate screen accessible from Hub.
Working Memory
The current conversation context passed to the model on each turn. Managed automatically. Long conversations are summarised rather than truncated so the model always has a coherent picture without blowing the context window.
Daily Memory
A rolling log of events and findings from the current day. Injected into the system prompt at session start so the agent knows what it already did today. Cleared at end of day; important entries are promoted to long-term memory first. Configurable max entries (default: 1000) and compression threshold (default: 800).
Tools: memory_store, memory_recall, memory_summary.
Long-term Memory
A semantic embedding store backed by LongtermMemory and SemanticFactIndex. Entries are embedded and stored; retrieval is by cosine similarity. Persists across days and app restarts. Default max: 10,000 entries, retention: 90 days. Embeddings use text-embedding-3-small via OpenAI by default (configurable).
The system prompt explicitly requires:
- Aggressive writes โ after any meaningful result (research, calculations, user preferences) call
memory_store. - Aggressive reads โ before any research task call
semantic_recall_factsto avoid recomputing known information.
Tools: memory_store, semantic_recall_facts, memory_store_image, memory_summary.
Skills
Completed Python scripts can be saved as named, reusable skills via memory_store_skill. The agent can retrieve and replay them without rewriting the code.
Tools: memory_store_skill, memory_get_skill, memory_list_skills.
Python Runtime
Python 3.11 via Chaquopy. Pre-installed packages:
- numpy 1.26.2, pillow 11.0.0
- requests, beautifulsoup4, lxml
- pandas, openpyxl, xlrd, xlwt
- pyyaml, python-dateutil, psutil
Scripts run with a configurable timeout (default: 30 s). stdout and stderr are captured and returned to the agent. Completed scripts can be saved as skills. An optional remote Python worker URL can be configured for heavy scripts (torch, tensorflow, etc.) that should run off-device.
Tool: python_run. Remote variant: python_run_remote.
multiprocessing.fork() is not supported on Android โ use threading instead.
Shell Executor
Runs shell commands in a sandboxed environment with a limited PATH and no access to system directories outside the workspace. Useful for grep, find, file manipulation, and calling command-line tools available on the device.
Tool: shell_exec (default timeout: 30 s).
Sandbox & Security
All code execution goes through SandboxManager and SecurityPolicy:
- Max file size: 10 MB. Max workspace size: 500 MB.
- Blocked paths:
/etc,/sys,/proc,/dev. - AST-based import filter โ blocks disallowed Python modules before execution.
- Per-tool permission checks via
PermissionManagerbefore every dispatch. - Tool audit log โ every call is recorded with timestamp, args, result, and source (agent vs user).
- Destructive tools (
file_delete,shell_exec,git_push,config_write, etc.) require confirmation by default. - Settings โ Advanced Overrides: add extra blocked hosts, blocked file extensions, blocked config paths. Flip Lock agent out to freeze all
permissions.*keys against agent modification.
Headless Browser
Agent-controlled browser backed by HeadlessBrowser. Shares a cookie jar with the on-screen browser tab.
browser_set_viewport accepts presets: desktop, laptop, tablet, mobile, or custom width/height/user-agent. browser_screenshot_region accepts a CSS selector or x/y/width/height and saves a PNG to the workspace. file_upload_to_browser opens the on-screen browser's file chooser and picks from the workspace.
On-screen Browser
A visible browser tab (Browser screen) for interactive use. Shares cookies with the headless browser โ log in manually and the agent can then access cookie-gated pages. History and bookmarks are stored locally under workspace/.history and workspace/.cookies.
Tools: browser_history_list, browser_history_clear, browser_session_new.
Downloads
Two download tools, both stream directly into workspace/downloads/, sniff the MIME type, and return SHA-256 + byte count:
file_downloadโ open web, no cookies (timeout: 120 s).browser_downloadโ cookie-gated pages, uses the shared browser cookie jar (timeout: 120 s).
File Manager
Sandboxed file area with enforced quotas (max 500 MB total, 10 MB per file):
The Workspace screen provides a full file manager UI with breadcrumb navigation, sort, search, multi-select, and a file viewer/editor. Upload files from the device via the SAF picker. Pick files from the workspace into the on-screen browser.
Snapshots
Time-travel your workspace: take a snapshot, browse it, diff against current state, restore. Snapshots are stored under workspace/.snapshots.
system_backup_export creates a full ZIP backup in workspace/exports/. system_backup_import restores from a backup ZIP.
Cron Jobs
Backed by WorkManager. Survive reboots. Max 50 concurrent jobs, max 3 running simultaneously.
Schedule with plain-English text such as "every 30 m", "every 2 hours", "every hour", "every day", or "daily at 09:00". Minimum interval: 5 minutes. Each job has a task_type: PROMPT (run a prompt through the agent), PYTHON (run a script), or TOOL (call a tool). Jobs can specify a model override.
Alarms
Exact-time alarms backed by AlarmManager. Survive reboots. Every fire is recorded to workspace/alarms/sessions.json (200-event ring buffer), visible under Alarms โ Sessions.
Set with alarm_set { label, in_seconds | at_millis, action, payload, repeat_ms? } where action is one of:
NOTIFYโ post a notificationRUN_TOOLโ execute a tool callRUN_PYTHONโ run a Python scriptPROMPT_AGENTโ run a prompt through the full agent loop including tools and the fallback chain
Plugins
Python packages (.fp or .zip) that add new tools to the agent's tool surface. Plugins survive app upgrades via the plugin exporter.
- Install from file: drop a
.fpor.ziponto the Plugins screen. - Generate mid-loop: agent calls
plugin_create { id, name, description, tool_name, tool_description, python_code }. New tool is callable on the next iteration. - Execute:
plugin_execute { plugin_id, tool_name, args }.
MCP Client
Connects to Model Context Protocol servers and imports their tools and resources into the agent's tool surface. Configure in Settings โ Tools โ MCP. Tools appear prefixed with [mcp:server_name].
Sub-agents
Spawn focused sub-agents via DelegationManager. Each sub-agent runs the full agent loop with its own context. Max 3 concurrent sub-agents, max depth 1 (no recursive delegation by default). Sub-agents use the global fallback chain.
plan_and_execute_dag takes a complex goal, generates a JSON DAG of sub-tasks, and executes them. message_bus_* tools let agents communicate via named topics.
Channels (Telegram)
The agent can send and receive messages via Telegram through the Channels system. Each channel has its own session and optional model overrides.
Device Info & Control
Read device state and perform basic control actions via AndroidController.
android_set_volume and android_launch_app require confirmation by default (configurable in Settings โ Advanced).
Contacts, SMS, Calendar
Read and write contacts, send/read SMS, and manage calendar events. These tools require the corresponding Android runtime permissions.
Media & Clipboard
Control media playback and read/write the clipboard.
Wi-Fi & Bluetooth
Read Wi-Fi state, request scans, and interact with Bluetooth devices.
ACCESS_FINE_LOCATION (Android requirement to read SSID). Bluetooth tools need BLUETOOTH_CONNECT / BLUETOOTH_SCAN on API 31+.
Companion Mode
A separate, warmer conversation mode with its own persona, episodic memory, and safety infrastructure. Accessible from Hub โ Companion.
Features
- Persona โ configurable name and personality via
PersonaManager. - Episodic memory โ
EpisodicMemoryStorerecords conversation summaries with timestamps and topics. - Proactive check-ins โ
CheckInSchedulercan send morning check-ins and follow-ups (opt-in, configurable quiet hours). - Crisis-aware responses โ
EmotionalContextdetects distress signals and surfaces region-aware crisis lines. Covered regions: US (988), CA, GB (116 123 Samaritans), IE, AU, NZ, ZA, IN, DE, FR, plus a global fallback (findahelpline.com) and a custom slot. - Dependency monitoring โ
DependencyMonitortracks session counts and wall-clock duration per day. Fires a gentle nudge notification at most once per 30 days if usage exceeds configurable thresholds (default: 3 h/day for 14 consecutive days, or 50 sessions/week). - Safety filter โ
SafetyFilterpost-hoc scans every reply for romantic/sexual content and dependency-reinforcing language. Blocked replies are replaced with warm, safe alternatives. - Real-world nudges โ opt-in weekly prompt to engage with the real world.
- Daily token budget โ default 50,000 tokens/day, resets at midnight.
- Memory transparency โ Companion Memory screen lists every stored episode and fact with individual delete buttons and a two-step "Forget Everything" wipe.
- Relationship state โ
RelationshipStatetracks interaction history to personalise responses over time.
Git Integration
First-class git tools backed by JGit 5.13.3. PATs are stored in the encrypted memory store. HTTPS only (no SSH).
git_push, git_pull, and git_clone have a 60โ120 s timeout and require confirmation by default.
HTTP & Search
http_fetch and curl_exec make direct HTTP requests (timeout: 30 s). ddg_search queries DuckDuckGo (timeout: 20 s). composio_call routes to a configured Composio endpoint.
Notifications
The agent can post notifications to the device notification tray and attach action buttons that trigger tool calls when tapped.
Notification channels: agent notifications, wellbeing (Companion dependency nudges), cron/alarm alerts.
Vision
The agent can analyse images via VisionTool using a configured vision-capable model (e.g. GPT-4o, Gemini). Vision routing is configurable separately from the main model in Settings โ Model Routing.
Projects & Local Server
Projects are named workspaces with their own Python runner and health monitor. A built-in HTTP server (ForgeHttpServer) can serve project files over the local network.
External API
Other Android apps can call Forge OS as an on-device LLM service via a permission-gated AIDL interface. The interface is defined in IForgeOsService.aidl under app/src/main/aidl/com/forge/os/api/. External callers are registered in ExternalCallerRegistry and subject to per-caller rate limits (default: 30 calls/min, 50,000 tokens/day).
The external API is disabled by default. Enable in Settings โ Advanced โ External API.
Cost Meter
Live token and USD spend tracking per call, per session, and lifetime via CostMeter and ApiCallLog. Visible in the Hub screen (Cost tab).
Optional Compact Mode: limits context to 8 messages and 512 tokens per request, routes to a cheaper model (default: Groq llama-3.3-70b-versatile). Enable in Settings โ Model Routing โ Compact Mode.
Optional Daily budget: set a USD ceiling in Settings โ Model Routing โ Cost Budget. When exceeded, the agent switches to the configured eco model.
Permissions & Security
Per-tool permissions
Every tool call is checked by PermissionManager before dispatch. Permissions are configured per-tool in Settings โ Tools. The audit log records every call.
Named secrets
Store API keys and tokens as named secrets via NamedSecretRegistry. The agent can list secret names and request their use, but never sees raw values.
Agent control plane
The control plane (AgentControlPlane) lets the agent inspect and modify its own permissions within the bounds set by the user. The user can lock the agent out of all permission changes via Settings โ Advanced โ Lock agent out.
Config System
All settings are stored in ForgeConfig (serialised JSON). The agent can read and write config values within the bounds of the permission policy.
Key config sections: agentIdentity, behaviorRules, toolRegistry, modelRouting, sandboxLimits, cronSettings, pluginSettings, memorySettings, delegationRules, friendMode, permissions, costBudget.
The agent's name, personality, default greeting, language, and timezone are all configurable under agentIdentity. Max iterations per turn defaults to 15.
Diagnostics
doctor_check runs a self-diagnostic and doctor_fix attempts automatic remediation. request_user_input pauses the agent loop and waits for a human response mid-task.