Update for modern Android: fix carrier config override + build tooling - #35
Open
Dudeman456 wants to merge 2 commits into
Open
Dudeman456 wants to merge 2 commits into
Dudeman456 wants to merge 2 commits into
Conversation
added 2 commits
October 2, 2026 19:49
The carrier config override was broken on Android 14+ due to: 1. Direct ICarrierConfigLoader.overrideConfig() call without shell permission delegation 2. Hidden SubscriptionManager.getSubId() / getNetworkOperatorName(subId) APIs 3. Outdated build tooling (AGP 7.4.1, Kotlin 1.8.0, compileSdk 33) Changes based on the proven approach in eigenlux-ai/roamer: TargetFragment.kt: - Use CarrierConfigManager.overrideConfig() via reflection instead of direct ICarrierConfigLoader call - Add withShellPermissionIdentity() via Shizuku-delegated ActivityManager for proper permission escalation - Add SecurityException fallback (retry with override=false for OEM builds that reject true) - Call notifyConfigChangedForSubId() after override to force system config reload - Use public activeSubscriptionInfoList instead of hidden getSubId() - Use public createForSubscriptionId() instead of hidden getNetworkOperatorName(subId) - Improve reset: restore real ISO before clearing overrides - Better error handling with user-visible toasts MainActivity.kt: - Add hidden API exemption for com.android.internal.telephony package Build system: - AGP 7.4.1 -> 8.7.3 - Kotlin 1.8.0 -> 2.1.0 - Gradle 7.5 -> 8.12 - compileSdk/targetSdk 33 -> 35 - Java 8 -> 11 - Update AndroidX deps (core-ktx 1.13.1, appcompat 1.7.0, material 1.12.0, navigation 2.8.4) - Shizuku 13.1.0 -> 13.1.5
…hell permission delegation Root cause analysis (tested on Samsung Galaxy S24 Ultra, Android 17/API 37): 1. Manifest had ZERO <uses-permission> declarations → app saw 0 SIM subscriptions. Added READ_PHONE_STATE, READ_BASIC_PHONE_STATE, READ_PHONE_NUMBERS + runtime request. 2. ICarrierConfigLoader.overrideConfig() via ShizukuBinderWrapper fails: 'overrideConfig cannot be invoked by shell' (Android 17 rejects shell UID). 3. CarrierConfigManager.overrideConfig() + startDelegateShellPermissionIdentity from a regular Activity fails: 'requires MODIFY_PHONE_STATE'. Working approach (mirrors eigenlux-ai/roamer): - Declare <instrumentation> as direct child of <manifest> (NOT inside <application>). - Launch PrivilegedOverrideInstrumentation via IActivityManager.startInstrumentation through ShizukuBinderWrapper with INSTR_FLAG_NO_RESTART + UiAutomationConnection. The UiAutomationConnection instance is REQUIRED — passing null causes 'Shell can delegate its permissions only to an instrumentation started from the shell'. - Inside the Instrumentation, call startDelegateShellPermissionIdentity via Shizuku, then CarrierConfigManager.overrideConfig() (manager-level API, not the binder-level ICarrierConfigLoader). persistent=true is rejected on Samsung; fall back to false. - After override, notifyConfigChangedForSubId() triggers the UI update. New files: - PrivilegedOverrideInstrumentation.kt: Instrumentation running override logic - InstrumentationTrigger.kt: launches the Instrumentation via Shizuku Also: gradlew exec bit fix for Gradle builds.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
CarrierVanityName does not work on modern Android (14-17). Tested on Samsung Galaxy S26 Ultra (SM-S948U1), Android 17/API 37.
Root Causes (found via live ADB debugging)
1. Missing permissions → 0 SIM subscriptions
AndroidManifest.xmldeclared zero<uses-permission>entries. The app couldn't see any SIM subscriptions (found 0 subscriptionsin logcat).Fix: Added
READ_PHONE_STATE,READ_BASIC_PHONE_STATE,READ_PHONE_NUMBERS+ runtime permission request.2. Direct
ICarrierConfigLoader.overrideConfig()blockedCalling
overrideConfig()viaShizukuBinderWrapperon thecarrier_configbinder fails on Android 17:The shell UID (2000) is explicitly rejected at the binder level.
3.
startDelegateShellPermissionIdentityfrom Activity context blockedCalling
CarrierConfigManager.overrideConfig()from a regular Activity withstartDelegateShellPermissionIdentityfails:Working Solution (mirrors eigenlux-ai/roamer)
Use an Instrumentation launched via Shizuku to run in a shell-identity context:
Declare
<instrumentation>as direct child of<manifest>(NOT inside<application>— otherwise "Unable to find instrumentation info")Launch via
IActivityManager.startInstrumentation()throughShizukuBinderWrapperwithINSTR_FLAG_NO_RESTARTand a realUiAutomationConnectioninstance (passingnullcauses "Shell can delegate its permissions only to an instrumentation started from the shell")Inside the Instrumentation, call
startDelegateShellPermissionIdentityvia Shizuku, thenCarrierConfigManager.overrideConfig()(the manager-level API, NOT the binder-levelICarrierConfigLoader). Usepersistent=false—trueis rejected on Samsung.After override, call
notifyConfigChangedForSubId()to trigger the UI update.New Files
PrivilegedOverrideInstrumentation.kt— Instrumentation that performs the override using shell permission delegationInstrumentationTrigger.kt— Launches the Instrumentation via Shizuku'sIActivityManagerBuild Tooling (from previous commit)
activeSubscriptionInfoList+createForSubscriptionId()gradlewexec bit fixTesting
Verified working on Samsung Galaxy S26 Ultra (SM-S948U1), Android 17/API 37, build CP2A.260605.016.S948U1UEU4BZID with Shizuku 13.5.4.