├── .gitattributes ├── .github ├── ISSUE_TEMPLATE │ ├── bug_report.yml │ └── config.yml └── workflows │ └── app.yml ├── .gitignore ├── .gitmodules ├── LICENSE ├── README.md ├── build.gradle ├── common ├── .gitignore ├── build.gradle └── src │ └── main │ ├── AndroidManifest.xml │ └── java │ └── moe │ └── shizuku │ └── common │ └── util │ ├── BuildUtils.java │ └── OsUtils.java ├── gradle.properties ├── gradle └── wrapper │ ├── gradle-wrapper.jar │ └── gradle-wrapper.properties ├── gradlew ├── gradlew.bat ├── manager ├── .gitignore ├── aapt2-resources.cfg ├── build.gradle ├── proguard-rules.pro └── src │ └── main │ ├── .gitignore │ ├── AndroidManifest.xml │ ├── assets │ └── rish │ ├── java │ └── moe │ │ └── shizuku │ │ └── manager │ │ ├── AppConstants.java │ │ ├── Helps.java │ │ ├── MainActivity.java │ │ ├── Manifest.java │ │ ├── ShizukuApplication.kt │ │ ├── ShizukuManagerProvider.kt │ │ ├── ShizukuSettings.java │ │ ├── adb │ │ ├── AdbClient.kt │ │ ├── AdbException.kt │ │ ├── AdbKey.kt │ │ ├── AdbMdns.kt │ │ ├── AdbMessage.kt │ │ ├── AdbPairingClient.kt │ │ ├── AdbPairingService.kt │ │ ├── AdbPairingTutorialActivity.kt │ │ └── AdbProtocol.kt │ │ ├── app │ │ ├── AppActivity.kt │ │ ├── AppBarActivity.kt │ │ └── ThemeHelper.java │ │ ├── authorization │ │ ├── AuthorizationManager.kt │ │ └── RequestPermissionActivity.kt │ │ ├── home │ │ ├── AdbDialogFragment.kt │ │ ├── AdbPairDialogFragment.kt │ │ ├── AdbPermissionLimitedViewHolder.kt │ │ ├── HomeActivity.kt │ │ ├── HomeAdapter.kt │ │ ├── HomeViewModel.kt │ │ ├── LearnMoreViewHolder.kt │ │ ├── ManageAppsViewHolder.kt │ │ ├── ServerStatusViewHolder.kt │ │ ├── StartAdbViewHolder.kt │ │ ├── StartRootViewHolder.kt │ │ ├── StartWirelessAdbViewHolder.kt │ │ ├── TerminalViewHolder.kt │ │ └── WadbNotEnabledDialogFragment.kt │ │ ├── ktx │ │ ├── Context.kt │ │ ├── Log.kt │ │ ├── PackageManager.kt │ │ ├── RecyclerView.kt │ │ └── String.kt │ │ ├── legacy │ │ ├── LegacyIsNotSupportedActivity.kt │ │ └── ShellRequestHandlerActivity.kt │ │ ├── management │ │ ├── AppViewHolder.kt │ │ ├── ApplicationManagementActivity.kt │ │ ├── AppsAdapter.java │ │ ├── AppsViewModel.kt │ │ └── EmptyViewHolder.kt │ │ ├── model │ │ └── ServiceStatus.kt │ │ ├── receiver │ │ ├── BootCompleteReceiver.kt │ │ └── ShizukuReceiver.kt │ │ ├── settings │ │ ├── IntegerSimpleMenuPreference.java │ │ ├── SettingsActivity.kt │ │ └── SettingsFragment.kt │ │ ├── shell │ │ ├── Shell.java │ │ ├── ShellBinderRequestHandler.kt │ │ └── ShellTutorialActivity.kt │ │ ├── starter │ │ ├── Starter.kt │ │ └── StarterActivity.kt │ │ ├── utils │ │ ├── AppIconCache.kt │ │ ├── CustomTabsHelper.java │ │ ├── EmptySharedPreferencesImpl.java │ │ ├── EnvironmentUtils.kt │ │ ├── Logger.java │ │ ├── MultiLocaleEntity.java │ │ ├── ShizukuSystemApis.kt │ │ ├── UserHandleCompat.java │ │ └── UserInfoCompat.java │ │ └── widget │ │ ├── CheckedImageView.java │ │ └── VerticalPaddingDecoration.java │ ├── jni │ ├── CMakeLists.txt │ ├── adb_pairing.cpp │ ├── adb_pairing.h │ ├── android.cpp │ ├── android.h │ ├── cgroup.cpp │ ├── cgroup.h │ ├── helper.cpp │ ├── logging.h │ ├── misc.cpp │ ├── misc.h │ ├── selinux.cpp │ ├── selinux.h │ └── starter.cpp │ └── res │ ├── animator │ └── alpha_animator.xml │ ├── color-night │ ├── home_card_background_color.xml │ └── home_card_foreground_color.xml │ ├── color │ ├── grant_permissions_button_ripple_color_selector.xml │ ├── home_card_background_color.xml │ └── home_card_foreground_color.xml │ ├── drawable-v24 │ └── ic_default_app_icon_foreground.xml │ ├── drawable-v26 │ ├── ic_default_app_icon.xml │ └── ic_launcher.xml │ ├── drawable │ ├── card_btn_background.xml │ ├── grant_permissions_buttons_bottom.xml │ ├── grant_permissions_buttons_top.xml │ ├── home_card_foreground.xml │ ├── ic_action_about_24dp.xml │ ├── ic_action_settings_24dp.xml │ ├── ic_adb_24dp.xml │ ├── ic_baseline_link_24.xml │ ├── ic_close_24.xml │ ├── ic_code_24dp.xml │ ├── ic_default_app_icon_background.xml │ ├── ic_help_outline_24dp.xml │ ├── ic_launcher.xml │ ├── ic_learn_more_24dp.xml │ ├── ic_monochrome.xml │ ├── ic_numeric_1_circle_outline_24.xml │ ├── ic_numeric_2_circle_outline_24.xml │ ├── ic_numeric_3_circle_outline_24.xml │ ├── ic_outline_arrow_upward_24.xml │ ├── ic_outline_dark_mode_24.xml │ ├── ic_outline_info_24.xml │ ├── ic_outline_notifications_active_24.xml │ ├── ic_outline_open_in_new_24.xml │ ├── ic_outline_play_arrow_24.xml │ ├── ic_outline_translate_24.xml │ ├── ic_root_24dp.xml │ ├── ic_server_error_24dp.xml │ ├── ic_server_ok_24dp.xml │ ├── ic_server_restart.xml │ ├── ic_server_start_24dp.xml │ ├── ic_settings_outline_24dp.xml │ ├── ic_system_icon.xml │ ├── ic_terminal_24.xml │ ├── ic_wadb_24.xml │ ├── ic_warning_24.xml │ └── shape_circle_icon_background.xml │ ├── layout │ ├── about_dialog.xml │ ├── adb_dialog.xml │ ├── adb_pair_dialog.xml │ ├── adb_pairing_tutorial_activity.xml │ ├── app_list_empty.xml │ ├── app_list_item.xml │ ├── appbar.xml │ ├── appbar_activity.xml │ ├── appbar_fragment_activity.xml │ ├── apps_activity.xml │ ├── confirmation_dialog.xml │ ├── home_activity.xml │ ├── home_extra_step_required.xml │ ├── home_item_container.xml │ ├── home_learn_more.xml │ ├── home_manage_apps_item.xml │ ├── home_server_status.xml │ ├── home_start_adb.xml │ ├── home_start_root.xml │ ├── home_start_wireless_adb.xml │ ├── home_terminal.xml │ ├── preference_recyclerview.xml │ ├── shell_dialog.xml │ ├── starter_activity.xml │ └── terminal_tutorial_activity.xml │ ├── menu │ └── main.xml │ ├── mipmap-hdpi │ ├── ic_launcher.png │ ├── ic_launcher_background.png │ └── ic_launcher_foreground.png │ ├── mipmap-xhdpi │ ├── banner.png │ ├── ic_launcher.png │ ├── ic_launcher_background.png │ └── ic_launcher_foreground.png │ ├── mipmap-xxhdpi │ ├── ic_launcher.png │ ├── ic_launcher_background.png │ └── ic_launcher_foreground.png │ ├── mipmap-xxxhdpi │ ├── ic_launcher.png │ ├── ic_launcher_background.png │ └── ic_launcher_foreground.png │ ├── values-ang │ └── strings.xml │ ├── values-ar │ └── strings.xml │ ├── values-ars │ └── strings.xml │ ├── values-az │ └── strings.xml │ ├── values-b+es+419 │ └── strings.xml │ ├── values-bg │ └── strings.xml │ ├── values-bn │ └── strings.xml │ ├── values-ca │ └── strings.xml │ ├── values-ckb │ └── strings.xml │ ├── values-cs │ └── strings.xml │ ├── values-da │ └── strings.xml │ ├── values-de │ └── strings.xml │ ├── values-el │ └── strings.xml │ ├── values-enm │ └── strings.xml │ ├── values-eo │ └── strings.xml │ ├── values-es-rCL │ └── strings.xml │ ├── values-es │ └── strings.xml │ ├── values-et │ └── strings.xml │ ├── values-fa │ └── strings.xml │ ├── values-fi │ └── strings.xml │ ├── values-fil │ └── strings.xml │ ├── values-fr │ └── strings.xml │ ├── values-he │ └── strings.xml │ ├── values-hi │ └── strings.xml │ ├── values-hr │ └── strings.xml │ ├── values-hu │ └── strings.xml │ ├── values-hy │ └── strings.xml │ ├── values-id │ └── strings.xml │ ├── values-it │ └── strings.xml │ ├── values-ja │ └── strings.xml │ ├── values-ka │ └── strings.xml │ ├── values-kk │ └── strings.xml │ ├── values-km │ └── strings.xml │ ├── values-kn │ └── strings.xml │ ├── values-ko │ └── strings.xml │ ├── values-lb │ └── strings.xml │ ├── values-lv │ └── strings.xml │ ├── values-mk │ └── strings.xml │ ├── values-ml │ └── strings.xml │ ├── values-ms │ └── strings.xml │ ├── values-my │ └── strings.xml │ ├── values-night │ └── styles.xml │ ├── values-nl │ └── strings.xml │ ├── values-or │ └── strings.xml │ ├── values-pl │ └── strings.xml │ ├── values-pt-rBR │ └── strings.xml │ ├── values-pt │ └── strings.xml │ ├── values-ro │ └── strings.xml │ ├── values-ru │ └── strings.xml │ ├── values-sk │ └── strings.xml │ ├── values-sl │ └── strings.xml │ ├── values-sr │ └── strings.xml │ ├── values-sv │ └── strings.xml │ ├── values-sw600dp │ ├── bools.xml │ ├── dimens.xml │ └── values.xml │ ├── values-ta │ └── strings.xml │ ├── values-te │ └── strings.xml │ ├── values-th │ └── strings.xml │ ├── values-tr │ └── strings.xml │ ├── values-ug │ └── strings.xml │ ├── values-uk │ └── strings.xml │ ├── values-ur │ └── strings.xml │ ├── values-v21 │ └── themes_override.xml │ ├── values-v31 │ └── themes_overlay.xml │ ├── values-vi │ └── strings.xml │ ├── values-zh-rCN │ └── strings.xml │ ├── values-zh-rTW │ └── strings.xml │ ├── values │ ├── arrays.xml │ ├── attrs.xml │ ├── bools.xml │ ├── colors.xml │ ├── dimens.xml │ ├── strings.xml │ ├── strings_untranslatable.xml │ ├── styles.xml │ ├── themes.xml │ ├── themes_overlay.xml │ └── values.xml │ └── xml │ ├── backup_descriptor.xml │ ├── data_extraction_rules.xml │ └── settings.xml ├── server ├── .gitignore ├── build.gradle └── src │ └── main │ ├── AndroidManifest.xml │ └── java │ └── rikka │ └── shizuku │ └── server │ ├── ApkChangedObservers.kt │ ├── BinderSender.java │ ├── ServerConstants.java │ ├── ShizukuClientManager.java │ ├── ShizukuConfig.java │ ├── ShizukuConfigManager.java │ ├── ShizukuService.java │ ├── ShizukuUserServiceManager.java │ ├── api │ └── IContentProviderUtils.java │ └── ktx │ └── Handler.kt ├── settings.gradle ├── shell ├── .gitignore ├── build.gradle ├── proguard-rules.pro └── src │ └── main │ ├── AndroidManifest.xml │ └── java │ └── rikka │ └── shizuku │ └── shell │ └── ShizukuShellLoader.java ├── signing.gradle └── starter ├── .gitignore ├── build.gradle └── src └── main ├── AndroidManifest.xml └── java └── moe └── shizuku └── starter ├── ServiceStarter.java └── util └── IContentProviderCompat.java /.gitattributes: -------------------------------------------------------------------------------- 1 | * text=auto eol=lf 2 | 3 | *.bat text eol=crlf 4 | *.jar binary -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/bug_report.yml: -------------------------------------------------------------------------------- 1 | name: Bug report 2 | description: Report a bug of Shizuku 3 | 4 | body: 5 | - type: checkboxes 6 | id: requirements 7 | attributes: 8 | label: Requirements 9 | options: 10 | - label: Shizuku is downloaded from official channels (GitHub release or Google Play) 11 | - label: Shizuku is not running in a virtual environment or broken ROM (GrapheneOS) 12 | - label: (Root users) No Xposed installed / Xposed is not enabled for Shizuku 13 | 14 | - type: input 15 | id: version 16 | attributes: 17 | label: Latest Shizuku version 18 | validations: 19 | required: true 20 | 21 | - type: input 22 | id: shizuku_version 23 | attributes: 24 | label: Version in use 25 | validations: 26 | required: true 27 | 28 | - type: dropdown 29 | id: mode 30 | attributes: 31 | label: Mode 32 | options: 33 | - adb 34 | - root 35 | - manual 36 | validations: 37 | required: true 38 | 39 | - type: input 40 | id: android_version 41 | attributes: 42 | label: Android version 43 | validations: 44 | required: true 45 | 46 | - type: input 47 | id: device 48 | attributes: 49 | label: Device 50 | validations: 51 | required: true 52 | 53 | - type: textarea 54 | id: reproducer 55 | attributes: 56 | label: What did you do 57 | 58 | - type: textarea 59 | id: logs 60 | attributes: 61 | label: What happened 62 | description: You can upload log and screenshot 63 | 64 | - type: textarea 65 | id: expected-behaviour 66 | attributes: 67 | label: What do you expect 68 | -------------------------------------------------------------------------------- /.github/ISSUE_TEMPLATE/config.yml: -------------------------------------------------------------------------------- 1 | blank_issues_enabled: false 2 | contact_links: 3 | - name: GitHub Community Support 4 | url: https://github.com/RikkaApps/Shizuku/discussions 5 | about: Please ask and answer questions here. 6 | -------------------------------------------------------------------------------- /.github/workflows/app.yml: -------------------------------------------------------------------------------- 1 | name: App 2 | 3 | on: 4 | push: 5 | paths-ignore: 6 | - '.github/ISSUE_TEMPLATE' 7 | 8 | jobs: 9 | build: 10 | runs-on: ubuntu-latest 11 | 12 | steps: 13 | - name: Checkout 14 | uses: actions/checkout@v4 15 | with: 16 | submodules: 'recursive' 17 | fetch-depth: 0 18 | - name: Setup Java 19 | uses: actions/setup-java@v4 20 | with: 21 | distribution: 'temurin' 22 | java-version: '21' 23 | - name: Write key 24 | if: github.event_name != 'pull_request' && github.ref == 'refs/heads/master' 25 | run: | 26 | echo KEYSTORE_PASSWORD=${{ secrets.KEYSTORE_PASSWORD }} > signing.properties 27 | echo KEYSTORE_ALIAS=${{ secrets.KEYSTORE_ALIAS }} >> signing.properties 28 | echo KEYSTORE_ALIAS_PASSWORD='${{ secrets.KEYSTORE_ALIAS_PASSWORD }}' >> signing.properties 29 | echo KEYSTORE_FILE=../key.jks >> signing.properties 30 | echo ${{ secrets.KEYSTORE }} | base64 --decode > key.jks 31 | - name: Setup Gradle 32 | uses: gradle/actions/setup-gradle@v4 33 | with: 34 | dependency-graph: generate-and-submit 35 | build-scan-publish: true 36 | build-scan-terms-of-use-url: "https://gradle.com/terms-of-service" 37 | build-scan-terms-of-use-agree: "yes" 38 | - name: Build with Gradle 39 | id: buildWithGradle 40 | run: | 41 | yes | $ANDROID_HOME/cmdline-tools/latest/bin/sdkmanager --licenses > /dev/null || true 42 | echo 'android.sdk.channel=3' >> gradle.properties 43 | echo 'android.native.buildOutput=verbose' >> gradle.properties 44 | echo 'org.gradle.caching=true' >> gradle.properties 45 | echo 'org.gradle.parallel=true' >> gradle.properties 46 | ./gradlew :manager:assemble 47 | releaseName=`ls manager/build/outputs/apk/release/shizuku*-v*-release.apk | awk -F '(/|-release.apk)' '{print $6}'` && echo "releaseName=$releaseName" >> $GITHUB_OUTPUT 48 | - name: Upload release 49 | if: success() 50 | uses: actions/upload-artifact@v4 51 | with: 52 | name: ${{ steps.buildWithGradle.outputs.releaseName }} 53 | path: "manager/build/outputs" 54 | compression-level: 9 55 | -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | *.iml 2 | .gradle 3 | /local.properties 4 | /.idea/workspace.xml 5 | /.idea/libraries 6 | .DS_Store 7 | /build 8 | /captures 9 | .externalNativeBuild 10 | /.idea 11 | /manager/signing.properties 12 | /out 13 | /signing.properties 14 | -------------------------------------------------------------------------------- /.gitmodules: -------------------------------------------------------------------------------- 1 | [submodule "api"] 2 | path = api 3 | url = git@github.com:RikkaApps/Shizuku-API.git 4 | branch = master 5 | -------------------------------------------------------------------------------- /build.gradle: -------------------------------------------------------------------------------- 1 | plugins { 2 | id("idea") 3 | } 4 | 5 | idea.module { 6 | excludeDirs += file('out') 7 | } 8 | 9 | subprojects { 10 | plugins.withId("com.android.base") { 11 | android { 12 | compileSdk = 36 13 | buildToolsVersion = "36.0.0" 14 | ndkVersion = "29.0.13113456" 15 | defaultConfig { 16 | minSdk = 24 17 | targetSdk = 36 18 | } 19 | compileOptions { 20 | sourceCompatibility = JavaVersion.VERSION_21 21 | targetCompatibility = JavaVersion.VERSION_21 22 | } 23 | } 24 | } 25 | } 26 | 27 | apply from: 'api/manifest.gradle' 28 | def gitCommitId = 'git rev-parse --short HEAD'.execute([], project.rootDir).text.trim() 29 | def gitCommitCount = Integer.parseInt('git rev-list --count HEAD'.execute([], project.rootDir).text.trim()) 30 | def baseVersionName = "${api_version_major}.6.0" 31 | ext { 32 | versionCode = gitCommitCount 33 | versionName = "${baseVersionName}.r${gitCommitCount}.${gitCommitId}" 34 | } 35 | -------------------------------------------------------------------------------- /common/.gitignore: -------------------------------------------------------------------------------- 1 | /build -------------------------------------------------------------------------------- /common/build.gradle: -------------------------------------------------------------------------------- 1 | plugins { 2 | id 'com.android.library' 3 | } 4 | 5 | android { 6 | namespace 'rikka.shizuku.common' 7 | buildFeatures { 8 | buildConfig = false 9 | } 10 | } 11 | 12 | dependencies { 13 | compileOnly libs.hidden.stub 14 | } 15 | -------------------------------------------------------------------------------- /common/src/main/AndroidManifest.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | -------------------------------------------------------------------------------- /common/src/main/java/moe/shizuku/common/util/BuildUtils.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.common.util; 2 | 3 | import android.os.Build; 4 | 5 | /** 6 | * TODO: Replace it with {@link rikka.core.util.BuildUtils}. 7 | */ 8 | public class BuildUtils { 9 | 10 | private static final int SDK = Build.VERSION.SDK_INT; 11 | 12 | private static final int PREVIEW_SDK = SDK >= 23 ? Build.VERSION.PREVIEW_SDK_INT : 0; 13 | 14 | public static boolean atLeast31() { 15 | return SDK >= 31 || SDK == 30 && PREVIEW_SDK > 0; 16 | } 17 | 18 | public static boolean atLeast30() { 19 | return SDK >= 30; 20 | } 21 | 22 | public static boolean atLeast29() { 23 | return SDK >= 29; 24 | } 25 | 26 | public static boolean atLeast28() { 27 | return SDK >= 28; 28 | } 29 | 30 | public static boolean atLeast26() { 31 | return SDK >= 26; 32 | } 33 | 34 | public static boolean atLeast24() { 35 | return SDK >= 24; 36 | } 37 | 38 | public static boolean atLeast23() { 39 | return SDK >= 23; 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /common/src/main/java/moe/shizuku/common/util/OsUtils.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.common.util; 2 | 3 | import android.os.SELinux; 4 | 5 | public class OsUtils { 6 | 7 | private static final int UID = android.system.Os.getuid(); 8 | private static final int PID = android.system.Os.getpid(); 9 | private static final String SELINUX_CONTEXT; 10 | 11 | static { 12 | String context; 13 | try { 14 | context = SELinux.getContext(); 15 | } catch (Throwable tr) { 16 | context = null; 17 | } 18 | SELINUX_CONTEXT = context; 19 | } 20 | 21 | 22 | public static int getUid() { 23 | return UID; 24 | } 25 | 26 | public static int getPid() { 27 | return PID; 28 | } 29 | 30 | public static String getSELinuxContext() { 31 | return SELINUX_CONTEXT; 32 | } 33 | } 34 | 35 | -------------------------------------------------------------------------------- /gradle.properties: -------------------------------------------------------------------------------- 1 | org.gradle.jvmargs=-Xmx2048m -Dfile.encoding=UTF-8 2 | android.useAndroidX=true 3 | android.nonTransitiveRClass=false 4 | android.nonFinalResIds=false 5 | -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.jar: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/gradle/wrapper/gradle-wrapper.jar -------------------------------------------------------------------------------- /gradle/wrapper/gradle-wrapper.properties: -------------------------------------------------------------------------------- 1 | distributionBase=GRADLE_USER_HOME 2 | distributionPath=wrapper/dists 3 | distributionUrl=https\://services.gradle.org/distributions/gradle-8.14-bin.zip 4 | networkTimeout=10000 5 | validateDistributionUrl=true 6 | zipStoreBase=GRADLE_USER_HOME 7 | zipStorePath=wrapper/dists 8 | -------------------------------------------------------------------------------- /gradlew.bat: -------------------------------------------------------------------------------- 1 | @rem 2 | @rem Copyright 2015 the original author or authors. 3 | @rem 4 | @rem Licensed under the Apache License, Version 2.0 (the "License"); 5 | @rem you may not use this file except in compliance with the License. 6 | @rem You may obtain a copy of the License at 7 | @rem 8 | @rem https://www.apache.org/licenses/LICENSE-2.0 9 | @rem 10 | @rem Unless required by applicable law or agreed to in writing, software 11 | @rem distributed under the License is distributed on an "AS IS" BASIS, 12 | @rem WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 | @rem See the License for the specific language governing permissions and 14 | @rem limitations under the License. 15 | @rem 16 | @rem SPDX-License-Identifier: Apache-2.0 17 | @rem 18 | 19 | @if "%DEBUG%"=="" @echo off 20 | @rem ########################################################################## 21 | @rem 22 | @rem Gradle startup script for Windows 23 | @rem 24 | @rem ########################################################################## 25 | 26 | @rem Set local scope for the variables with windows NT shell 27 | if "%OS%"=="Windows_NT" setlocal 28 | 29 | set DIRNAME=%~dp0 30 | if "%DIRNAME%"=="" set DIRNAME=. 31 | @rem This is normally unused 32 | set APP_BASE_NAME=%~n0 33 | set APP_HOME=%DIRNAME% 34 | 35 | @rem Resolve any "." and ".." in APP_HOME to make it shorter. 36 | for %%i in ("%APP_HOME%") do set APP_HOME=%%~fi 37 | 38 | @rem Add default JVM options here. You can also use JAVA_OPTS and GRADLE_OPTS to pass JVM options to this script. 39 | set DEFAULT_JVM_OPTS="-Xmx64m" "-Xms64m" 40 | 41 | @rem Find java.exe 42 | if defined JAVA_HOME goto findJavaFromJavaHome 43 | 44 | set JAVA_EXE=java.exe 45 | %JAVA_EXE% -version >NUL 2>&1 46 | if %ERRORLEVEL% equ 0 goto execute 47 | 48 | echo. 1>&2 49 | echo ERROR: JAVA_HOME is not set and no 'java' command could be found in your PATH. 1>&2 50 | echo. 1>&2 51 | echo Please set the JAVA_HOME variable in your environment to match the 1>&2 52 | echo location of your Java installation. 1>&2 53 | 54 | goto fail 55 | 56 | :findJavaFromJavaHome 57 | set JAVA_HOME=%JAVA_HOME:"=% 58 | set JAVA_EXE=%JAVA_HOME%/bin/java.exe 59 | 60 | if exist "%JAVA_EXE%" goto execute 61 | 62 | echo. 1>&2 63 | echo ERROR: JAVA_HOME is set to an invalid directory: %JAVA_HOME% 1>&2 64 | echo. 1>&2 65 | echo Please set the JAVA_HOME variable in your environment to match the 1>&2 66 | echo location of your Java installation. 1>&2 67 | 68 | goto fail 69 | 70 | :execute 71 | @rem Setup the command line 72 | 73 | set CLASSPATH= 74 | 75 | 76 | @rem Execute Gradle 77 | "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* 78 | 79 | :end 80 | @rem End local scope for the variables with windows NT shell 81 | if %ERRORLEVEL% equ 0 goto mainEnd 82 | 83 | :fail 84 | rem Set variable GRADLE_EXIT_CONSOLE if you need the _script_ return code instead of 85 | rem the _cmd.exe /c_ return code! 86 | set EXIT_CODE=%ERRORLEVEL% 87 | if %EXIT_CODE% equ 0 set EXIT_CODE=1 88 | if not ""=="%GRADLE_EXIT_CONSOLE%" exit %EXIT_CODE% 89 | exit /b %EXIT_CODE% 90 | 91 | :mainEnd 92 | if "%OS%"=="Windows_NT" endlocal 93 | 94 | :omega 95 | -------------------------------------------------------------------------------- /manager/.gitignore: -------------------------------------------------------------------------------- 1 | /build 2 | /signing.properties 3 | /.cxx -------------------------------------------------------------------------------- /manager/aapt2-resources.cfg: -------------------------------------------------------------------------------- 1 | color/material_orange_50#no_obfuscate 2 | color/material_indigo_50#no_obfuscate 3 | color/material_blue_grey_50#no_obfuscate 4 | color/material_teal_50#no_obfuscate 5 | color/material_cyan_50#no_obfuscate 6 | color/material_blue_50#no_obfuscate 7 | color/material_blue_grey_50#no_obfuscate 8 | color/material_deep_purple_50#no_obfuscate 9 | color/material_red_50#no_obfuscate 10 | 11 | color/material_orange_100#no_obfuscate 12 | color/material_indigo_100#no_obfuscate 13 | color/material_blue_grey_100#no_obfuscate 14 | color/material_teal_100#no_obfuscate 15 | color/material_cyan_100#no_obfuscate 16 | color/material_blue_100#no_obfuscate 17 | color/material_blue_grey_100#no_obfuscate 18 | color/material_deep_purple_100#no_obfuscate 19 | color/material_red_100#no_obfuscate 20 | 21 | color/material_orange_600#no_obfuscate 22 | color/material_indigo_600#no_obfuscate 23 | color/material_blue_grey_600#no_obfuscate 24 | color/material_teal_600#no_obfuscate 25 | color/material_cyan_600#no_obfuscate 26 | color/material_blue_600#no_obfuscate 27 | color/material_blue_grey_600#no_obfuscate 28 | color/material_deep_purple_600#no_obfuscate 29 | color/material_red_600#no_obfuscate 30 | -------------------------------------------------------------------------------- /manager/proguard-rules.pro: -------------------------------------------------------------------------------- 1 | -keepclassmembers class * implements android.os.Parcelable { 2 | public static final ** CREATOR; 3 | } 4 | 5 | -keepclasseswithmembernames,includedescriptorclasses class * { 6 | native ; 7 | } 8 | 9 | -assumenosideeffects class kotlin.jvm.internal.Intrinsics { 10 | public static void check*(...); 11 | public static void throw*(...); 12 | } 13 | 14 | -assumenosideeffects class java.util.Objects{ 15 | ** requireNonNull(...); 16 | } 17 | 18 | -keepnames class moe.shizuku.api.BinderContainer 19 | 20 | # Missing class android.app.IProcessObserver$Stub 21 | # Missing class android.app.IUidObserver$Stub 22 | -keepclassmembers class rikka.hidden.compat.adapter.ProcessObserverAdapter { 23 | ; 24 | } 25 | 26 | -keepclassmembers class rikka.hidden.compat.adapter.UidObserverAdapter { 27 | ; 28 | } 29 | 30 | # Entrance of Shizuku service 31 | -keep class rikka.shizuku.server.ShizukuService { 32 | public static void main(java.lang.String[]); 33 | } 34 | 35 | # Entrance of user service starter 36 | -keep class moe.shizuku.starter.ServiceStarter { 37 | public static void main(java.lang.String[]); 38 | } 39 | 40 | # Entrance of shell 41 | -keep class moe.shizuku.manager.shell.Shell { 42 | public static void main(java.lang.String[], java.lang.String, android.os.IBinder, android.os.Handler); 43 | } 44 | 45 | -assumenosideeffects class android.util.Log { 46 | public static *** d(...); 47 | } 48 | 49 | -assumenosideeffects class moe.shizuku.manager.utils.Logger { 50 | public *** d(...); 51 | } 52 | 53 | #noinspection ShrinkerUnresolvedReference 54 | -assumenosideeffects class rikka.shizuku.server.util.Logger { 55 | public *** d(...); 56 | } 57 | 58 | -allowaccessmodification 59 | -repackageclasses rikka.shizuku 60 | -keepattributes SourceFile,LineNumberTable 61 | -renamesourcefileattribute SourceFile 62 | -------------------------------------------------------------------------------- /manager/src/main/.gitignore: -------------------------------------------------------------------------------- 1 | /assets/*.dex -------------------------------------------------------------------------------- /manager/src/main/assets/rish: -------------------------------------------------------------------------------- 1 | #!/system/bin/sh 2 | BASEDIR=$(dirname "$0") 3 | DEX="$BASEDIR"/rish_shizuku.dex 4 | 5 | if [ ! -f "$DEX" ]; then 6 | echo "Cannot find $DEX, please check the tutorial in Shizuku app" 7 | exit 1 8 | fi 9 | 10 | if [ $(getprop ro.build.version.sdk) -ge 34 ]; then 11 | if [ -w $DEX ]; then 12 | echo "On Android 14+, app_process cannot load writable dex." 13 | echo "Attempting to remove the write permission..." 14 | chmod 400 $DEX 15 | fi 16 | if [ -w $DEX ]; then 17 | echo "Cannot remove the write permission of $DEX." 18 | echo "You can copy to file to terminal app's private directory (/data/data/, so that remove write permission is possible" 19 | exit 1 20 | fi 21 | fi 22 | 23 | # Replace "PKG" with the application id of your terminal app 24 | [ -z "$RISH_APPLICATION_ID" ] && export RISH_APPLICATION_ID="PKG" 25 | /system/bin/app_process -Djava.class.path="$DEX" /system/bin --nice-name=rish rikka.shizuku.shell.ShizukuShellLoader "$@" 26 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/AppConstants.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager; 2 | 3 | public class AppConstants { 4 | 5 | public static final String TAG = "ShizukuManager"; 6 | 7 | public static final String NOTIFICATION_CHANNEL_STATUS = "starter"; 8 | public static final String NOTIFICATION_CHANNEL_WORK = "work"; 9 | public static final int NOTIFICATION_ID_STATUS = 1; 10 | public static final int NOTIFICATION_ID_WORK = 2; 11 | 12 | private static final String PACKAGE = "moe.shizuku.manager"; 13 | public static final String EXTRA = PACKAGE + ".extra"; 14 | } 15 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/Helps.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager; 2 | 3 | import moe.shizuku.manager.utils.MultiLocaleEntity; 4 | 5 | public class Helps { 6 | 7 | public static final MultiLocaleEntity ADB = new MultiLocaleEntity(); 8 | public static final MultiLocaleEntity ADB_ANDROID11 = new MultiLocaleEntity(); 9 | public static final MultiLocaleEntity APPS = new MultiLocaleEntity(); 10 | public static final MultiLocaleEntity HOME = new MultiLocaleEntity(); 11 | public static final MultiLocaleEntity DOWNLOAD = new MultiLocaleEntity(); 12 | public static final MultiLocaleEntity SUI = new MultiLocaleEntity(); 13 | public static final MultiLocaleEntity RISH = new MultiLocaleEntity(); 14 | public static final MultiLocaleEntity ADB_PERMISSION = new MultiLocaleEntity(); 15 | 16 | static { 17 | ADB.put("zh-CN", "https://shizuku.rikka.app/zh-hans/guide/setup/"); 18 | ADB.put("zh-TW", "https://shizuku.rikka.app/zh-hant/guide/setup/"); 19 | ADB.put("en", "https://shizuku.rikka.app/guide/setup/"); 20 | 21 | ADB_ANDROID11.put("zh-CN", "https://shizuku.rikka.app/zh-hans/guide/setup/"); 22 | ADB_ANDROID11.put("zh-TW", "https://shizuku.rikka.app/zh-hant/guide/setup/"); 23 | ADB_ANDROID11.put("en", "https://shizuku.rikka.app/guide/setup/"); 24 | 25 | APPS.put("zh-CN", "https://shizuku.rikka.app/zh-hans/apps/"); 26 | APPS.put("zh-TW", "https://shizuku.rikka.app/zh-hant/apps/"); 27 | APPS.put("en", "https://shizuku.rikka.app/apps/"); 28 | 29 | HOME.put("zh-CN", "https://shizuku.rikka.app/zh-hans/"); 30 | HOME.put("zh-TW", "https://shizuku.rikka.app/zh-hant/"); 31 | HOME.put("en", "https://shizuku.rikka.app/"); 32 | 33 | DOWNLOAD.put("zh-CN", "https://shizuku.rikka.app/zh-hans/download/"); 34 | DOWNLOAD.put("zh-TW", "https://shizuku.rikka.app/zh-hant/download/"); 35 | DOWNLOAD.put("en", "https://shizuku.rikka.app/download/"); 36 | 37 | ADB_PERMISSION.put("zh-CN", "https://shizuku.rikka.app/zh-hans/guide/setup/#%E9%80%9A%E8%BF%87%E6%97%A0%E7%BA%BF%E8%B0%83%E8%AF%95%E5%90%AF%E5%8A%A8-%E9%80%9A%E8%BF%87%E8%BF%9E%E6%8E%A5%E7%94%B5%E8%84%91%E5%90%AF%E5%8A%A8-adb-%E6%9D%83%E9%99%90%E5%8F%97%E9%99%90"); 38 | ADB_PERMISSION.put("zh-TW", "https://shizuku.rikka.app/zh-hant/guide/setup/#%E9%80%8F%E9%81%8E%E7%84%A1%E7%B7%9A%E9%99%A4%E9%8C%AF%E5%95%9F%E5%8B%95-%E9%80%8F%E9%81%8E%E9%80%A3%E7%B7%9A%E9%9B%BB%E8%85%A6%E5%95%9F%E5%8B%95-adb-%E6%AC%8A%E9%99%90%E5%8F%97%E9%99%90"); 39 | ADB_PERMISSION.put("en", "https://shizuku.rikka.app/guide/setup/#start-via-wireless-debugging-start-by-connecting-to-a-computer-the-permission-of-adb-is-limited"); 40 | 41 | SUI.put("en", "https://github.com/RikkaApps/Sui"); 42 | 43 | RISH.put("en", "https://github.com/RikkaApps/Shizuku-API/tree/master/rish"); 44 | } 45 | } 46 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/MainActivity.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager; 2 | 3 | import moe.shizuku.manager.home.HomeActivity; 4 | 5 | public class MainActivity extends HomeActivity { 6 | } 7 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/Manifest.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager; 2 | 3 | public class Manifest { 4 | 5 | public static class permission { 6 | 7 | public static final String API_V23 = "moe.shizuku.manager.permission.API_V23"; 8 | } 9 | } 10 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ShizukuApplication.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager 2 | 3 | import android.app.Application 4 | import android.content.Context 5 | import android.os.Build 6 | import androidx.appcompat.app.AppCompatDelegate 7 | import com.topjohnwu.superuser.Shell 8 | import moe.shizuku.manager.ktx.logd 9 | import org.lsposed.hiddenapibypass.HiddenApiBypass 10 | import rikka.core.util.BuildUtils.atLeast30 11 | import rikka.material.app.LocaleDelegate 12 | 13 | lateinit var application: ShizukuApplication 14 | 15 | class ShizukuApplication : Application() { 16 | 17 | companion object { 18 | 19 | init { 20 | logd("ShizukuApplication", "init") 21 | 22 | Shell.setDefaultBuilder(Shell.Builder.create().setFlags(Shell.FLAG_REDIRECT_STDERR)) 23 | if (Build.VERSION.SDK_INT >= 28) { 24 | HiddenApiBypass.setHiddenApiExemptions("") 25 | } 26 | if (atLeast30) { 27 | System.loadLibrary("adb") 28 | } 29 | } 30 | } 31 | 32 | private fun init(context: Context?) { 33 | ShizukuSettings.initialize(context) 34 | LocaleDelegate.defaultLocale = ShizukuSettings.getLocale() 35 | AppCompatDelegate.setDefaultNightMode(ShizukuSettings.getNightMode()) 36 | } 37 | 38 | override fun onCreate() { 39 | super.onCreate() 40 | application = this 41 | init(this) 42 | } 43 | 44 | } 45 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ShizukuManagerProvider.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager 2 | 3 | import android.os.Bundle 4 | import androidx.core.os.bundleOf 5 | import moe.shizuku.api.BinderContainer 6 | import moe.shizuku.manager.utils.Logger.LOGGER 7 | import rikka.shizuku.Shizuku 8 | import rikka.shizuku.ShizukuApiConstants.USER_SERVICE_ARG_TOKEN 9 | import rikka.shizuku.ShizukuProvider 10 | import rikka.shizuku.server.ktx.workerHandler 11 | import java.util.concurrent.CountDownLatch 12 | import java.util.concurrent.TimeUnit 13 | import java.util.concurrent.TimeoutException 14 | 15 | class ShizukuManagerProvider : ShizukuProvider() { 16 | 17 | companion object { 18 | private const val EXTRA_BINDER = "moe.shizuku.privileged.api.intent.extra.BINDER" 19 | private const val METHOD_SEND_USER_SERVICE = "sendUserService" 20 | } 21 | 22 | override fun onCreate(): Boolean { 23 | disableAutomaticSuiInitialization() 24 | return super.onCreate() 25 | } 26 | 27 | override fun call(method: String, arg: String?, extras: Bundle?): Bundle? { 28 | if (extras == null) return null 29 | 30 | return if (method == METHOD_SEND_USER_SERVICE) { 31 | try { 32 | extras.classLoader = BinderContainer::class.java.classLoader 33 | 34 | val token = extras.getString(USER_SERVICE_ARG_TOKEN) ?: return null 35 | val binder = extras.getParcelable(EXTRA_BINDER)?.binder ?: return null 36 | 37 | val countDownLatch = CountDownLatch(1) 38 | var reply: Bundle? = Bundle() 39 | 40 | val listener = object : Shizuku.OnBinderReceivedListener { 41 | 42 | override fun onBinderReceived() { 43 | try { 44 | Shizuku.attachUserService(binder, bundleOf( 45 | USER_SERVICE_ARG_TOKEN to token 46 | )) 47 | reply!!.putParcelable(EXTRA_BINDER, BinderContainer(Shizuku.getBinder())) 48 | } catch (e: Throwable) { 49 | LOGGER.e(e, "attachUserService $token") 50 | reply = null 51 | } 52 | 53 | Shizuku.removeBinderReceivedListener(this) 54 | 55 | countDownLatch.countDown() 56 | } 57 | } 58 | 59 | Shizuku.addBinderReceivedListenerSticky(listener, workerHandler) 60 | 61 | return try { 62 | countDownLatch.await(5, TimeUnit.SECONDS) 63 | reply 64 | } catch (e: TimeoutException) { 65 | LOGGER.e(e, "Binder not received in 5s") 66 | null 67 | } 68 | } catch (e: Throwable) { 69 | LOGGER.e(e, "sendUserService") 70 | null 71 | } 72 | } else { 73 | super.call(method, arg, extras) 74 | } 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/adb/AdbException.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.adb 2 | 3 | @Suppress("NOTHING_TO_INLINE") 4 | inline fun adbError(message: Any): Nothing = throw AdbException(message.toString()) 5 | 6 | open class AdbException : Exception { 7 | 8 | constructor(message: String, cause: Throwable?) : super(message, cause) 9 | constructor(message: String) : super(message) 10 | constructor(cause: Throwable) : super(cause) 11 | constructor() 12 | } 13 | 14 | class AdbInvalidPairingCodeException : AdbException() 15 | 16 | class AdbKeyException(cause: Throwable) : AdbException(cause) 17 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/adb/AdbProtocol.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.adb 2 | 3 | object AdbProtocol { 4 | 5 | const val A_SYNC = 0x434e5953 6 | const val A_CNXN = 0x4e584e43 7 | const val A_AUTH = 0x48545541 8 | const val A_OPEN = 0x4e45504f 9 | const val A_OKAY = 0x59414b4f 10 | const val A_CLSE = 0x45534c43 11 | const val A_WRTE = 0x45545257 12 | const val A_STLS = 0x534C5453 13 | 14 | const val A_VERSION = 0x01000000 15 | const val A_MAXDATA = 4096 16 | 17 | const val A_STLS_VERSION = 0x01000000 18 | 19 | const val ADB_AUTH_TOKEN = 1 20 | const val ADB_AUTH_SIGNATURE = 2 21 | const val ADB_AUTH_RSAPUBLICKEY = 3 22 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/app/AppActivity.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.app 2 | 3 | import android.content.res.Resources 4 | import android.content.res.Resources.Theme 5 | import android.graphics.Color 6 | import android.os.Build 7 | import androidx.annotation.RequiresApi 8 | import moe.shizuku.manager.R 9 | import rikka.core.res.isNight 10 | import rikka.core.res.resolveColor 11 | import rikka.material.app.MaterialActivity 12 | 13 | abstract class AppActivity : MaterialActivity() { 14 | 15 | override fun computeUserThemeKey(): String { 16 | return ThemeHelper.getTheme(this) + ThemeHelper.isUsingSystemColor() 17 | } 18 | 19 | override fun onApplyUserThemeResource(theme: Theme, isDecorView: Boolean) { 20 | if (ThemeHelper.isUsingSystemColor()) { 21 | if (resources.configuration.isNight()) 22 | theme.applyStyle(R.style.ThemeOverlay_DynamicColors_Dark, true) 23 | else 24 | theme.applyStyle(R.style.ThemeOverlay_DynamicColors_Light, true) 25 | } 26 | 27 | theme.applyStyle(ThemeHelper.getThemeStyleRes(this), true) 28 | } 29 | 30 | @RequiresApi(Build.VERSION_CODES.M) 31 | override fun onApplyTranslucentSystemBars() { 32 | super.onApplyTranslucentSystemBars() 33 | 34 | val window = window 35 | val theme = theme 36 | 37 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) { 38 | window?.decorView?.post { 39 | if (window.decorView.rootWindowInsets?.systemWindowInsetBottom ?: 0 >= Resources.getSystem().displayMetrics.density * 40) { 40 | window.navigationBarColor = 41 | theme.resolveColor(android.R.attr.navigationBarColor) and 0x00ffffff or -0x20000000 42 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { 43 | window.isNavigationBarContrastEnforced = false 44 | } 45 | } else { 46 | window.navigationBarColor = Color.TRANSPARENT 47 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { 48 | window.isNavigationBarContrastEnforced = true 49 | } 50 | } 51 | } 52 | } 53 | } 54 | 55 | override fun onSupportNavigateUp(): Boolean { 56 | if (!super.onSupportNavigateUp()) { 57 | finish() 58 | } 59 | return true 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/app/AppBarActivity.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.app 2 | 3 | import android.graphics.Color 4 | import android.os.Build 5 | import android.os.Bundle 6 | import android.view.View 7 | import android.view.ViewGroup 8 | import android.widget.FrameLayout 9 | import androidx.annotation.LayoutRes 10 | import androidx.annotation.RequiresApi 11 | import androidx.appcompat.widget.Toolbar 12 | import com.google.android.material.appbar.AppBarLayout 13 | import moe.shizuku.manager.R 14 | import rikka.core.ktx.unsafeLazy 15 | 16 | abstract class AppBarActivity : AppActivity() { 17 | 18 | private val rootView: ViewGroup by unsafeLazy { 19 | findViewById(R.id.root) 20 | } 21 | 22 | private val toolbarContainer: AppBarLayout by unsafeLazy { 23 | findViewById(R.id.toolbar_container) 24 | } 25 | 26 | private val toolbar: Toolbar by unsafeLazy { 27 | findViewById(R.id.toolbar) 28 | } 29 | 30 | override fun onCreate(savedInstanceState: Bundle?) { 31 | super.onCreate(savedInstanceState) 32 | super.setContentView(getLayoutId()) 33 | 34 | setSupportActionBar(toolbar) 35 | } 36 | 37 | @LayoutRes 38 | open fun getLayoutId(): Int { 39 | return R.layout.appbar_activity 40 | } 41 | 42 | override fun setContentView(layoutResID: Int) { 43 | layoutInflater.inflate(layoutResID, rootView, true) 44 | rootView.bringChildToFront(toolbarContainer) 45 | } 46 | 47 | override fun setContentView(view: View?) { 48 | setContentView(view, FrameLayout.LayoutParams(ViewGroup.LayoutParams.MATCH_PARENT, ViewGroup.LayoutParams.MATCH_PARENT)) 49 | } 50 | 51 | override fun setContentView(view: View?, params: ViewGroup.LayoutParams?) { 52 | rootView.addView(view, 0, params) 53 | } 54 | 55 | @RequiresApi(Build.VERSION_CODES.M) 56 | override fun onApplyTranslucentSystemBars() { 57 | super.onApplyTranslucentSystemBars() 58 | window?.statusBarColor = Color.TRANSPARENT 59 | } 60 | } 61 | 62 | abstract class AppBarFragmentActivity : AppBarActivity() { 63 | 64 | override fun getLayoutId(): Int { 65 | return R.layout.appbar_fragment_activity 66 | } 67 | } 68 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/app/ThemeHelper.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.app; 2 | 3 | import android.content.Context; 4 | import android.os.Build; 5 | 6 | import androidx.annotation.StyleRes; 7 | 8 | import moe.shizuku.manager.R; 9 | import moe.shizuku.manager.ShizukuSettings; 10 | import moe.shizuku.manager.utils.EnvironmentUtils; 11 | import rikka.core.util.ResourceUtils; 12 | 13 | public class ThemeHelper { 14 | 15 | private static final String THEME_DEFAULT = "DEFAULT"; 16 | private static final String THEME_BLACK = "BLACK"; 17 | 18 | public static final String KEY_LIGHT_THEME = "light_theme"; 19 | public static final String KEY_BLACK_NIGHT_THEME = "black_night_theme"; 20 | public static final String KEY_USE_SYSTEM_COLOR = "use_system_color"; 21 | 22 | public static boolean isBlackNightTheme(Context context) { 23 | return ShizukuSettings.getPreferences().getBoolean(KEY_BLACK_NIGHT_THEME, EnvironmentUtils.isWatch(context)); 24 | } 25 | 26 | public static boolean isUsingSystemColor() { 27 | return Build.VERSION.SDK_INT >= Build.VERSION_CODES.S 28 | && ShizukuSettings.getPreferences().getBoolean(KEY_USE_SYSTEM_COLOR, true); 29 | } 30 | 31 | public static String getTheme(Context context) { 32 | if (isBlackNightTheme(context) 33 | && ResourceUtils.isNightMode(context.getResources().getConfiguration())) 34 | return THEME_BLACK; 35 | 36 | return ShizukuSettings.getPreferences().getString(KEY_LIGHT_THEME, THEME_DEFAULT); 37 | } 38 | 39 | @StyleRes 40 | public static int getThemeStyleRes(Context context) { 41 | switch (getTheme(context)) { 42 | case THEME_BLACK: 43 | return R.style.ThemeOverlay_Black; 44 | case THEME_DEFAULT: 45 | default: 46 | return R.style.ThemeOverlay; 47 | } 48 | } 49 | } 50 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/AdbPermissionLimitedViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.view.LayoutInflater 4 | import android.view.View 5 | import android.view.ViewGroup 6 | import moe.shizuku.manager.Helps 7 | import moe.shizuku.manager.databinding.HomeExtraStepRequiredBinding 8 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 9 | import moe.shizuku.manager.utils.CustomTabsHelper 10 | import rikka.recyclerview.BaseViewHolder 11 | import rikka.recyclerview.BaseViewHolder.Creator 12 | 13 | class AdbPermissionLimitedViewHolder(binding: HomeExtraStepRequiredBinding, root: View) : BaseViewHolder(root) { 14 | 15 | companion object { 16 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> 17 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 18 | val inner = HomeExtraStepRequiredBinding.inflate(inflater, outer.root, true) 19 | AdbPermissionLimitedViewHolder(inner, outer.root) 20 | } 21 | } 22 | 23 | init { 24 | binding.button1.setOnClickListener { v: View -> CustomTabsHelper.launchUrlOrCopy(v.context, Helps.ADB_PERMISSION.get()) } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/HomeAdapter.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.os.Build 4 | import moe.shizuku.manager.management.AppsViewModel 5 | import moe.shizuku.manager.utils.EnvironmentUtils 6 | import moe.shizuku.manager.utils.UserHandleCompat 7 | import rikka.recyclerview.IdBasedRecyclerViewAdapter 8 | import rikka.recyclerview.IndexCreatorPool 9 | import rikka.shizuku.Shizuku 10 | 11 | class HomeAdapter(private val homeModel: HomeViewModel, private val appsModel: AppsViewModel) : 12 | IdBasedRecyclerViewAdapter(ArrayList()) { 13 | 14 | init { 15 | updateData() 16 | setHasStableIds(true) 17 | } 18 | 19 | companion object { 20 | 21 | private const val ID_STATUS = 0L 22 | private const val ID_APPS = 1L 23 | private const val ID_TERMINAL = 2L 24 | private const val ID_START_ROOT = 3L 25 | private const val ID_START_WADB = 4L 26 | private const val ID_START_ADB = 5L 27 | private const val ID_LEARN_MORE = 6L 28 | private const val ID_ADB_PERMISSION_LIMITED = 7L 29 | } 30 | 31 | override fun onCreateCreatorPool(): IndexCreatorPool { 32 | return IndexCreatorPool() 33 | } 34 | 35 | fun updateData() { 36 | val status = homeModel.serviceStatus.value?.data ?: return 37 | val grantedCount = appsModel.grantedCount.value?.data ?: 0 38 | val adbPermission = status.permission 39 | val running = status.isRunning 40 | val isPrimaryUser = UserHandleCompat.myUserId() == 0 41 | 42 | clear() 43 | addItem(ServerStatusViewHolder.CREATOR, status, ID_STATUS) 44 | 45 | if (adbPermission) { 46 | addItem(ManageAppsViewHolder.CREATOR, status to grantedCount, ID_APPS) 47 | addItem(TerminalViewHolder.CREATOR, status, ID_TERMINAL) 48 | } 49 | 50 | if (running && !adbPermission) { 51 | addItem(AdbPermissionLimitedViewHolder.CREATOR, status, ID_ADB_PERMISSION_LIMITED) 52 | } 53 | 54 | if (isPrimaryUser) { 55 | val root = EnvironmentUtils.isRooted() 56 | val rootRestart = running && status.uid == 0 57 | 58 | if (root) { 59 | addItem(StartRootViewHolder.CREATOR, rootRestart, ID_START_ROOT) 60 | } 61 | 62 | if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R || EnvironmentUtils.getAdbTcpPort() > 0) { 63 | addItem(StartWirelessAdbViewHolder.CREATOR, null, ID_START_WADB) 64 | } 65 | 66 | addItem(StartAdbViewHolder.CREATOR, null, ID_START_ADB) 67 | 68 | if (!root) { 69 | addItem(StartRootViewHolder.CREATOR, rootRestart, ID_START_ROOT) 70 | } 71 | } 72 | addItem(LearnMoreViewHolder.CREATOR, null, ID_LEARN_MORE) 73 | notifyDataSetChanged() 74 | } 75 | } 76 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/HomeViewModel.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.content.pm.PackageManager 4 | import androidx.lifecycle.LiveData 5 | import androidx.lifecycle.MutableLiveData 6 | import androidx.lifecycle.ViewModel 7 | import androidx.lifecycle.viewModelScope 8 | import kotlinx.coroutines.CancellationException 9 | import kotlinx.coroutines.Dispatchers 10 | import kotlinx.coroutines.launch 11 | import moe.shizuku.manager.BuildConfig 12 | import moe.shizuku.manager.Manifest 13 | import moe.shizuku.manager.model.ServiceStatus 14 | import moe.shizuku.manager.utils.Logger.LOGGER 15 | import moe.shizuku.manager.utils.ShizukuSystemApis 16 | import rikka.lifecycle.Resource 17 | import rikka.shizuku.Shizuku 18 | 19 | class HomeViewModel : ViewModel() { 20 | 21 | private val _serviceStatus = MutableLiveData>() 22 | val serviceStatus = _serviceStatus as LiveData> 23 | 24 | private fun load(): ServiceStatus { 25 | if (!Shizuku.pingBinder()) { 26 | return ServiceStatus() 27 | } 28 | 29 | val uid = Shizuku.getUid() 30 | val apiVersion = Shizuku.getVersion() 31 | val patchVersion = Shizuku.getServerPatchVersion().let { if (it < 0) 0 else it } 32 | val seContext = if (apiVersion >= 6) { 33 | try { 34 | Shizuku.getSELinuxContext() 35 | } catch (tr: Throwable) { 36 | LOGGER.w(tr, "getSELinuxContext") 37 | null 38 | } 39 | } else null 40 | val permissionTest = 41 | Shizuku.checkRemotePermission("android.permission.GRANT_RUNTIME_PERMISSIONS") == PackageManager.PERMISSION_GRANTED 42 | 43 | // Before a526d6bb, server will not exit on uninstall, manager installed later will get not permission 44 | // Run a random remote transaction here, report no permission as not running 45 | ShizukuSystemApis.checkPermission(Manifest.permission.API_V23, BuildConfig.APPLICATION_ID, 0) 46 | return ServiceStatus(uid, apiVersion, patchVersion, seContext, permissionTest) 47 | } 48 | 49 | fun reload() { 50 | viewModelScope.launch(Dispatchers.IO) { 51 | try { 52 | val status = load() 53 | _serviceStatus.postValue(Resource.success(status)) 54 | } catch (e: CancellationException) { 55 | 56 | } catch (e: Throwable) { 57 | _serviceStatus.postValue(Resource.error(e, ServiceStatus())) 58 | } 59 | } 60 | } 61 | } 62 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/LearnMoreViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.view.LayoutInflater 4 | import android.view.View 5 | import android.view.ViewGroup 6 | import moe.shizuku.manager.Helps 7 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 8 | import moe.shizuku.manager.databinding.HomeLearnMoreBinding 9 | import moe.shizuku.manager.utils.CustomTabsHelper 10 | import rikka.recyclerview.BaseViewHolder 11 | import rikka.recyclerview.BaseViewHolder.Creator 12 | 13 | class LearnMoreViewHolder(binding: HomeLearnMoreBinding, root: View) : BaseViewHolder(root) { 14 | 15 | companion object { 16 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> 17 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 18 | val inner = HomeLearnMoreBinding.inflate(inflater, outer.root, true) 19 | LearnMoreViewHolder(inner, outer.root) 20 | } 21 | } 22 | 23 | init { 24 | root.setOnClickListener { v: View -> CustomTabsHelper.launchUrlOrCopy(v.context, Helps.HOME.get()) } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/ManageAppsViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.content.Intent 4 | import android.text.method.LinkMovementMethod 5 | import android.view.LayoutInflater 6 | import android.view.View 7 | import android.view.ViewGroup 8 | import moe.shizuku.manager.Helps 9 | import moe.shizuku.manager.R 10 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 11 | import moe.shizuku.manager.databinding.HomeManageAppsItemBinding 12 | import moe.shizuku.manager.ktx.toHtml 13 | import moe.shizuku.manager.management.ApplicationManagementActivity 14 | import moe.shizuku.manager.model.ServiceStatus 15 | import rikka.html.text.HtmlCompat 16 | import rikka.recyclerview.BaseViewHolder 17 | import rikka.recyclerview.BaseViewHolder.Creator 18 | 19 | class ManageAppsViewHolder(private val binding: HomeManageAppsItemBinding, root: View) : 20 | BaseViewHolder>(root), View.OnClickListener { 21 | 22 | companion object { 23 | val CREATOR = Creator> { inflater: LayoutInflater, parent: ViewGroup? -> 24 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 25 | val inner = HomeManageAppsItemBinding.inflate(inflater, outer.root, true) 26 | ManageAppsViewHolder(inner, outer.root) 27 | } 28 | } 29 | 30 | init { 31 | root.setOnClickListener(this) 32 | } 33 | 34 | private inline val title get() = binding.text1 35 | private inline val summary get() = binding.text2 36 | 37 | override fun onBind() { 38 | val context = itemView.context 39 | if (!data.first.isRunning) { 40 | itemView.isEnabled = false 41 | title.setText(R.string.home_app_management_title) 42 | summary.text = context.getString( 43 | R.string.home_status_service_not_running, 44 | context.getString(R.string.app_name) 45 | ) 46 | } else { 47 | itemView.isEnabled = true 48 | title.text = context.resources.getQuantityString( 49 | R.plurals.home_app_management_authorized_apps_count, 50 | data.second, 51 | data.second 52 | ) 53 | summary.text = context.getString(R.string.home_app_management_view_authorized_apps) 54 | } 55 | } 56 | 57 | override fun onClick(v: View) { 58 | v.context.startActivity(Intent(v.context, ApplicationManagementActivity::class.java)) 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/StartAdbViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.content.Intent 4 | import android.text.method.LinkMovementMethod 5 | import android.view.LayoutInflater 6 | import android.view.View 7 | import android.view.ViewGroup 8 | import android.widget.Toast 9 | import com.google.android.material.dialog.MaterialAlertDialogBuilder 10 | import moe.shizuku.manager.Helps 11 | import moe.shizuku.manager.R 12 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 13 | import moe.shizuku.manager.databinding.HomeStartAdbBinding 14 | import moe.shizuku.manager.ktx.toHtml 15 | import moe.shizuku.manager.starter.Starter 16 | import rikka.core.util.ClipboardUtils 17 | import rikka.html.text.HtmlCompat 18 | import rikka.recyclerview.BaseViewHolder 19 | import rikka.recyclerview.BaseViewHolder.Creator 20 | 21 | class StartAdbViewHolder(binding: HomeStartAdbBinding, root: View) : BaseViewHolder(root) { 22 | 23 | companion object { 24 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> 25 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 26 | val inner = HomeStartAdbBinding.inflate(inflater, outer.root, true) 27 | StartAdbViewHolder(inner, outer.root) 28 | } 29 | } 30 | 31 | init { 32 | binding.button1.setOnClickListener { v: View -> 33 | val context = v.context 34 | MaterialAlertDialogBuilder(context) 35 | .setTitle(R.string.home_adb_button_view_command) 36 | .setMessage( 37 | HtmlCompat.fromHtml( 38 | context.getString( 39 | R.string.home_adb_dialog_view_command_message, 40 | Starter.adbCommand 41 | ) 42 | ) 43 | ) 44 | .setPositiveButton(R.string.home_adb_dialog_view_command_copy_button) { _, _ -> 45 | if (ClipboardUtils.put(context, Starter.adbCommand)) { 46 | Toast.makeText( 47 | context, 48 | context.getString(R.string.toast_copied_to_clipboard, Starter.adbCommand), 49 | Toast.LENGTH_SHORT 50 | ).show() 51 | } 52 | } 53 | .setNegativeButton(android.R.string.cancel, null) 54 | .setNeutralButton(R.string.home_adb_dialog_view_command_button_send) { _, _ -> 55 | var intent = Intent(Intent.ACTION_SEND) 56 | intent.type = "text/plain" 57 | intent.putExtra(Intent.EXTRA_TEXT, Starter.adbCommand) 58 | intent = Intent.createChooser( 59 | intent, 60 | context.getString(R.string.home_adb_dialog_view_command_button_send) 61 | ) 62 | context.startActivity(intent) 63 | } 64 | .show() 65 | } 66 | binding.text1.movementMethod = LinkMovementMethod.getInstance() 67 | binding.text1.text = context.getString(R.string.home_adb_description, Helps.ADB.get()) 68 | .toHtml(HtmlCompat.FROM_HTML_OPTION_TRIM_WHITESPACE) 69 | } 70 | } 71 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/StartRootViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.content.Intent 4 | import android.text.method.LinkMovementMethod 5 | import android.view.LayoutInflater 6 | import android.view.View 7 | import android.view.ViewGroup 8 | import androidx.appcompat.app.AlertDialog 9 | import moe.shizuku.manager.Helps 10 | import moe.shizuku.manager.R 11 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 12 | import moe.shizuku.manager.databinding.HomeStartRootBinding 13 | import moe.shizuku.manager.ktx.toHtml 14 | import moe.shizuku.manager.starter.StarterActivity 15 | import rikka.html.text.HtmlCompat 16 | import rikka.recyclerview.BaseViewHolder 17 | import rikka.recyclerview.BaseViewHolder.Creator 18 | import rikka.shizuku.Shizuku 19 | 20 | class StartRootViewHolder(private val binding: HomeStartRootBinding, root: View) : 21 | BaseViewHolder(root) { 22 | 23 | companion object { 24 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> 25 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 26 | val inner = HomeStartRootBinding.inflate(inflater, outer.root, true) 27 | StartRootViewHolder(inner, outer.root) 28 | } 29 | } 30 | 31 | private inline val start get() = binding.button1 32 | private inline val restart get() = binding.button2 33 | 34 | private var alertDialog: AlertDialog? = null 35 | 36 | init { 37 | val listener = View.OnClickListener { v: View -> onStartClicked(v) } 38 | start.setOnClickListener(listener) 39 | restart.setOnClickListener(listener) 40 | binding.text1.movementMethod = LinkMovementMethod.getInstance() 41 | } 42 | 43 | private fun onStartClicked(v: View) { 44 | val context = v.context 45 | val intent = Intent(context, StarterActivity::class.java).apply { 46 | putExtra(StarterActivity.EXTRA_IS_ROOT, true) 47 | } 48 | context.startActivity(intent) 49 | } 50 | 51 | override fun onBind() { 52 | start.isEnabled = true 53 | restart.isEnabled = true 54 | if (data!!) { 55 | start.visibility = View.GONE 56 | restart.visibility = View.VISIBLE 57 | } else { 58 | start.visibility = View.VISIBLE 59 | restart.visibility = View.GONE 60 | } 61 | 62 | val sb = StringBuilder() 63 | .append( 64 | context.getString( 65 | R.string.home_root_description, 66 | "Don\'t kill my app!" 67 | ) 68 | ) 69 | if (Shizuku.pingBinder()) { 70 | sb.append("

").append( 71 | context.getString( 72 | R.string.home_root_description_sui, 73 | "Sui", 74 | "Sui" 75 | ) 76 | ) 77 | } 78 | 79 | binding.text1.text = sb.toHtml(HtmlCompat.FROM_HTML_OPTION_TRIM_WHITESPACE) 80 | } 81 | 82 | override fun onRecycle() { 83 | super.onRecycle() 84 | alertDialog = null 85 | } 86 | } 87 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/TerminalViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.content.Intent 4 | import android.view.LayoutInflater 5 | import android.view.View 6 | import android.view.ViewGroup 7 | import moe.shizuku.manager.R 8 | import moe.shizuku.manager.databinding.HomeItemContainerBinding 9 | import moe.shizuku.manager.databinding.HomeTerminalBinding 10 | import moe.shizuku.manager.model.ServiceStatus 11 | import moe.shizuku.manager.shell.ShellTutorialActivity 12 | import rikka.recyclerview.BaseViewHolder 13 | import rikka.recyclerview.BaseViewHolder.Creator 14 | 15 | class TerminalViewHolder(private val binding: HomeTerminalBinding, private val root: View) : 16 | BaseViewHolder(root), 17 | View.OnClickListener { 18 | 19 | companion object { 20 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> 21 | val outer = HomeItemContainerBinding.inflate(inflater, parent, false) 22 | val inner = HomeTerminalBinding.inflate(inflater, outer.root, true) 23 | TerminalViewHolder(inner, outer.root) 24 | } 25 | } 26 | 27 | init { 28 | root.setOnClickListener(this) 29 | } 30 | 31 | private inline val summary get() = binding.text2 32 | 33 | override fun onBind() { 34 | val context = itemView.context 35 | if (!data.isRunning) { 36 | root.isEnabled = false 37 | summary.text = 38 | context.getString(R.string.home_status_service_not_running, context.getString(R.string.app_name)) 39 | } else { 40 | root.isEnabled = true 41 | summary.text = context.getString(R.string.home_terminal_description) 42 | } 43 | } 44 | 45 | override fun onClick(v: View) { 46 | v.context.startActivity(Intent(v.context, ShellTutorialActivity::class.java)) 47 | } 48 | } 49 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/home/WadbNotEnabledDialogFragment.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.home 2 | 3 | import android.app.Dialog 4 | import android.os.Bundle 5 | import androidx.fragment.app.DialogFragment 6 | import androidx.fragment.app.FragmentManager 7 | import com.google.android.material.dialog.MaterialAlertDialogBuilder 8 | import moe.shizuku.manager.R 9 | 10 | class WadbNotEnabledDialogFragment :DialogFragment() { 11 | 12 | override fun onCreateDialog(savedInstanceState: Bundle?): Dialog { 13 | val context = requireContext() 14 | return MaterialAlertDialogBuilder(context) 15 | .setMessage(R.string.dialog_wireless_adb_not_enabled) 16 | .setPositiveButton(android.R.string.ok, null) 17 | .create() 18 | } 19 | 20 | fun show(fragmentManager: FragmentManager) { 21 | if (fragmentManager.isStateSaved) return 22 | show(fragmentManager, javaClass.simpleName) 23 | } 24 | } 25 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ktx/Context.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.ktx 2 | 3 | import android.content.Context 4 | import android.os.Build 5 | import android.os.UserManager 6 | import moe.shizuku.manager.ShizukuApplication 7 | 8 | val Context.application: ShizukuApplication 9 | get() { 10 | return applicationContext as ShizukuApplication 11 | } 12 | 13 | fun Context.createDeviceProtectedStorageContextCompat(): Context { 14 | return if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { 15 | createDeviceProtectedStorageContext() 16 | } else { 17 | this 18 | } 19 | } 20 | 21 | fun Context.createDeviceProtectedStorageContextCompatWhenLocked(): Context { 22 | return if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && getSystemService(UserManager::class.java)?.isUserUnlocked != true) { 23 | createDeviceProtectedStorageContext() 24 | } else { 25 | this 26 | } 27 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ktx/Log.kt: -------------------------------------------------------------------------------- 1 | @file:Suppress("NOTHING_TO_INLINE") 2 | 3 | package moe.shizuku.manager.ktx 4 | 5 | import android.util.Log 6 | 7 | inline val T.TAG: String 8 | get() = 9 | T::class.java.simpleName.let { 10 | if (it.isBlank()) throw IllegalStateException("tag is empty") 11 | if (it.length > 23) it.substring(0, 23) else it 12 | } 13 | 14 | inline fun T.logv(message: String, throwable: Throwable? = null) = logv(TAG, message, throwable) 15 | inline fun T.logi(message: String, throwable: Throwable? = null) = logi(TAG, message, throwable) 16 | inline fun T.logw(message: String, throwable: Throwable? = null) = logw(TAG, message, throwable) 17 | inline fun T.logd(message: String, throwable: Throwable? = null) = logd(TAG, message, throwable) 18 | inline fun T.loge(message: String, throwable: Throwable? = null) = loge(TAG, message, throwable) 19 | 20 | inline fun T.logv(tag: String, message: String, throwable: Throwable? = null) = Log.v(tag, message, throwable) 21 | inline fun T.logi(tag: String, message: String, throwable: Throwable? = null) = Log.i(tag, message, throwable) 22 | inline fun T.logw(tag: String, message: String, throwable: Throwable? = null) = Log.w(tag, message, throwable) 23 | inline fun T.logd(tag: String, message: String, throwable: Throwable? = null) = Log.d(tag, message, throwable) 24 | inline fun T.loge(tag: String, message: String, throwable: Throwable? = null) = Log.e(tag, message, throwable) -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ktx/PackageManager.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.ktx 2 | 3 | import android.content.ComponentName 4 | import android.content.pm.PackageManager 5 | 6 | fun PackageManager.setComponentEnabled(componentName: ComponentName, enabled: Boolean) { 7 | val oldState = getComponentEnabledSetting(componentName) 8 | val newState = if (enabled) PackageManager.COMPONENT_ENABLED_STATE_ENABLED else PackageManager.COMPONENT_ENABLED_STATE_DISABLED 9 | if (newState != oldState) { 10 | val flags = PackageManager.DONT_KILL_APP 11 | setComponentEnabledSetting(componentName, newState, flags) 12 | } 13 | } 14 | 15 | fun PackageManager.isComponentEnabled(componentName: ComponentName, defaultValue: Boolean = true): Boolean { 16 | return when (getComponentEnabledSetting(componentName)) { 17 | PackageManager.COMPONENT_ENABLED_STATE_DISABLED -> false 18 | PackageManager.COMPONENT_ENABLED_STATE_ENABLED -> true 19 | PackageManager.COMPONENT_ENABLED_STATE_DEFAULT -> defaultValue 20 | else -> false 21 | } 22 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ktx/RecyclerView.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.ktx 2 | 3 | import android.graphics.Canvas 4 | import android.widget.EdgeEffect 5 | import androidx.recyclerview.widget.RecyclerView 6 | 7 | class FixedAlwaysClipToPaddingEdgeEffectFactory( 8 | private val paddingLeft: Int, 9 | private val paddingTop: Int, 10 | private val paddingRight: Int, 11 | private val paddingBottom: Int 12 | ) : RecyclerView.EdgeEffectFactory() { 13 | 14 | 15 | override fun createEdgeEffect(view: RecyclerView, direction: Int): EdgeEffect { 16 | 17 | return object : EdgeEffect(view.context) { 18 | private var ensureSize = false 19 | 20 | private fun ensureSize() { 21 | if (ensureSize) return 22 | ensureSize = true 23 | 24 | when (direction) { 25 | DIRECTION_LEFT -> { 26 | setSize(view.measuredHeight - paddingTop - paddingBottom, 27 | view.measuredWidth - paddingLeft - paddingRight) 28 | } 29 | DIRECTION_TOP -> { 30 | setSize(view.measuredWidth - paddingLeft - paddingRight, 31 | view.measuredHeight - paddingTop - paddingBottom) 32 | } 33 | DIRECTION_RIGHT -> { 34 | setSize(view.measuredHeight - paddingTop - paddingBottom, 35 | view.measuredWidth - paddingLeft - paddingRight) 36 | } 37 | DIRECTION_BOTTOM -> { 38 | setSize(view.measuredWidth - paddingLeft - paddingRight, 39 | view.measuredHeight - paddingTop - paddingBottom) 40 | } 41 | } 42 | } 43 | 44 | override fun draw(c: Canvas): Boolean { 45 | ensureSize() 46 | 47 | val restore = c.save() 48 | when (direction) { 49 | DIRECTION_LEFT -> { 50 | c.translate(paddingBottom.toFloat(), 0f) 51 | } 52 | DIRECTION_TOP -> { 53 | c.translate(paddingLeft.toFloat(), paddingTop.toFloat()) 54 | } 55 | DIRECTION_RIGHT -> { 56 | c.translate(-paddingTop.toFloat(), 0f) 57 | } 58 | DIRECTION_BOTTOM -> { 59 | c.translate(paddingRight.toFloat(), paddingBottom.toFloat()) 60 | } 61 | } 62 | val res = super.draw(c) 63 | c.restoreToCount(restore) 64 | return res 65 | } 66 | } 67 | } 68 | } 69 | 70 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/ktx/String.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.ktx 2 | 3 | import android.text.Spanned 4 | import rikka.html.text.HtmlCompat 5 | 6 | fun CharSequence.toHtml(flags: Int = 0): Spanned { 7 | return HtmlCompat.fromHtml(this.toString(), flags) 8 | } 9 | 10 | fun CharSequence.toHtml(tagHandler: HtmlCompat.TagHandler): Spanned { 11 | return HtmlCompat.fromHtml(this.toString(), null, tagHandler) 12 | } 13 | 14 | fun CharSequence.toHtml(flags: Int, tagHandler: HtmlCompat.TagHandler): Spanned { 15 | return HtmlCompat.fromHtml(this.toString(), flags, null, tagHandler) 16 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/legacy/ShellRequestHandlerActivity.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.legacy 2 | 3 | import android.os.Bundle 4 | import android.widget.Toast 5 | import moe.shizuku.manager.app.AppActivity 6 | import moe.shizuku.manager.shell.ShellBinderRequestHandler 7 | 8 | class ShellRequestHandlerActivity : AppActivity() { 9 | 10 | override fun onCreate(savedInstanceState: Bundle?) { 11 | super.onCreate(savedInstanceState) 12 | 13 | ShellBinderRequestHandler.handleRequest(this, intent) 14 | finish() 15 | } 16 | } 17 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/management/ApplicationManagementActivity.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.management 2 | 3 | import android.os.Bundle 4 | import android.util.TypedValue 5 | import android.view.MenuItem 6 | import android.widget.Toast 7 | import androidx.recyclerview.widget.RecyclerView.AdapterDataObserver 8 | import moe.shizuku.manager.Helps 9 | import moe.shizuku.manager.R 10 | import moe.shizuku.manager.app.AppBarActivity 11 | import moe.shizuku.manager.databinding.AppsActivityBinding 12 | import moe.shizuku.manager.utils.CustomTabsHelper 13 | import rikka.lifecycle.Status 14 | import rikka.recyclerview.addEdgeSpacing 15 | import rikka.recyclerview.fixEdgeEffect 16 | import rikka.shizuku.Shizuku 17 | import java.util.* 18 | 19 | class ApplicationManagementActivity : AppBarActivity() { 20 | 21 | private val viewModel by appsViewModel() 22 | private val adapter = AppsAdapter() 23 | 24 | private val binderDeadListener = Shizuku.OnBinderDeadListener { 25 | if (!isFinishing) { 26 | finish() 27 | } 28 | } 29 | 30 | override fun onCreate(savedInstanceState: Bundle?) { 31 | super.onCreate(savedInstanceState) 32 | 33 | if (!Shizuku.pingBinder()) { 34 | finish() 35 | return 36 | } 37 | 38 | val binding = AppsActivityBinding.inflate(layoutInflater) 39 | setContentView(binding.root) 40 | 41 | supportActionBar?.setDisplayHomeAsUpEnabled(true) 42 | 43 | viewModel.packages.observe(this) { 44 | when (it.status) { 45 | Status.SUCCESS -> { 46 | adapter.updateData(it.data) 47 | } 48 | Status.ERROR -> { 49 | finish() 50 | val tr = it.error 51 | Toast.makeText(this, Objects.toString(tr, "unknown"), Toast.LENGTH_SHORT).show() 52 | tr.printStackTrace() 53 | } 54 | Status.LOADING -> { 55 | 56 | } 57 | } 58 | } 59 | if (viewModel.packages.value == null) { 60 | viewModel.load() 61 | } 62 | 63 | val recyclerView = binding.list 64 | recyclerView.adapter = adapter 65 | recyclerView.fixEdgeEffect() 66 | recyclerView.addEdgeSpacing(top = 8f, bottom = 8f, unit = TypedValue.COMPLEX_UNIT_DIP) 67 | 68 | adapter.registerAdapterDataObserver(object : AdapterDataObserver() { 69 | override fun onItemRangeChanged(positionStart: Int, itemCount: Int, payload: Any?) { 70 | viewModel.load(true) 71 | } 72 | }) 73 | 74 | Shizuku.addBinderDeadListener(binderDeadListener) 75 | } 76 | 77 | override fun onDestroy() { 78 | super.onDestroy() 79 | 80 | Shizuku.removeBinderDeadListener(binderDeadListener) 81 | } 82 | 83 | override fun onResume() { 84 | super.onResume() 85 | adapter.notifyDataSetChanged() 86 | } 87 | } 88 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/management/AppsAdapter.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.management; 2 | 3 | import android.content.pm.PackageInfo; 4 | 5 | import java.util.List; 6 | 7 | import rikka.recyclerview.BaseRecyclerViewAdapter; 8 | import rikka.recyclerview.ClassCreatorPool; 9 | 10 | public class AppsAdapter extends BaseRecyclerViewAdapter { 11 | 12 | public AppsAdapter() { 13 | super(); 14 | 15 | getCreatorPool().putRule(PackageInfo.class, AppViewHolder.CREATOR); 16 | getCreatorPool().putRule(Object.class, EmptyViewHolder.CREATOR); 17 | setHasStableIds(true); 18 | } 19 | 20 | @Override 21 | public long getItemId(int position) { 22 | return getItemAt(position).hashCode(); 23 | } 24 | 25 | @Override 26 | public ClassCreatorPool onCreateCreatorPool() { 27 | return new ClassCreatorPool(); 28 | } 29 | 30 | public void updateData(List data) { 31 | getItems().clear(); 32 | if (data.isEmpty()) { 33 | getItems().add(new Object()); 34 | } else { 35 | getItems().addAll(data); 36 | } 37 | notifyDataSetChanged(); 38 | } 39 | } 40 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/management/AppsViewModel.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.management 2 | 3 | import android.content.Context 4 | import android.content.pm.PackageInfo 5 | import androidx.activity.ComponentActivity 6 | import androidx.annotation.MainThread 7 | import androidx.fragment.app.Fragment 8 | import androidx.lifecycle.LiveData 9 | import androidx.lifecycle.MutableLiveData 10 | import androidx.lifecycle.ViewModel 11 | import androidx.lifecycle.viewModelScope 12 | import kotlinx.coroutines.CancellationException 13 | import kotlinx.coroutines.Dispatchers 14 | import kotlinx.coroutines.launch 15 | import moe.shizuku.manager.authorization.AuthorizationManager 16 | import rikka.lifecycle.Resource 17 | import rikka.lifecycle.activityViewModels 18 | import rikka.lifecycle.viewModels 19 | 20 | @MainThread 21 | fun ComponentActivity.appsViewModel() = viewModels { AppsViewModel(this) } 22 | 23 | @MainThread 24 | fun Fragment.appsViewModel() = activityViewModels { AppsViewModel(requireContext()) } 25 | 26 | class AppsViewModel(context: Context) : ViewModel() { 27 | 28 | private val _packages = MutableLiveData>>() 29 | val packages = _packages as LiveData>> 30 | 31 | private val _grantedCount = MutableLiveData>() 32 | val grantedCount = _grantedCount as LiveData> 33 | 34 | fun load(onlyCount: Boolean = false) { 35 | viewModelScope.launch(Dispatchers.IO) { 36 | try { 37 | val list: MutableList = ArrayList() 38 | var count = 0 39 | for (pi in AuthorizationManager.getPackages()) { 40 | list.add(pi) 41 | if (AuthorizationManager.granted(pi.packageName, pi.applicationInfo!!.uid)) count++ 42 | } 43 | if (!onlyCount) _packages.postValue(Resource.success(list)) 44 | _grantedCount.postValue(Resource.success(count)) 45 | } catch (e: CancellationException) { 46 | 47 | } catch (e: Throwable) { 48 | _packages.postValue(Resource.error(e, null)) 49 | _grantedCount.postValue(Resource.error(e, 0)) 50 | } 51 | } 52 | } 53 | } 54 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/management/EmptyViewHolder.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.management 2 | 3 | import android.content.pm.PackageInfo 4 | import android.text.method.LinkMovementMethod 5 | import android.view.LayoutInflater 6 | import android.view.View 7 | import android.view.ViewGroup 8 | import android.widget.TextView 9 | import androidx.appcompat.app.AlertDialog 10 | import androidx.appcompat.content.res.AppCompatResources 11 | import com.google.android.material.dialog.MaterialAlertDialogBuilder 12 | import kotlinx.coroutines.Job 13 | import moe.shizuku.manager.Helps 14 | import moe.shizuku.manager.R 15 | import moe.shizuku.manager.authorization.AuthorizationManager 16 | import moe.shizuku.manager.databinding.AppListEmptyBinding 17 | import moe.shizuku.manager.databinding.AppListItemBinding 18 | import moe.shizuku.manager.ktx.toHtml 19 | import moe.shizuku.manager.utils.AppIconCache 20 | import moe.shizuku.manager.utils.ShizukuSystemApis 21 | import moe.shizuku.manager.utils.UserHandleCompat 22 | import rikka.html.text.HtmlCompat 23 | import rikka.recyclerview.BaseViewHolder 24 | import rikka.recyclerview.BaseViewHolder.Creator 25 | import rikka.shizuku.Shizuku 26 | 27 | class EmptyViewHolder(private val binding: AppListEmptyBinding) : BaseViewHolder(binding.root) { 28 | 29 | companion object { 30 | @JvmField 31 | val CREATOR = Creator { inflater: LayoutInflater, parent: ViewGroup? -> EmptyViewHolder(AppListEmptyBinding.inflate(inflater, parent, false)) } 32 | } 33 | 34 | } 35 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/model/ServiceStatus.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.model 2 | 3 | import rikka.shizuku.Shizuku 4 | 5 | data class ServiceStatus( 6 | val uid: Int = -1, 7 | val apiVersion: Int = -1, 8 | val patchVersion: Int = -1, 9 | val seContext: String? = null, 10 | val permission: Boolean = false 11 | ) { 12 | val isRunning: Boolean 13 | get() = uid != -1 && Shizuku.pingBinder() 14 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/receiver/ShizukuReceiver.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.receiver 2 | 3 | import android.content.BroadcastReceiver 4 | import android.content.Context 5 | import android.content.Intent 6 | import moe.shizuku.manager.shell.ShellBinderRequestHandler 7 | 8 | class ShizukuReceiver : BroadcastReceiver() { 9 | 10 | override fun onReceive(context: Context, intent: Intent) { 11 | if ("rikka.shizuku.intent.action.REQUEST_BINDER" == intent.action) { 12 | ShellBinderRequestHandler.handleRequest(context, intent) 13 | } 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/settings/SettingsActivity.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.settings 2 | 3 | import android.content.res.Resources 4 | import android.os.Bundle 5 | import moe.shizuku.manager.R 6 | import moe.shizuku.manager.app.AppBarFragmentActivity 7 | 8 | class SettingsActivity : AppBarFragmentActivity() { 9 | 10 | override fun onApplyUserThemeResource(theme: Resources.Theme, isDecorView: Boolean) { 11 | super.onApplyUserThemeResource(theme, isDecorView) 12 | theme.applyStyle(R.style.ThemeOverlay_Rikka_Material3_Preference, true) 13 | } 14 | 15 | override fun onCreate(savedInstanceState: Bundle?) { 16 | super.onCreate(savedInstanceState) 17 | 18 | supportActionBar?.setDisplayHomeAsUpEnabled(true) 19 | 20 | if (savedInstanceState == null) { 21 | supportFragmentManager.beginTransaction() 22 | .replace(R.id.fragment_container, SettingsFragment()) 23 | .commit() 24 | } 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/shell/Shell.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.shell; 2 | 3 | import android.content.pm.PackageManager; 4 | import android.os.Handler; 5 | import android.os.IBinder; 6 | 7 | import rikka.rish.Rish; 8 | import rikka.rish.RishConfig; 9 | import rikka.shizuku.Shizuku; 10 | import rikka.shizuku.ShizukuApiConstants; 11 | 12 | public class Shell extends Rish { 13 | 14 | @Override 15 | public void requestPermission(Runnable onGrantedRunnable) { 16 | if (Shizuku.checkSelfPermission() == PackageManager.PERMISSION_GRANTED) { 17 | onGrantedRunnable.run(); 18 | } else if (Shizuku.shouldShowRequestPermissionRationale()) { 19 | System.err.println("Permission denied"); 20 | System.err.flush(); 21 | System.exit(1); 22 | } else { 23 | Shizuku.addRequestPermissionResultListener(new Shizuku.OnRequestPermissionResultListener() { 24 | @Override 25 | public void onRequestPermissionResult(int requestCode, int grantResult) { 26 | Shizuku.removeRequestPermissionResultListener(this); 27 | 28 | if (grantResult == PackageManager.PERMISSION_GRANTED) { 29 | onGrantedRunnable.run(); 30 | } else { 31 | System.err.println("Permission denied"); 32 | System.err.flush(); 33 | System.exit(1); 34 | } 35 | } 36 | }); 37 | Shizuku.requestPermission(0); 38 | } 39 | } 40 | 41 | public static void main(String[] args, String packageName, IBinder binder, Handler handler) { 42 | RishConfig.init(binder, ShizukuApiConstants.BINDER_DESCRIPTOR, 30000); 43 | Shizuku.onBinderReceived(binder, packageName); 44 | Shizuku.addBinderReceivedListenerSticky(() -> { 45 | int version = Shizuku.getVersion(); 46 | if (version < 12) { 47 | System.err.println("Rish requires server 12 (running " + version + ")"); 48 | System.err.flush(); 49 | System.exit(1); 50 | } 51 | new Shell().start(args); 52 | }); 53 | } 54 | } 55 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/shell/ShellBinderRequestHandler.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.shell 2 | 3 | import android.content.Context 4 | import android.content.Intent 5 | import android.os.IBinder 6 | import android.os.Parcel 7 | import moe.shizuku.manager.utils.Logger.LOGGER 8 | import rikka.shizuku.Shizuku 9 | 10 | object ShellBinderRequestHandler { 11 | 12 | fun handleRequest(context: Context, intent: Intent): Boolean { 13 | if (intent.action != "rikka.shizuku.intent.action.REQUEST_BINDER") { 14 | return false 15 | } 16 | 17 | val binder = intent.getBundleExtra("data")?.getBinder("binder") ?: return false 18 | val shizukuBinder = Shizuku.getBinder() 19 | if (shizukuBinder == null) { 20 | LOGGER.w("Binder not received or Shizuku service not running") 21 | } 22 | 23 | val data = Parcel.obtain() 24 | return try { 25 | data.writeStrongBinder(shizukuBinder) 26 | data.writeString(context.applicationInfo.sourceDir) 27 | binder.transact(1, data, null, IBinder.FLAG_ONEWAY) 28 | true 29 | } catch (e: Throwable) { 30 | e.printStackTrace() 31 | false 32 | } finally { 33 | data.recycle() 34 | } 35 | } 36 | } 37 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/starter/Starter.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.starter 2 | 3 | import moe.shizuku.manager.application 4 | import java.io.File 5 | 6 | object Starter { 7 | 8 | private val starterFile = File(application.applicationInfo.nativeLibraryDir, "libshizuku.so") 9 | 10 | val userCommand: String = starterFile.absolutePath 11 | 12 | val adbCommand = "adb shell $userCommand" 13 | 14 | val internalCommand = "$userCommand --apk=${application.applicationInfo.sourceDir}" 15 | } 16 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/utils/EmptySharedPreferencesImpl.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.utils; 2 | 3 | import android.content.SharedPreferences; 4 | 5 | import androidx.annotation.Nullable; 6 | 7 | import java.util.HashMap; 8 | import java.util.Map; 9 | import java.util.Set; 10 | 11 | public class EmptySharedPreferencesImpl implements SharedPreferences { 12 | 13 | @Override 14 | public Map getAll() { 15 | return new HashMap<>(); 16 | } 17 | 18 | @Nullable 19 | @Override 20 | public String getString(String key, @Nullable String defValue) { 21 | return defValue; 22 | } 23 | 24 | @Nullable 25 | @Override 26 | public Set getStringSet(String key, @Nullable Set defValues) { 27 | return defValues; 28 | } 29 | 30 | @Override 31 | public int getInt(String key, int defValue) { 32 | return defValue; 33 | } 34 | 35 | @Override 36 | public long getLong(String key, long defValue) { 37 | return defValue; 38 | } 39 | 40 | @Override 41 | public float getFloat(String key, float defValue) { 42 | return defValue; 43 | } 44 | 45 | @Override 46 | public boolean getBoolean(String key, boolean defValue) { 47 | return defValue; 48 | } 49 | 50 | @Override 51 | public boolean contains(String key) { 52 | return false; 53 | } 54 | 55 | @Override 56 | public Editor edit() { 57 | return new EditorImpl(); 58 | } 59 | 60 | @Override 61 | public void registerOnSharedPreferenceChangeListener(OnSharedPreferenceChangeListener listener) { 62 | 63 | } 64 | 65 | @Override 66 | public void unregisterOnSharedPreferenceChangeListener(OnSharedPreferenceChangeListener listener) { 67 | 68 | } 69 | 70 | private static class EditorImpl implements Editor { 71 | 72 | @Override 73 | public Editor putString(String key, @Nullable String value) { 74 | return this; 75 | } 76 | 77 | @Override 78 | public Editor putStringSet(String key, @Nullable Set values) { 79 | return this; 80 | } 81 | 82 | @Override 83 | public Editor putInt(String key, int value) { 84 | return this; 85 | } 86 | 87 | @Override 88 | public Editor putLong(String key, long value) { 89 | return this; 90 | } 91 | 92 | @Override 93 | public Editor putFloat(String key, float value) { 94 | return this; 95 | } 96 | 97 | @Override 98 | public Editor putBoolean(String key, boolean value) { 99 | return this; 100 | } 101 | 102 | @Override 103 | public Editor remove(String key) { 104 | return this; 105 | } 106 | 107 | @Override 108 | public Editor clear() { 109 | return this; 110 | } 111 | 112 | @Override 113 | public boolean commit() { 114 | return true; 115 | } 116 | 117 | @Override 118 | public void apply() { 119 | 120 | } 121 | } 122 | } 123 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/utils/EnvironmentUtils.kt: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.utils 2 | 3 | import android.app.UiModeManager 4 | import android.content.Context 5 | import android.content.res.Configuration 6 | import android.os.SystemProperties 7 | import java.io.File 8 | 9 | object EnvironmentUtils { 10 | 11 | @JvmStatic 12 | fun isWatch(context: Context): Boolean { 13 | return (context.getSystemService(UiModeManager::class.java).currentModeType 14 | == Configuration.UI_MODE_TYPE_WATCH) 15 | } 16 | 17 | fun isRooted(): Boolean { 18 | return System.getenv("PATH")?.split(File.pathSeparatorChar)?.find { File("$it/su").exists() } != null 19 | } 20 | 21 | fun getAdbTcpPort(): Int { 22 | var port = SystemProperties.getInt("service.adb.tcp.port", -1) 23 | if (port == -1) port = SystemProperties.getInt("persist.adb.tcp.port", -1) 24 | return port 25 | } 26 | } 27 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/utils/MultiLocaleEntity.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.utils; 2 | 3 | import androidx.annotation.NonNull; 4 | 5 | import java.util.LinkedHashMap; 6 | import java.util.Locale; 7 | 8 | import moe.shizuku.manager.ShizukuSettings; 9 | 10 | public class MultiLocaleEntity extends LinkedHashMap { 11 | 12 | public abstract static class LocaleProvider { 13 | public abstract Locale get(); 14 | } 15 | 16 | public static final LocaleProvider DEFAULT_LOCAL_PROVIDER = new LocaleProvider() { 17 | @Override 18 | public Locale get() { 19 | return ShizukuSettings.getLocale(); 20 | } 21 | }; 22 | 23 | private static LocaleProvider sLocaleProvider = DEFAULT_LOCAL_PROVIDER; 24 | 25 | public static void setLocaleProvider(@NonNull LocaleProvider localeProvider) { 26 | sLocaleProvider = localeProvider; 27 | } 28 | 29 | public String get() { 30 | return get(sLocaleProvider.get()); 31 | } 32 | 33 | public String get(@NonNull Locale locale) { 34 | if (size() > 0) { 35 | String language = locale.getLanguage(); 36 | String region = locale.getCountry(); 37 | 38 | // fully match 39 | locale = new Locale(language, region); 40 | for (String l : keySet()) { 41 | if (locale.toString().equals(l.replace('-', '_'))) { 42 | return get(l); 43 | } 44 | } 45 | 46 | // match language only keys 47 | locale = new Locale(language); 48 | for (String l : keySet()) { 49 | if (locale.toString().equals(l)) { 50 | return get(l); 51 | } 52 | } 53 | 54 | // match a language_region with only language 55 | for (String l : keySet()) { 56 | if (l.startsWith(locale.toString())) { 57 | return get(l); 58 | } 59 | } 60 | 61 | if (containsKey("en")) { 62 | return get("en"); 63 | } 64 | 65 | if (containsKey("default")) { 66 | return get("default"); 67 | } 68 | 69 | for (String key : keySet()) { 70 | if (!"overwrite_default".equals(key)) 71 | return get(key); 72 | } 73 | } 74 | return null; 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/utils/UserHandleCompat.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.utils; 2 | 3 | import android.system.Os; 4 | 5 | public class UserHandleCompat { 6 | 7 | private static final int MY_USER_ID = getUserId(Os.getuid()); 8 | 9 | public static final int PER_USER_RANGE = 100000; 10 | 11 | public static int getUserId(int uid) { 12 | return uid / PER_USER_RANGE; 13 | } 14 | 15 | public static int getAppId(int uid) { 16 | return uid % PER_USER_RANGE; 17 | } 18 | 19 | public static int myUserId() { 20 | return MY_USER_ID; 21 | } 22 | } -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/utils/UserInfoCompat.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.utils; 2 | 3 | public class UserInfoCompat { 4 | 5 | public final int id; 6 | public final String name; 7 | 8 | public UserInfoCompat(int id, String name) { 9 | this.id = id; 10 | this.name = name; 11 | } 12 | } 13 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/widget/CheckedImageView.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.widget; 2 | 3 | import android.content.Context; 4 | import android.util.AttributeSet; 5 | import android.widget.Checkable; 6 | import android.widget.ImageView; 7 | 8 | import androidx.annotation.Nullable; 9 | 10 | public class CheckedImageView extends ImageView implements Checkable { 11 | 12 | private boolean mChecked; 13 | 14 | private static final int[] CHECKED_STATE_SET = { 15 | android.R.attr.state_checked 16 | }; 17 | 18 | public CheckedImageView(Context context) { 19 | super(context); 20 | } 21 | 22 | public CheckedImageView(Context context, @Nullable AttributeSet attrs) { 23 | super(context, attrs); 24 | } 25 | 26 | public CheckedImageView(Context context, @Nullable AttributeSet attrs, int defStyleAttr) { 27 | super(context, attrs, defStyleAttr); 28 | } 29 | 30 | public CheckedImageView(Context context, @Nullable AttributeSet attrs, int defStyleAttr, int defStyleRes) { 31 | super(context, attrs, defStyleAttr, defStyleRes); 32 | } 33 | 34 | @Override 35 | public void setChecked(boolean checked) { 36 | if (mChecked != checked) { 37 | mChecked = checked; 38 | refreshDrawableState(); 39 | } 40 | } 41 | 42 | @Override 43 | public boolean isChecked() { 44 | return mChecked; 45 | } 46 | 47 | @Override 48 | public void toggle() { 49 | setChecked(!mChecked); 50 | } 51 | 52 | @Override 53 | public int[] onCreateDrawableState(int extraSpace) { 54 | final int[] drawableState = super.onCreateDrawableState(extraSpace + 1); 55 | if (isChecked()) { 56 | mergeDrawableStates(drawableState, CHECKED_STATE_SET); 57 | } 58 | return drawableState; 59 | } 60 | } 61 | -------------------------------------------------------------------------------- /manager/src/main/java/moe/shizuku/manager/widget/VerticalPaddingDecoration.java: -------------------------------------------------------------------------------- 1 | package moe.shizuku.manager.widget; 2 | 3 | import android.content.Context; 4 | import android.graphics.Rect; 5 | import android.view.View; 6 | 7 | import androidx.annotation.NonNull; 8 | import androidx.recyclerview.widget.RecyclerView; 9 | 10 | public class VerticalPaddingDecoration extends RecyclerView.ItemDecoration { 11 | 12 | private boolean mAllowTop, mAllowBottom; 13 | private int mPadding; 14 | 15 | public VerticalPaddingDecoration(Context context) { 16 | this(context, 8); 17 | } 18 | 19 | public VerticalPaddingDecoration(Context context, int paddingDp) { 20 | this.mPadding = Math.round(paddingDp * context.getResources().getDisplayMetrics().density); 21 | this.mAllowTop = true; 22 | this.mAllowBottom = true; 23 | } 24 | 25 | public void setAllowTop(boolean allowTop) { 26 | mAllowTop = allowTop; 27 | } 28 | 29 | public void setAllowBottom(boolean allowBottom) { 30 | mAllowBottom = allowBottom; 31 | } 32 | 33 | @Override 34 | public void getItemOffsets(@NonNull Rect outRect, @NonNull View view, @NonNull RecyclerView parent, @NonNull RecyclerView.State state) { 35 | if (parent.getAdapter() == null) { 36 | return; 37 | } 38 | int position = parent.getChildAdapterPosition(view); 39 | int count = parent.getAdapter().getItemCount(); 40 | if (position == 0 && mAllowTop) { 41 | outRect.top = mPadding; 42 | } else if (position == count - 1 && mAllowBottom) { 43 | outRect.bottom = mPadding; 44 | } 45 | } 46 | } 47 | 48 | -------------------------------------------------------------------------------- /manager/src/main/jni/CMakeLists.txt: -------------------------------------------------------------------------------- 1 | cmake_minimum_required(VERSION 3.31) 2 | 3 | project("shizuku") 4 | 5 | set(CMAKE_CXX_STANDARD 17) 6 | 7 | add_compile_options(-Werror=format -fdata-sections -ffunction-sections -fno-exceptions -fno-rtti -fno-threadsafe-statics) 8 | 9 | if (NOT CMAKE_BUILD_TYPE STREQUAL "Debug") 10 | message("Builing Release...") 11 | 12 | add_compile_options(-Os -flto -fvisibility=hidden -fvisibility-inlines-hidden) 13 | add_link_options(-flto -Wl,--exclude-libs,ALL -Wl,--gc-sections -Wl,--strip-all) 14 | else () 15 | message("Builing Debug...") 16 | 17 | add_definitions(-DDEBUG) 18 | endif () 19 | 20 | find_package(boringssl REQUIRED CONFIG) 21 | find_package(cxx REQUIRED CONFIG) 22 | 23 | add_executable(libshizuku.so 24 | starter.cpp misc.cpp selinux.cpp cgroup.cpp) 25 | 26 | target_link_libraries(libshizuku.so log cxx::cxx) 27 | 28 | if (NOT CMAKE_BUILD_TYPE STREQUAL "Debug") 29 | add_custom_command(TARGET libshizuku.so POST_BUILD 30 | COMMAND ${CMAKE_STRIP} --remove-section=.comment "${CMAKE_LIBRARY_OUTPUT_DIRECTORY}/libshizuku.so") 31 | endif () 32 | 33 | add_library(adb SHARED 34 | adb_pairing.cpp misc.cpp) 35 | 36 | target_link_libraries(adb log boringssl::crypto_static cxx::cxx) 37 | 38 | if (NOT CMAKE_BUILD_TYPE STREQUAL "Debug") 39 | add_custom_command(TARGET adb POST_BUILD 40 | COMMAND ${CMAKE_STRIP} --remove-section=.comment "${CMAKE_LIBRARY_OUTPUT_DIRECTORY}/libadb.so") 41 | endif () 42 | -------------------------------------------------------------------------------- /manager/src/main/jni/adb_pairing.h: -------------------------------------------------------------------------------- 1 | #ifndef ADB_H 2 | #define ADB_H 3 | 4 | #endif // ADB_H 5 | -------------------------------------------------------------------------------- /manager/src/main/jni/android.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | 7 | namespace android { 8 | 9 | int GetApiLevel() { 10 | static int apiLevel = 0; 11 | if (apiLevel > 0) return apiLevel; 12 | 13 | char buf[PROP_VALUE_MAX + 1]; 14 | if (__system_property_get("ro.build.version.sdk", buf) > 0) 15 | apiLevel = atoi(buf); 16 | 17 | return apiLevel; 18 | } 19 | 20 | int GetPreviewApiLevel() { 21 | static int previewApiLevel = 0; 22 | if (previewApiLevel > 0) return previewApiLevel; 23 | 24 | char buf[PROP_VALUE_MAX + 1]; 25 | if (__system_property_get("ro.build.version.preview_sdk", buf) > 0) 26 | previewApiLevel = atoi(buf); 27 | 28 | return previewApiLevel; 29 | } 30 | } -------------------------------------------------------------------------------- /manager/src/main/jni/android.h: -------------------------------------------------------------------------------- 1 | #pragma once 2 | 3 | namespace android { 4 | 5 | int GetApiLevel(); 6 | 7 | int GetPreviewApiLevel(); 8 | } -------------------------------------------------------------------------------- /manager/src/main/jni/cgroup.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | 6 | namespace cgroup { 7 | bool switch_cgroup(const char *cgroup, int pid) { 8 | char buf[1024]; 9 | snprintf(buf, sizeof(buf), "%s/cgroup.procs", cgroup); 10 | if (access(buf, F_OK) != 0) 11 | return false; 12 | int fd = open(buf, O_WRONLY | O_APPEND | O_CLOEXEC); 13 | if (fd == -1) 14 | return false; 15 | snprintf(buf, sizeof(buf), "%d\n", pid); 16 | ssize_t c = write(fd, buf, strlen(buf)); 17 | close(fd); 18 | return c == strlen(buf); 19 | } 20 | } 21 | -------------------------------------------------------------------------------- /manager/src/main/jni/cgroup.h: -------------------------------------------------------------------------------- 1 | #ifndef CGROUP_H 2 | #define CGROUP_H 3 | 4 | namespace cgroup { 5 | bool switch_cgroup(const char *cgroup, int pid); 6 | } 7 | 8 | #endif // CGROUP_H 9 | -------------------------------------------------------------------------------- /manager/src/main/jni/helper.cpp: -------------------------------------------------------------------------------- 1 | #include 2 | #include 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include "selinux.h" 10 | 11 | #define LOG_TAG "ShizukuServer" 12 | 13 | #include "logging.h" 14 | 15 | static jint setcontext(JNIEnv *env, jobject thiz, jstring jName) { 16 | const char *name = env->GetStringUTFChars(jName, nullptr); 17 | 18 | if (!se::setcon) 19 | return -1; 20 | 21 | int res = se::setcon(name); 22 | if (res == -1) PLOGE("setcon %s", name); 23 | 24 | env->ReleaseStringUTFChars(jName, name); 25 | 26 | return res; 27 | } 28 | 29 | static JNINativeMethod gMethods[] = { 30 | {"setSELinuxContext", "(Ljava/lang/String;)I", (void *) setcontext}, 31 | }; 32 | 33 | static int registerNativeMethods(JNIEnv *env, const char *className, 34 | JNINativeMethod *gMethods, int numMethods) { 35 | jclass clazz; 36 | clazz = env->FindClass(className); 37 | if (clazz == nullptr) 38 | return JNI_FALSE; 39 | 40 | if (env->RegisterNatives(clazz, gMethods, numMethods) < 0) 41 | return JNI_FALSE; 42 | 43 | return JNI_TRUE; 44 | } 45 | 46 | static int registerNatives(JNIEnv *env) { 47 | if (!registerNativeMethods(env, "moe/shizuku/server/utils/NativeHelper", gMethods, 48 | sizeof(gMethods) / sizeof(gMethods[0]))) 49 | return JNI_FALSE; 50 | 51 | return JNI_TRUE; 52 | } 53 | 54 | JNIEXPORT jint JNICALL JNI_OnLoad(JavaVM *vm, void *reserved) { 55 | JNIEnv *env = nullptr; 56 | jint result; 57 | 58 | if (vm->GetEnv((void **) &env, JNI_VERSION_1_6) != JNI_OK) 59 | return -1; 60 | 61 | assert(env != nullptr); 62 | 63 | se::init(); 64 | 65 | if (!registerNatives(env)) { 66 | LOGE("registerNatives NativeHelper"); 67 | return -1; 68 | } 69 | 70 | result = JNI_VERSION_1_6; 71 | 72 | return result; 73 | } 74 | -------------------------------------------------------------------------------- /manager/src/main/jni/logging.h: -------------------------------------------------------------------------------- 1 | #ifndef _LOGGING_H 2 | #define _LOGGING_H 3 | 4 | #include 5 | #include "android/log.h" 6 | 7 | #ifndef LOG_TAG 8 | #define LOG_TAG "Shizuku" 9 | #endif 10 | 11 | #ifndef NO_LOG 12 | #ifndef NO_DEBUG_LOG 13 | #define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG, LOG_TAG, __VA_ARGS__) 14 | #else 15 | #define LOGD(...) 16 | #endif 17 | #define LOGV(...) __android_log_print(ANDROID_LOG_VERBOSE, LOG_TAG, __VA_ARGS__) 18 | #define LOGI(...) __android_log_print(ANDROID_LOG_INFO, LOG_TAG, __VA_ARGS__) 19 | #define LOGW(...) __android_log_print(ANDROID_LOG_WARN, LOG_TAG, __VA_ARGS__) 20 | #define LOGE(...) __android_log_print(ANDROID_LOG_ERROR, LOG_TAG, __VA_ARGS__) 21 | #define PLOGE(fmt, args...) LOGE(fmt " failed with %d: %s", ##args, errno, strerror(errno)) 22 | #else 23 | #define LOGD(...) 24 | #define LOGV(...) 25 | #define LOGI(...) 26 | #define LOGW(...) 27 | #define LOGE(...) 28 | #define PLOGE(fmt, args...) 29 | #endif 30 | #endif // _LOGGING_H 31 | -------------------------------------------------------------------------------- /manager/src/main/jni/misc.h: -------------------------------------------------------------------------------- 1 | #ifndef MISC_H 2 | #define MISC_H 3 | 4 | int copyfile(const char *src_path, const char *dst_path); 5 | uintptr_t memsearch(const uintptr_t start, const uintptr_t end, const void *value, size_t size); 6 | int switch_mnt_ns(int pid); 7 | int get_proc_name(int pid, char *name, size_t _size); 8 | 9 | using foreach_proc_function = void(pid_t); 10 | void foreach_proc(foreach_proc_function *func); 11 | 12 | char *trim(char *str); 13 | 14 | #endif // MISC_H 15 | -------------------------------------------------------------------------------- /manager/src/main/jni/selinux.h: -------------------------------------------------------------------------------- 1 | #ifndef SELINUX_H 2 | #define SELINUX_H 3 | 4 | namespace se { 5 | void init(); 6 | 7 | using getcon_t = int(char **); 8 | using setcon_t = int(const char *); 9 | using setfilecon_t = int(const char *, const char *); 10 | using selinux_check_access_t = int(const char *, const char *, const char *, const char *, 11 | void *); 12 | using freecon_t = void(char *); 13 | 14 | extern getcon_t *getcon; 15 | extern setcon_t *setcon; 16 | extern setfilecon_t *setfilecon; 17 | extern selinux_check_access_t *selinux_check_access; 18 | extern freecon_t *freecon; 19 | } 20 | 21 | #endif // SELINUX_H 22 | -------------------------------------------------------------------------------- /manager/src/main/res/animator/alpha_animator.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 11 | 12 | 13 | 14 | 15 | 20 | 21 | 22 | -------------------------------------------------------------------------------- /manager/src/main/res/color-night/home_card_background_color.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/color-night/home_card_foreground_color.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/color/grant_permissions_button_ripple_color_selector.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /manager/src/main/res/color/home_card_background_color.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/color/home_card_foreground_color.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable-v24/ic_default_app_icon_foreground.xml: -------------------------------------------------------------------------------- 1 | 7 | 12 | 13 | 19 | 22 | 25 | 26 | 27 | 28 | 34 | 35 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable-v26/ic_default_app_icon.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable-v26/ic_launcher.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 7 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/card_btn_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/grant_permissions_buttons_bottom.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 7 | 8 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/grant_permissions_buttons_top.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 6 | 7 | 8 | 13 | 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/home_card_foreground.xml: -------------------------------------------------------------------------------- 1 | 2 | 17 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_action_about_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_action_settings_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_adb_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_baseline_link_24.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_close_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_code_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_help_outline_24dp.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 10 | 13 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_launcher.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_learn_more_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_monochrome.xml: -------------------------------------------------------------------------------- 1 | 6 | 11 | 14 | 15 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_numeric_1_circle_outline_24.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_numeric_2_circle_outline_24.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_numeric_3_circle_outline_24.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_arrow_upward_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_dark_mode_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_info_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_notifications_active_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_open_in_new_24.xml: -------------------------------------------------------------------------------- 1 | 8 | 11 | 12 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_play_arrow_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_outline_translate_24.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_root_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 7 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_server_error_24dp.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_server_ok_24dp.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_server_restart.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_server_start_24dp.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_settings_outline_24dp.xml: -------------------------------------------------------------------------------- 1 | 7 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_system_icon.xml: -------------------------------------------------------------------------------- 1 | 6 | 11 | 14 | 15 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_terminal_24.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_wadb_24.xml: -------------------------------------------------------------------------------- 1 | 6 | 7 | 17 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/ic_warning_24.xml: -------------------------------------------------------------------------------- 1 | 6 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/drawable/shape_circle_icon_background.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 5 | 10 | 11 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/about_dialog.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 15 | 16 | 21 | 22 | 28 | 29 | 34 | 35 | 43 | 44 | 45 | 46 | 47 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/adb_dialog.xml: -------------------------------------------------------------------------------- 1 | 2 | 12 | 13 | 19 | 20 | 25 | 26 | 33 | 34 | 35 | 36 | 37 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/app_list_empty.xml: -------------------------------------------------------------------------------- 1 | 2 | 10 | 11 | 18 | 19 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/app_list_item.xml: -------------------------------------------------------------------------------- 1 | 2 | 15 | 16 | 22 | 23 | 30 | 31 | 37 | 38 | 47 | 48 | 53 | 54 | 60 | 61 | 62 | 63 | 64 | 65 | 71 | 72 | 73 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/appbar.xml: -------------------------------------------------------------------------------- 1 | 2 | 11 | 12 | 22 | 23 | 24 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/appbar_activity.xml: -------------------------------------------------------------------------------- 1 | 2 | 13 | 14 | 15 | 16 | 17 | 18 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/appbar_fragment_activity.xml: -------------------------------------------------------------------------------- 1 | 2 | 13 | 14 | 18 | 19 | 20 | 21 | 22 | 23 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/apps_activity.xml: -------------------------------------------------------------------------------- 1 | 2 | 18 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/confirmation_dialog.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 18 | 19 | 31 | 32 | 36 | 37 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_activity.xml: -------------------------------------------------------------------------------- 1 | 2 | 21 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_extra_step_required.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 14 | 15 | 23 | 24 | 30 | 31 | 39 | 40 | 41 | 42 | 43 | 44 | 53 | 54 | 62 | 63 | 64 | 65 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_item_container.xml: -------------------------------------------------------------------------------- 1 | 2 | 16 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_learn_more.xml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 13 | 14 | 20 | 21 | 28 | 29 | 36 | 37 | 38 | 39 | 40 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_manage_apps_item.xml: -------------------------------------------------------------------------------- 1 | 2 | 6 | 7 | 13 | 14 | 20 | 21 | 28 | 29 | 36 | 37 | 38 | 39 | 40 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_server_status.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 16 | 17 | 23 | 24 | 32 | 33 | 39 | 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_start_adb.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 13 | 14 | 20 | 21 | 28 | 29 | 30 | 31 | 40 | 41 | 48 | 49 | 50 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_start_root.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 15 | 16 | 22 | 23 | 31 | 32 | 33 | 34 | 42 | 43 | 49 | 50 | 58 | 59 | 60 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_start_wireless_adb.xml: -------------------------------------------------------------------------------- 1 | 2 | 9 | 10 | 15 | 16 | 22 | 23 | 30 | 31 | 32 | 33 | 41 | 42 | 47 | 48 | 53 | 54 | 59 | 60 | 61 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/home_terminal.xml: -------------------------------------------------------------------------------- 1 | 2 | 8 | 9 | 15 | 16 | 22 | 23 | 30 | 31 | 38 | 39 | 40 | 41 | 42 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/preference_recyclerview.xml: -------------------------------------------------------------------------------- 1 | 2 | 19 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/shell_dialog.xml: -------------------------------------------------------------------------------- 1 | 2 | 5 | 6 | 9 | 10 | 18 | 19 | 20 | 21 | -------------------------------------------------------------------------------- /manager/src/main/res/layout/starter_activity.xml: -------------------------------------------------------------------------------- 1 | 2 | 7 | 8 | 20 | 21 | 33 | 34 | 35 | 36 | 37 | -------------------------------------------------------------------------------- /manager/src/main/res/menu/main.xml: -------------------------------------------------------------------------------- 1 | 2 |

3 | 4 | 9 | 10 | 14 | 15 | 19 | 20 | -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-hdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-hdpi/ic_launcher.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-hdpi/ic_launcher_background.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-hdpi/ic_launcher_background.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-hdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-hdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xhdpi/banner.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xhdpi/banner.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xhdpi/ic_launcher.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xhdpi/ic_launcher_background.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xhdpi/ic_launcher_background.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxhdpi/ic_launcher_background.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxhdpi/ic_launcher_background.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxxhdpi/ic_launcher.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxxhdpi/ic_launcher.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxxhdpi/ic_launcher_background.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxxhdpi/ic_launcher_background.png -------------------------------------------------------------------------------- /manager/src/main/res/mipmap-xxxhdpi/ic_launcher_foreground.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/RikkaApps/Shizuku/16d28799e4039f0c008ec20513be20174a087069/manager/src/main/res/mipmap-xxxhdpi/ic_launcher_foreground.png -------------------------------------------------------------------------------- /manager/src/main/res/values-ang/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | Webmaster araçlan 5 | 6 | 7 | Webmaster araçlan 8 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ars/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | “ارجوك شغل ”المعالجة اللاسلكية 4 | \"عم نشيّك خاصية \"المعالجة اللاسلكية 5 | على إصدارات الأندرويد ١١ او اعلى، فيك تشغل \"المعالجة اللاسلكية\" وتشغل معها شيزوكو مباشرا من جهازك، من دون ما تتصل بالكمبيوتر 6 | \nبحيات ربك، ارجوك شوف التعليمات 7 | بلش بـالمعالجة اللاسلكية 8 | نسخ 9 | شوف الأمر 10 | -------------------------------------------------------------------------------- /manager/src/main/res/values-bg/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-bn/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | নকল 4 | কমান্ড প্রদর্শন করুন 5 | সহযোগিতা নিন 6 | একটি কম্পিউটার এ সংযোগ প্রদানের মাধ্যমে শুরু করুন 7 | সংস্করণ %2$s, %1$s<br> %3$s সংস্করণে নবায়ন করতে আবার শুরু করুন 8 | সংস্করণ %2$s, %1$s 9 | %1$s চলছে না 10 | %1$s চলমান 11 | অনুবাদকগণ 12 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ca/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Activeu \"Depuració sense fil\" a \"Opcions de desenvolupador\". La \"depuració sense fil\" es desactiva automàticament quan canvia la xarxa. 4 | \n 5 | \nTingueu en compte que no desactiveu les \"Opcions de desenvolupador\" ni la \"depuració USB\", o Shizuku s\'aturarà. 6 | Abans d\'Android 11, cal connectar-se a un ordinador per habilitar la depuració sense fil. 7 | Obre Shizuku 8 | El codi de vinculació és incorrecte. 9 | Codi d\'aparellament 10 | S\'està buscant el servei d\'aparellament 11 | Vincula amb el dispositiu 12 | Maridatge 13 | El port és un nombre enter que va de l\'1 al 65535. 14 | Si us plau, proveu de desactivar i activar \"Depuració sense fil\" si continua cercant. 15 | Cercant servei de depuració sense fil 16 | Guia pas a pas 17 | Comenceu mitjançant la depuració sense fil 18 | Enviar 19 | Còpia 20 | Veure comanda 21 | Llegeix l\'ajuda 22 | Comenceu connectant-vos a un ordinador 23 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ckb/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-da/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-el/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Δεν είναι δυνατή η σύνδεση με την υπηρεσία ασύρματου εντοπισμού σφαλμάτων. 4 | Ο κωδικός σύζευξης είναι εσφαλμένος. 5 | Κωδικός σύζευξης 6 | Αναζήτηση για υπηρεσία σύζευξης 7 | Σύζευξη με συσκευή 8 | Σύζευξη 9 | Η θύρα είναι ένας ακέραιος αριθμός μεταξύ 1 και 65535. 10 | Αναζήτηση για υπηρεσία ασύρματου εντοπισμού σφαλμάτων 11 | Αναλυτικός οδηγός 12 | Πριν από το Android 11, είναι απαραίτητη η σύνδεση με έναν υπολογιστή για την ενεργοποίηση του ασύρματου εντοπισμού σφαλμάτων. 13 | Προβολή εντολής 14 | Ανάγνωση βοήθειας 15 | Για συσκευές χωρίς πρόσβαση root, πρέπει να χρησιμοποιήσετε το adb για την εκκίνηση του Shizuku (απαιτεί σύνδεση σε υπολογιστή). Αυτή η διαδικασία θα πρέπει να επαναλαμβάνεται κάθε φορά που επανεκκινείται η συσκευή. Διαβάστε τη βοήθεια. 16 | Έναρξη μέσω σύνδεσης με υπολογιστή 17 | Έκδοση %2$s, %1$s<br>Κάντε ξανά εκκίνηση για ενημέρωση στην έκδοση %3$s 18 | Το %1$s δεν εκτελείται 19 | Το %1$s εκτελείται 20 | Θύρα 21 | Έναρξη μέσω Ασύρματου εντοπισμού σφαλμάτων 22 | -------------------------------------------------------------------------------- /manager/src/main/res/values-enm/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-eo/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Nigra nokta etoso 4 | Aspekto 5 | Lingvo 6 | Agordoj 7 | Lerni Shizuku 8 | 9 | Rajtigis %d aplikaĵon 10 | Rajtigis %d aplikaĵojn 11 | 12 | Komenci 13 | Programistaj opcioj 14 | Sendi 15 | Kopii 16 | Vidi komandon 17 | Legi helpon 18 | Konektu al komputilo por komenci 19 | Versio %2$s, %1$s 20 | %1$s ne estas funkcianta 21 | %1$s estas funkcianta 22 | JakubFabijan 23 | 24 | -------------------------------------------------------------------------------- /manager/src/main/res/values-es-rCL/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Iniciar desde depuración inalámbrica 4 | Enviar 5 | Copiar 6 | <font face=monospace>%1$s</font><br><br>* Esto tiene otras consideraciones, por favor confirme que ha leído la información de ayuda primero. 7 | Ver ayuda 8 | Ver comando 9 | Para dispositivos sin root, usted necesita ADB para ejecutar Shizuku (requiere una conexión a un ordenador). Este proceso se debe repetir cada vez que el dispositivo sea reiniciando. <b><a href=\"%1$s\">obtener más ayuda</a></b>. 10 | Versión %2$s, %1$s 11 | %1$s no está activo 12 | %1$s está activo 13 | Abrir Shizuku 14 | Acerca de 15 | Opciones de desarrollador 16 | El sistema requiere que el cuadro de diálogo de emparejamiento esté siempre visible, el uso del modo de pantalla dividida es la única forma de permitir que esta aplicación y el cuadro de diálogo del sistema estén visibles al mismo tiempo. 17 | Ingrese primero al modo de pantalla dividida (ventanas múltiples). 18 | El puerto es un número entero comprendido entre 1 y 65535. 19 | Puerto 20 | Buscando servicio de depuración inalámbrica 21 | Empiece por conectarse a su computador 22 | —Peter Cuevas 23 | Versión %2$s, %1$s<br>Reinicie para actualizar a la versión %3$s 24 | 25 | -------------------------------------------------------------------------------- /manager/src/main/res/values-et/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Saada 4 | Kopeeri 5 | Versioon %2$s, %1$s 6 | -------------------------------------------------------------------------------- /manager/src/main/res/values-fi/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-he/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | הצג פקודה 4 | קראו את דפי העזרה 5 | עבור מכשירים ללא גישת שורש, עליך להשתמש ב-adb כדי להתחיל את Shizuku (נדרש חיבור למחשב). \u0020עליך לחזור על תהליך זה בכל פעם שמכשירך יופעל מחדש. בבקשה קראו את דפי העזרה. 6 | התחל באמצעות חיבור למחשב 7 | גירסה %2$s, %1$s<br>התחל מחדש כדי לעדכן לגירסה %3$s 8 | גירסה %2$s, %1$s 9 | %1$s לא רץ 10 | %1$s פועל 11 | <font face=monospace>%1$s</font><br><br>* יש עדין שיקולים אחרים, בבקשה תאשר שקראת את העזרה לפני. 12 | שלח 13 | העתק 14 | באנדרואיד 11 ומעלה, אתם יכולים להפעיל ניפוי באגים אלחוטי ולהתחיל את Shizuku ישירות מהמכשיר שלכם, ללא חיבור למחשב. קודם כל, הביטו בבקשה במדריך. 15 | התחל עם ניפוי באגים אלחוטי 16 | -------------------------------------------------------------------------------- /manager/src/main/res/values-hi/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-hr/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ka/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | ბრძანების ნახვა 4 | წაიკითხეთ დახმარება 5 | არა დარუთული მოწყობილობებისთვის, Shizuku რომ ჩართო შენ გჭირდება ადბ-ს გამოყენება(საჭიროებს კომპიუტერთან კავშირს). ეს პროცესი უნდა გაიმეოროთ თქვენი მოწყობილობის ყოველ გადატვირთვაზე. გთხოვთ წაიკითხოთ დახმარება. 6 | დაიწყე კომპიუტერთან დაკავშირებით 7 | ვერსია %2$, %1$<br>თავიდან ჩართე, რომ განაახლო %3$s ვერსიაზე 8 | ვერსია 9 | არ მუშაობს 10 | მთავარი-სტატუსი 11 | მთარგმნელები 12 | -------------------------------------------------------------------------------- /manager/src/main/res/values-kk/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-km/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-kn/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-lb/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-lv/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-mk/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ml/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-ms/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | Versi %2$s, %1$s 4 | %1$s tidak berjalan 5 | Sistem memerlukan dialog berpasangan sentiasa kelihatan, menggunakan mod skrin pisah ialah satu-satunya cara untuk membolehkan apl dan dialog sistem ini kelihatan serentak. 6 | Hantar 7 | Salin 8 | -------------------------------------------------------------------------------- /manager/src/main/res/values-my/strings.xml: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /manager/src/main/res/values-night/styles.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 10 | 11 | 16 | 17 | 21 | 22 | 26 | 27 | 42 | 43 | 44 | -------------------------------------------------------------------------------- /manager/src/main/res/values-v31/themes_overlay.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 6 | 7 | 9 | 10 | -------------------------------------------------------------------------------- /manager/src/main/res/values/arrays.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | @string/dark_theme_off 6 | @string/dark_theme_on 7 | @string/follow_system 8 | 9 | 10 | 11 | 1 12 | 2 13 | -1 14 | 15 | 16 | 17 | -------------------------------------------------------------------------------- /manager/src/main/res/values/attrs.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | -------------------------------------------------------------------------------- /manager/src/main/res/values/bools.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | false 5 | -------------------------------------------------------------------------------- /manager/src/main/res/values/colors.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | #3F51B5 4 | 5 | #3F51B5 6 | #B1B8DF 7 | 8 | -------------------------------------------------------------------------------- /manager/src/main/res/values/dimens.xml: -------------------------------------------------------------------------------- 1 | 2 | 4 | 16dp 5 | 6 | 18sp 7 | 8 | 16dp 9 | 10 | 16dp 11 | 72dp 12 | 0dp 13 | 14 | 0dp 15 | 16 | 4dp 17 | 18 | 40dp 19 | 20 | 16dp 21 | 22 | 23 | -------------------------------------------------------------------------------- /manager/src/main/res/values/strings_untranslatable.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | https://rikka.app/contribute_translation/ 4 | 5 | -------------------------------------------------------------------------------- /manager/src/main/res/values/themes.xml: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 15 | 16 | 27 | 28 | 11 | 12 |