131 lines
5.2 KiB
Markdown
131 lines
5.2 KiB
Markdown
# 009 — Sideload system package updates (FR-019)
|
||
|
||
Owner cadence: refresh bundled **system / privileged** packages about every
|
||
**2–3 months** without a full ROM reflash. **No** AXP OTA / external repos.
|
||
|
||
Status: **documented** — commands and signing gates below define the intended
|
||
refresh path. The owner has also verified full-ROM upgrades over existing
|
||
userdata without a wipe. A real individual-APK refresh drill can wait for the
|
||
final ROM candidate; packaging of the shipping image MUST preserve update
|
||
eligibility.
|
||
|
||
**Full ROM updates** (new LOS base + rebacon) are a different path: recovery
|
||
sideload of the project zip. See [`009-upstream-rebase-ota.md`](009-upstream-rebase-ota.md).
|
||
|
||
## In scope
|
||
|
||
| Component | Intended update path | Signing constraint |
|
||
|-----------|----------------------|--------------------|
|
||
| microG GmsCore / companions | `adb install -r` / recovery sideload of upstream APK | **PRESIGNED** / same signer as shipped |
|
||
| Magisk | Magisk app self-update and/or documented boot re-patch | Manager + boot image must stay matched |
|
||
| Project Phonesky | Sideload project-signed APK | **Same project key** across releases |
|
||
| Other bundled system apps | Sideload matching-signer APK (or recovery zip if priv-app needs it) | Same identity as image |
|
||
|
||
## Out of scope
|
||
|
||
- Network OTA / AXP update servers
|
||
- Full `bacon` + clean flash for routine APK bumps (still OK for kernel /
|
||
framework / Magisk boot changes when required)
|
||
|
||
## Checklist before claiming FR-019 done
|
||
|
||
- [ ] Each row above has a concrete command/runbook step
|
||
- [ ] `pm install` / PackageManager does not reject for signature mismatch
|
||
- [ ] Privileged permissions still grant after update (or re-flash privapp XML noted)
|
||
- [ ] Magisk version after update matches kernel/boot expectation
|
||
- [ ] Record new versions in `docs/009-version-pins.md`
|
||
|
||
## Preparation and safety
|
||
|
||
1. Keep the last known-good full ROM zip and its SHA-256. APK refreshes do not
|
||
replace a boot/kernel rollback path.
|
||
2. Download the new APK from the upstream/project source into a host-only
|
||
staging directory. Never put it in Git or paste its bytes into evidence.
|
||
3. Verify the APK before connecting the phone:
|
||
|
||
```bash
|
||
apksigner verify --verbose --print-certs NEW.apk
|
||
sha256sum NEW.apk
|
||
```
|
||
|
||
4. Compare the signer with the installed package. For a system app, first
|
||
record `adb shell pm path PACKAGE` and the installed version. Do not use
|
||
`-d` for routine refreshes and do not accept a signer mismatch.
|
||
|
||
## microG / GSF Proxy
|
||
|
||
For a compatible same-signer update on a test device:
|
||
|
||
```bash
|
||
adb install -r GmsCore.apk
|
||
adb install -r GsfProxy.apk
|
||
adb shell pm path com.google.android.gms
|
||
adb shell dumpsys package com.google.android.gms | grep -E 'versionName=|versionCode='
|
||
adb shell dumpsys package com.google.android.gsf | grep -E 'versionName=|versionCode='
|
||
```
|
||
|
||
Then run microG Self-Check, open Phonesky, and verify one ordinary app update.
|
||
If a package is privileged or its signer/permissions change, stop and rebuild
|
||
the image or provide a recovery package with the matching privapp XML; do not
|
||
paper over the rejection with a weaker permission policy.
|
||
|
||
## Project Phonesky
|
||
|
||
Phonesky must remain the project-signed artifact and must retain the same
|
||
package identity and signer as the image:
|
||
|
||
```bash
|
||
adb install -r Phonesky.apk
|
||
adb shell pm path com.android.vending
|
||
adb shell dumpsys package com.android.vending | grep -E 'versionName=|versionCode='
|
||
adb shell monkey -p com.android.vending 1
|
||
```
|
||
|
||
Verify an ordinary install/update through Phonesky. A signature mismatch,
|
||
privileged-permission loss, or broken microG path is a failed refresh; restore
|
||
the previous APK or the known-good ROM rather than accepting the update.
|
||
|
||
## Other bundled system apps
|
||
|
||
Aurora, Droidify, Fossify Gallery, Jelly and OpenEUICC may be refreshed only
|
||
with an APK matching the shipped package identity and signing policy:
|
||
|
||
```bash
|
||
adb install -r APP.apk
|
||
adb shell pm path PACKAGE
|
||
adb shell dumpsys package PACKAGE | grep -E 'versionName=|versionCode='
|
||
```
|
||
|
||
For an app whose update must retain system/privileged permissions, verify its
|
||
normal function and the relevant permissions after install. If PackageManager
|
||
places the update under `/data/app/`, that is expected only when the signer and
|
||
permission model remain valid; record the path change and any required XML
|
||
handling in the version pin record.
|
||
|
||
## Magisk
|
||
|
||
Magisk manager APK updates and boot-preroot updates are separate:
|
||
|
||
- Manager-only update: use the manager's normal update path, then verify
|
||
`magisk -v`, Zygisk/DenyList behavior, and the test package before banking
|
||
experiments.
|
||
- Boot/runtime update: patch and test a new boot image with the matching
|
||
Magisk version. This is not an APK-only refresh and must use the full build
|
||
and LAB-only flash procedure; never mix a new Magisk manager with an older
|
||
preroot boot image casually.
|
||
|
||
## Post-update evidence
|
||
|
||
Record the following under the relevant host artifact or release note:
|
||
|
||
```bash
|
||
adb shell getprop ro.lineage.version
|
||
adb shell pm path PACKAGE
|
||
adb shell dumpsys package PACKAGE
|
||
adb shell logcat -d -t 500 | grep -E 'PackageManager|avc: denied|FATAL EXCEPTION'
|
||
```
|
||
|
||
Reboot once after privileged/system-package changes and repeat the package
|
||
path, permissions, microG Self-Check, Phonesky install, and WebView checks.
|
||
Record versions and SHA-256 values in `docs/009-version-pins.md`.
|