# Code review: IMPLEMENTATION-PLAN.md revision 30 (focus: section 19)

File reviewed: `/Users/rock3r/src/remozio/IMPLEMENTATION-PLAN.md` (1,699 lines; line numbers verified against the file).

## Confirmed design defects and inconsistencies

### 1. Unauthenticated loopback ADB listener is exposed to in-scope attackers — Medium
**Line 1678** (`The Mac command ... binds a temporary listener on 127.0.0.1 for the local ADB client`) combined with **line 1690** (`The Mac keeps its ADB pairing key in ADB's existing host store`).

Rationale: Section 2's threat boundary (**line 59**) explicitly includes "a malicious unprivileged requesting process," and section 3 (**line 120**) warns the command frontend "may be invoked by an untrusted same-user process: do not mistake its signature for user consent." Section 19 applies no analogous rule to the bridge. The `~/.android` ADB host key is same-user-readable, and a loopback listener accepts connections from any local process (including other GUI users). During any active session, an in-scope same-user process can connect to the listener and drive full ADB (package install, shell, device data) on the phone — remotely, since the bridge exists precisely to extend ADB off-LAN — with no enrolled-phone signature, no biometric, no phone tap, and no audit event. The plan authenticates the bridge *command* via peer check (line 1678) but never states who may connect to the *listener* or what protects it; "one active connection" (line 1678) makes a race-to-connect attack practical. Section 19 also never adds this boundary to the threat model in section 2.

Minimal correction: in section 19, (a) state the listener's protection model explicitly (e.g., accept exactly one connection, verify the connecting peer's audit token/UID matches the authenticated command's session, or bind a filesystem-protected socket instead of a TCP port); (b) document in section 2 that ADB host-key custody is same-user and that enabling wireless debugging plus the bridge extends that exposure off-LAN; (c) note that deferring per-session phone confirmation (line 1686) removes the only phone-side mitigation, and record that deferral as a pending decision per section 1 (line 27) — it is currently absent from the revision header's open-decision list (line 3).

### 2. Bridge endpoint conflicts with section 16's exposure and provisioning constraints — Medium
**Line 1676** (`a dedicated unprivileged Mac bridge endpoint ... reached through the section 16 internet transport candidate, Cloudflare Tunnel plus Access`) vs. **line 1156** (`Expose only the Remozio protocol endpoint, never the privileged helper, a general shell, or other local services`) and **line 1190** (`The controller enforces the exact configured account, tunnel, application, hostname, and local Remozio endpoint`).

Rationale: A proxied ADB byte stream is functionally remote shell capability; section 16 permits exactly one exposed endpoint, and the setup controller's typed operations cover a single hostname/application with no operation to create or verify a second ingress/Access policy. Section 19 contains no provisioning, rotation, or uninstall story for its endpoint at all, so as written the bridge cannot be deployed without silently amending section 16.

Minimal correction: amend line 1156 to name the optional bridge endpoint as a permitted second exposure when the feature is enabled; extend the controller's typed operations (line 1190) to cover bridge ingress/Access policy lifecycle; add one sentence in section 19 assigning bridge provisioning and teardown to the section 16 controller under the same administrator-authorized path.

### 3. "The initial product supports one Android phone and one Mac" contradicts multi-phone enrollment — Medium
**Line 1672** vs. **line 219** (`Permit multiple enrolled phones for one Mac/account tuple`), **line 221** (`deliver each request to every currently authorized phone`), and line 1059 (`Support token rotation, multiple phones`).

Rationale: As written, "the initial product" is a product-wide claim that directly contradicts section 5. If the intent is to scope the limit to bridge sessions, the sentence does not say so, and section 1 (line 21) integrates the bridge into the same product.

Minimal correction: reword line 1672 to scope the limitation, e.g. "The deployment bridge initially supports sessions to one enrolled phone per Mac; approval enrollment remains multi-phone per section 5."

### 4. "Keep the existing Tailscale path as a development fallback" references nonexistent infrastructure and contradicts the no-VPN posture — Medium
**Line 1694** vs. **line 89** (`No VPN or WARP client is required`), section 16 (`Neither requires a VPN`, line 1123), and the header (`This is a standalone project`, line 5; `no security settings, apps, or privileged components are installed`).

Rationale: Nothing named Tailscale exists anywhere else in this plan or project; "the existing Tailscale path" is undefined. Tailscale is also a VPN, and introducing it even as a development fallback contradicts the stated deployment posture without a recorded pending decision (section 1, lines 25–27, requires consultation for changes that add manual steps or dependencies).

Minimal correction: delete the sentence, or replace with "a development-only VPN fallback (e.g., Tailscale) is a pending user decision, not part of the shipped design" and record it accordingly.

### 5. Bridge components are absent from the update/floor and protocol-evolution machinery — Low
**Line 1434** (`Ship a signed release manifest with app, helper, GUI adapter, transport, and administrative setup-controller builds`) and the section 18 declaration table (**lines 1560–1565**) vs. **line 1672** (`against the same bridge protocol`) and line 1676.

Rationale: The Mac bridge endpoint and bridge command are in the component list (line 100) but not in the release manifest enumeration, so the floor-enforcement, protected-placement, and quiescent-activation rules of section 17 do not clearly apply to them. Unlike cloudflared (explicitly covered at lines 1143–1147), section 19 never states which account runs the bridge endpoint or that section 3/16 custody rules apply to its binaries, config, and update path. The bridge protocol also has no row in section 18's compatibility table despite being named as a cross-platform contract.

Minimal correction: add the bridge endpoint and command to the line 1434 manifest; add a section 18 row ("Bridge endpoint/protocol: bridge stream versions; no approval authority"); state in section 19 that the endpoint runs under a dedicated unprivileged account with section 3 placement and section 16 credential-custody rules.

### 6. Bridge sessions are not in the audit event set — Low
**Line 754** (`Record request creation ... pairing, revocation, recovery, update scheduling, activation, and update-caused interruption events`) vs. **line 1690** (`The bridge's local status identifies the paired Mac and last session`).

Rationale: An ADB session grants remote shell on the phone — more sensitive than several audited event classes — yet session start/stop/stop-reason and peer identity are only transient local status. Metadata-only session events are compatible with line 1682's exclusion of APK/ADB payloads from logs and audit.

Minimal correction: add bridge session lifecycle (metadata only) to line 754's event list and a corresponding audit acceptance case.

### 7. Byte-cap rationale misattributes the threat — Low
**Line 1682** (`a per-session byte cap ... so the relay cannot accumulate unbounded data`) vs. **line 1087** (`A tunnel is a live proxy, not an offline mailbox`).

Rationale: By the plan's own transport model, Cloudflare Tunnel streams and does not accumulate data; the cap's real purpose is bounding endpoint buffering and session resource consumption. The stated rationale is internally inconsistent with section 16.

Minimal correction: reword to "so neither endpoint nor relay buffers unbounded session data."

## Unproven feasibility — properly hedged, not defects

These are open platform questions that section 19 correctly defers with evidence requirements; they should not be counted as design defects:

- **NSD discovery vs. Android 17 local-network permission** (lines 1680, 1694): discovery of `_adb-tls-connect._tcp` is a LAN operation likely gated by the new permission model even though the subsequent connection is loopback. The plan flags the real-device test, scopes the Pixel 11 Pro observation correctly (loopback reachability only, not discovery/permission), and provides a manual-port fallback. Appropriately hedged.
- **`connectedDevice` foreground-service type** (line 1686): conditional on platform/distribution requirements. Appropriately hedged.
- **ADB Wi-Fi 2.0 re-enable behavior** (line 1688): explicit "test the exact behavior." Appropriately hedged.
- **Access service-token authentication over a WebSocket upgrade** (line 1694): extends section 16's existing background-Access feasibility gate (lines 1168–1176) rather than assuming it. Appropriately hedged.
- **Push waking the app to reopen Ready mode** (line 1688): explicitly denied as a replacement for the live socket and as a bypass of background-start limits. Correctly stated.

## Verified consistent (no findings)

- Section 1's carve-out that the bridge is not an approval request type (line 21), the authority separation in section 3 (line 100) and section 19 (line 1670: no approval/decision key/push token/transport credential grants ADB access), and stage 8 sequencing (line 647) are mutually consistent.
- ADB TLS is never terminated at the proxy (line 1682), keeping wireless-debugging pairing as the device-control authority — consistent with section 16's end-to-end encryption posture (line 1166).
- Revocation closes active sessions (lines 1678, 1690) and is enforceable at the Mac endpoint since the phone connects outbound; works even for an offline phone.
- Transport separation to protect approval latency (line 1670) plus the measurable acceptance criterion "bridge load does not delay an approval" (line 1696) are consistent.
- LAN path requires endpoint authentication (line 1676), consistent with "LAN discovery is not identity" (line 1129).

**Summary:** No feasibility claims in section 19 are overstated. The substantive work is in the security boundary around the Mac-side loopback listener (finding 1), the unamended section 16 exposure/provisioning rules (finding 2), and three internal-consistency defects (findings 3–5) that need text-level corrections before section 19 can be considered reviewed.
