diff --git a/520ApkBox/.gitignore b/520ApkBox-NewBlackbox/.gitignore similarity index 100% rename from 520ApkBox/.gitignore rename to 520ApkBox-NewBlackbox/.gitignore diff --git a/520ApkBox/BCore/black-fake/.gitignore b/520ApkBox-NewBlackbox/Bcore/.gitignore similarity index 100% rename from 520ApkBox/BCore/black-fake/.gitignore rename to 520ApkBox-NewBlackbox/Bcore/.gitignore diff --git a/520ApkBox-NewBlackbox/Bcore/build.gradle.kts b/520ApkBox-NewBlackbox/Bcore/build.gradle.kts new file mode 100644 index 0000000..3e45a20 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/build.gradle.kts @@ -0,0 +1,94 @@ +plugins { + id("com.android.library") + id("org.jetbrains.kotlin.android") +} + +android { + + namespace = "com.vcore" + compileSdk = (rootProject.ext["compileSdk"] as Int) + + + defaultConfig { + minSdk = (rootProject.ext["minSdk"] as Int) + consumerProguardFiles("consumer-rules.pro") + vectorDrawables { + useSupportLibrary = true + } + + ndk.apply{ + abiFilters.add("armeabi-v7a") + abiFilters.add("arm64-v8a") + } + // signingConfig = signingConfigs.getByName("debug") + + } + val cmake = rootProject.ext["cmakeVersion"] as String + externalNativeBuild { + cmake { + path = file("src/main/cpp/CMakeLists.txt") + version = cmake + } + } + + buildTypes { + release { + isMinifyEnabled = false //not tested yet + proguardFiles( + getDefaultProguardFile("proguard-android-optimize.txt"), + "proguard-rules.pro" + ) + } + debug { + isMinifyEnabled = false + proguardFiles( + getDefaultProguardFile("proguard-android-optimize.txt"), + "proguard-rules.pro" + ) + } + } + compileOptions { + sourceCompatibility = JavaVersion.VERSION_17 + targetCompatibility = JavaVersion.VERSION_17 + } + kotlinOptions { + jvmTarget = "17" + } + buildFeatures{ + aidl = true + prefab = true + viewBinding = true + } + + packagingOptions.apply { + jniLibs { + // 排除所有其他文件模式 + excludes.add("**/libshadowhook.so") + } + } + +} + +// it make update dependency update easy +val ktxversion = "1.13.1" +val stdlib_version = "1.9.24" +val hiddenapibypass = "4.3" +val xcrashversion = "3.1.0" +val shadowhook = "1.0.9" +val googlematerial = "1.12.0" + + +dependencies { + implementation("androidx.appcompat:appcompat") { + exclude(group = "com.android.support", module = "support-compat") + } + implementation("androidx.core:core-ktx:$ktxversion") + implementation("org.jetbrains.kotlin:kotlin-stdlib-jdk7:$stdlib_version") + implementation ("com.iqiyi.xcrash:xcrash-android-lib:$xcrashversion") + implementation("com.google.android.material:material:$googlematerial") + implementation ("org.lsposed.hiddenapibypass:hiddenapibypass:$hiddenapibypass") + implementation("com.bytedance.android:shadowhook:$shadowhook") + implementation ("top.canyie.pine:core:0.2.9") + implementation ("top.canyie.pine:xposed:0.1.0") + +} \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/consumer-rules.pro b/520ApkBox-NewBlackbox/Bcore/consumer-rules.pro new file mode 100644 index 0000000..f46cc03 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/consumer-rules.pro @@ -0,0 +1,5 @@ + +-keep class com.vcore.** {*; } +-keep class black.** {*; } +-keep class android.** {*; } +-keep class com.android.** {*; } \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/proguard-rules.pro b/520ApkBox-NewBlackbox/Bcore/proguard-rules.pro new file mode 100644 index 0000000..8bdd86e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/proguard-rules.pro @@ -0,0 +1,5 @@ + +-keep class com.vcore.** {*; } +-keep class black.** {*; } +-keep class android.** {*; } +-keep class com.android.** {*; } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/AndroidManifest.xml b/520ApkBox-NewBlackbox/Bcore/src/main/AndroidManifest.xml new file mode 100644 index 0000000..b2faeef --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/AndroidManifest.xml @@ -0,0 +1,2457 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/520ApkBox/android-mirror/src/main/aidl/android/accounts/IAccountAuthenticator.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticator.aidl similarity index 80% rename from 520ApkBox/android-mirror/src/main/aidl/android/accounts/IAccountAuthenticator.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticator.aidl index fe5c9ea..7d19a1f 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/accounts/IAccountAuthenticator.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticator.aidl @@ -1,19 +1,3 @@ -/* - * Copyright (C) 2009 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - package android.accounts; import android.accounts.IAccountAuthenticatorResponse; diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticatorResponse.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticatorResponse.aidl new file mode 100644 index 0000000..5de0175 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountAuthenticatorResponse.aidl @@ -0,0 +1,11 @@ +package android.accounts; +import android.os.Bundle; + +/** + * The interface used to return responses from an {@link IAccountAuthenticator} + */ +interface IAccountAuthenticatorResponse { + void onResult(in Bundle value); + void onRequestContinued(); + void onError(int errorCode, String errorMessage); +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/accounts/IAccountManagerResponse.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountManagerResponse.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/accounts/IAccountManagerResponse.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/accounts/IAccountManagerResponse.aidl diff --git a/520ApkBox/android-mirror/src/main/aidl/android/app/IActivityManager/ContentProviderHolder.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IActivityManager/ContentProviderHolder.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/app/IActivityManager/ContentProviderHolder.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IActivityManager/ContentProviderHolder.aidl diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IServiceConnection.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IServiceConnection.aidl new file mode 100644 index 0000000..9cf84c8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IServiceConnection.aidl @@ -0,0 +1,8 @@ +package android.app; + +import android.content.ComponentName; + +/** @hide */ +interface IServiceConnection { + void connected(in ComponentName name, IBinder service); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IStopUserCallback.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IStopUserCallback.aidl new file mode 100644 index 0000000..a6f1cc0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IStopUserCallback.aidl @@ -0,0 +1,10 @@ +package android.app; + +/** + * Callback to find out when we have finished stopping a user. + * {@hide} + */ +interface IStopUserCallback { + void userStopped(int userId); + void userStopAborted(int userId); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IWallpaperManagerCallback.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IWallpaperManagerCallback.aidl new file mode 100644 index 0000000..19ac832 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/IWallpaperManagerCallback.aidl @@ -0,0 +1,6 @@ +package android.app; + +/** @hide */ +interface IWallpaperManagerCallback { + void onWallpaperChanged(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/IJobCallback.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/IJobCallback.aidl new file mode 100644 index 0000000..6512138 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/IJobCallback.aidl @@ -0,0 +1,46 @@ +package android.app.job; + +import android.app.job.JobWorkItem; + +/** + * The server side of the JobScheduler IPC protocols. The app-side implementation + * invokes on this interface to indicate completion of the (asynchronous) instructions + * issued by the server. + * + * In all cases, the 'who' parameter is the caller's service binder, used to track + * which Job Service instance is reporting. + * + */ +interface IJobCallback { + /** + * Immediate callback to the system after sending a start signal, used to quickly detect ANR. + * + * @param jobId Unique integer used to identify this job. + * @param ongoing True to indicate that the client is processing the job. False if the job is + * complete + */ + void acknowledgeStartMessage(int jobId, boolean ongoing); + /** + * Immediate callback to the system after sending a stop signal, used to quickly detect ANR. + * + * @param jobId Unique integer used to identify this job. + * @param reschedule Whether or not to reschedule this job. + */ + void acknowledgeStopMessage(int jobId, boolean reschedule); + /* + * Called to deqeue next work item for the job. + */ + JobWorkItem dequeueWork(int jobId); + /* + * Called to report that job has completed processing a work item. + */ + boolean completeWork(int jobId, int workId); + /* + * Tell the job manager that the client is done with its execution, so that it can go on to + * the next one and stop attributing wakelock time to us etc. + * + * @param jobId Unique integer used to identify this job. + * @param reschedule Whether or not to reschedule this job. + */ + void jobFinished(int jobId, boolean reschedule); +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/app/job/IJobService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/IJobService.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/app/job/IJobService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/IJobService.aidl diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/JobWorkItem.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/JobWorkItem.aidl new file mode 100644 index 0000000..05f3cf9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/app/job/JobWorkItem.aidl @@ -0,0 +1,4 @@ +// JobWorkItem.aidl +package android.app.job; + +parcelable JobWorkItem; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/IIntentReceiver.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/IIntentReceiver.aidl new file mode 100644 index 0000000..2c9949d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/IIntentReceiver.aidl @@ -0,0 +1,15 @@ +package android.content; + +import android.content.Intent; +import android.os.Bundle; + +/** + * System private API for dispatching intent broadcasts. This is given to the + * activity manager as part of registering for an intent broadcasts, and is + * called when it receives intents. + * + */ +interface IIntentReceiver { + void performReceive(in Intent intent, int resultCode, String data, + in Bundle extras, boolean ordered, boolean sticky, int sendingUser); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncAdapter.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncAdapter.aidl new file mode 100644 index 0000000..8ca515c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncAdapter.aidl @@ -0,0 +1,38 @@ +package android.content; + +import android.accounts.Account; +import android.os.Bundle; +import android.content.ISyncContext; + +/** + * Interface used to control the sync activity on a SyncAdapter + */ +interface ISyncAdapter { + /** + * Initiate a sync for this account. SyncAdapter-specific parameters may + * be specified in extras, which is guaranteed to not be null. + * + * @param syncContext the ISyncContext used to indicate the progress of the sync. When + * the sync is finished (successfully or not) ISyncContext.onFinished() must be called. + * @param authority the authority that should be synced + * @param account the account that should be synced + * @param extras SyncAdapter-specific parameters + */ + void startSync(ISyncContext syncContext, String authority, + in Account account, in Bundle extras); + + /** + * Cancel the most recently initiated sync. Due to race conditions, this may arrive + * after the ISyncContext.onFinished() for that sync was called. + * @param syncContext the ISyncContext that was passed to {@link #startSync} + */ + void cancelSync(ISyncContext syncContext); + + /** + * Initialize the SyncAdapter for this account and authority. + * + * @param account the account that should be synced + * @param authority the authority that should be synced + */ + void initialize(in Account account, String authority); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncContext.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncContext.aidl new file mode 100644 index 0000000..a1b4460 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncContext.aidl @@ -0,0 +1,22 @@ +package android.content; + +import android.content.SyncResult; + +/** + * Interface used by the SyncAdapter to indicate its progress. + * @hide + */ +interface ISyncContext { + /** + * Call to indicate that the SyncAdapter is making progress. E.g., if this SyncAdapter + * downloads or sends records to/from the server, this may be called after each record + * is downloaded or uploaded. + */ + void sendHeartbeat(); + + /** + * Signal that the corresponding sync session is completed. + * @param result information about this sync session + */ + void onFinished(in SyncResult result); +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/ISyncStatusObserver.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncStatusObserver.aidl similarity index 98% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/ISyncStatusObserver.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncStatusObserver.aidl index 88ea23a..9c718c9 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/content/ISyncStatusObserver.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/ISyncStatusObserver.aidl @@ -1,6 +1,5 @@ package android.content; - interface ISyncStatusObserver { void onStatusChanged(int which); } diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/SyncStatusInfo.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/SyncStatusInfo.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/SyncStatusInfo.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/SyncStatusInfo.aidl diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageDataObserver.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageDataObserver.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageDataObserver.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageDataObserver.aidl diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageDeleteObserver2.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageDeleteObserver2.aidl new file mode 100644 index 0000000..5e829d7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageDeleteObserver2.aidl @@ -0,0 +1,8 @@ +package android.content.pm; + +import android.content.Intent; + +interface IPackageDeleteObserver2 { + void onUserActionRequired(in Intent intent); + void onPackageDeleted(String packageName, int returnCode, String msg); +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl similarity index 99% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl index 4ec7d4b..7b82182 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver.aidl @@ -6,4 +6,3 @@ package android.content.pm; interface IPackageInstallObserver { void packageInstalled(in String packageName, int returnCode); } - diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver2.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver2.aidl new file mode 100644 index 0000000..696ed12 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallObserver2.aidl @@ -0,0 +1,29 @@ +package android.content.pm; + +import android.content.Intent; +import android.os.Bundle; + +/** + * API for installation callbacks from the Package Manager. In certain result cases + * additional information will be provided. + */ +interface IPackageInstallObserver2 { + void onUserActionRequired(in Intent intent); + + /** + * The install operation has completed. {@code returnCode} holds a numeric code + * indicating success or failure. In certain cases the {@code extras} Bundle will + * contain additional details: + * + *

+ * + * + * + * + *
INSTALL_FAILED_DUPLICATE_PERMISSIONTwo strings are provided in the extras bundle: EXTRA_EXISTING_PERMISSION + * is the name of the permission that the app is attempting to define, and + * EXTRA_EXISTING_PACKAGE is the package name of the app which has already + * defined the permission.
+ */ + void onPackageInstalled(String basePackageName, int returnCode, String msg, in Bundle extras); +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallerCallback.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallerCallback.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallerCallback.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallerCallback.aidl diff --git a/520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallerSession.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallerSession.aidl similarity index 100% rename from 520ApkBox/android-mirror/src/main/aidl/android/content/pm/IPackageInstallerSession.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/content/pm/IPackageInstallerSession.aidl diff --git a/520ApkBox/android-mirror/src/main/aidl/android/database/IContentObserver.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/database/IContentObserver.aidl similarity index 92% rename from 520ApkBox/android-mirror/src/main/aidl/android/database/IContentObserver.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/database/IContentObserver.aidl index e395dc7..01b116d 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/database/IContentObserver.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/database/IContentObserver.aidl @@ -2,8 +2,7 @@ package android.database; import android.net.Uri; -interface IContentObserver -{ +interface IContentObserver { /** * This method is called when an update occurs to the cursor that is being * observed. selfUpdate is true if the update was caused by a call to diff --git a/520ApkBox/android-mirror/src/main/aidl/android/location/ILocationListener.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/location/ILocationListener.aidl similarity index 91% rename from 520ApkBox/android-mirror/src/main/aidl/android/location/ILocationListener.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/location/ILocationListener.aidl index 1571ae2..1d4ffcb 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/location/ILocationListener.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/location/ILocationListener.aidl @@ -4,10 +4,9 @@ package android.location; import android.location.Location; import android.os.Bundle; -interface ILocationListener -{ +interface ILocationListener { void onLocationChanged(in Location location); void onStatusChanged(String provider, int status, in Bundle extras); void onProviderEnabled(String provider); void onProviderDisabled(String provider); -} \ No newline at end of file +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/net/IConnectivityManager.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/IConnectivityManager.aidl similarity index 92% rename from 520ApkBox/android-mirror/src/main/aidl/android/net/IConnectivityManager.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/IConnectivityManager.aidl index b60a420..dea1546 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/net/IConnectivityManager.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/IConnectivityManager.aidl @@ -4,7 +4,7 @@ import android.net.NetworkInfo; import android.net.LinkProperties; interface IConnectivityManager { -NetworkInfo getActiveNetworkInfo(); + NetworkInfo getActiveNetworkInfo(); NetworkInfo getActiveNetworkInfoForUid(int uid, boolean ignoreBlocked); NetworkInfo getNetworkInfo(int networkType); @@ -13,4 +13,4 @@ NetworkInfo getActiveNetworkInfo(); boolean requestRouteToHostAddress(int networkType, int address); LinkProperties getActiveLinkProperties(); LinkProperties getLinkProperties(int networkType); -} \ No newline at end of file +} diff --git a/520ApkBox/android-mirror/src/main/aidl/android/net/wifi/IWifiScanner.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/wifi/IWifiScanner.aidl similarity index 85% rename from 520ApkBox/android-mirror/src/main/aidl/android/net/wifi/IWifiScanner.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/wifi/IWifiScanner.aidl index 3e71a5f..5d654b8 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/net/wifi/IWifiScanner.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/net/wifi/IWifiScanner.aidl @@ -3,9 +3,7 @@ package android.net.wifi; import android.os.Messenger; import android.os.Bundle; -interface IWifiScanner -{ +interface IWifiScanner { Messenger getMessenger(); - Bundle getAvailableChannels(int band); } diff --git a/520ApkBox/android-mirror/src/main/aidl/android/os/ISystemUpdateManager.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/os/ISystemUpdateManager.aidl similarity index 99% rename from 520ApkBox/android-mirror/src/main/aidl/android/os/ISystemUpdateManager.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/os/ISystemUpdateManager.aidl index cfce210..3ce3285 100644 --- a/520ApkBox/android-mirror/src/main/aidl/android/os/ISystemUpdateManager.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/android/os/ISystemUpdateManager.aidl @@ -6,4 +6,4 @@ import android.os.PersistableBundle; interface ISystemUpdateManager { Bundle retrieveSystemUpdateInfo(); void updateSystemUpdateInfo(in PersistableBundle data); -} \ No newline at end of file +} diff --git a/520ApkBox/android-mirror/src/main/aidl/com/android/internal/widget/ILockSettings.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/android/internal/widget/ILockSettings.aidl similarity index 98% rename from 520ApkBox/android-mirror/src/main/aidl/com/android/internal/widget/ILockSettings.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/android/internal/widget/ILockSettings.aidl index 7c725f8..6ebc673 100644 --- a/520ApkBox/android-mirror/src/main/aidl/com/android/internal/widget/ILockSettings.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/android/internal/widget/ILockSettings.aidl @@ -3,4 +3,4 @@ package com.android.internal.widget; interface ILockSettings { void setRecoverySecretTypes(in int[] secretTypes); int[] getRecoverySecretTypes(); -} \ No newline at end of file +} diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/IBActivityThread.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IBActivityThread.aidl similarity index 88% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/IBActivityThread.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IBActivityThread.aidl index 8e9530d..2704177 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/IBActivityThread.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IBActivityThread.aidl @@ -1,5 +1,5 @@ // IBActivityThread.aidl -package top.niunaijun.blackbox.core; +package com.vcore.core; // Declare any non-default types here with import statements @@ -9,7 +9,7 @@ import android.content.Intent; import java.util.List; import android.content.pm.ResolveInfo; import android.content.pm.ActivityInfo; -import top.niunaijun.blackbox.entity.am.ReceiverData; +import com.vcore.entity.am.ReceiverData; interface IBActivityThread { IBinder getActivityThread(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IEmpty.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IEmpty.aidl new file mode 100644 index 0000000..8ed4449 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/IEmpty.aidl @@ -0,0 +1,7 @@ +// IBActivityThread.aidl +package com.vcore.core; + +// Declare any non-default types here with import statements +interface IEmpty { + +} diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/accounts/IBAccountManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/accounts/IBAccountManagerService.aidl similarity index 92% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/accounts/IBAccountManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/accounts/IBAccountManagerService.aidl index f2f577a..ae7af25 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/accounts/IBAccountManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/accounts/IBAccountManagerService.aidl @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.accounts; +package com.vcore.core.system.accounts; import android.accounts.IAccountManagerResponse; import android.accounts.Account; @@ -10,7 +10,6 @@ import android.os.UserHandle; import java.util.Map; - interface IBAccountManagerService { String getPassword(in Account account, int userId); String getUserData(in Account account, String key, int userId); @@ -68,10 +67,10 @@ interface IBAccountManagerService { void unregisterAccountListener(in String[] accountTypes, String opPackageName, int userId); /* Check if the package in a user can access an account */ -// boolean hasAccountAccess(in Account account, String packageName, in UserHandle userHandle); + // boolean hasAccountAccess(in Account account, String packageName, in UserHandle userHandle); /* Crate an intent to request account access for package and a given user id */ -// IntentSender createRequestAccountAccessIntentSenderAsUser(in Account account, -// String packageName, in UserHandle userHandle); + // IntentSender createRequestAccountAccessIntentSenderAsUser(in Account account, + // String packageName, in UserHandle userHandle); -// void onAccountAccessed(String token); + // void onAccountAccessed(String token); } diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBActivityManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBActivityManagerService.aidl similarity index 84% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBActivityManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBActivityManagerService.aidl index 5c7245e..d1c08f4 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBActivityManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBActivityManagerService.aidl @@ -1,5 +1,5 @@ // IBActivityManagerService.aidl -package top.niunaijun.blackbox.core.system.am; +package com.vcore.core.system.am; import android.content.Intent; import android.content.ComponentName; @@ -8,15 +8,14 @@ import android.content.pm.ProviderInfo; import android.os.IBinder; import java.lang.String; import android.app.IServiceConnection; -import top.niunaijun.blackbox.entity.AppConfig; -import top.niunaijun.blackbox.entity.UnbindRecord; +import com.vcore.entity.AppConfig; +import com.vcore.entity.UnbindRecord; import android.os.Bundle; -import top.niunaijun.blackbox.entity.am.RunningAppProcessInfo; -import top.niunaijun.blackbox.entity.am.PendingResultData; -import top.niunaijun.blackbox.entity.am.RunningServiceInfo; +import com.vcore.entity.am.RunningAppProcessInfo; +import com.vcore.entity.am.PendingResultData; +import com.vcore.entity.am.RunningServiceInfo; // Declare any non-default types here with import statements - interface IBActivityManagerService { AppConfig initProcess(String packageName, String processName, int userId); void restartProcess(String packageName, String processName, int userId); @@ -33,7 +32,6 @@ interface IBActivityManagerService { void stopServiceToken(in ComponentName className, in IBinder token, int userId); - void onStartCommand(in Intent proxyIntent, int userId); UnbindRecord onServiceUnbind(in Intent proxyIntent, int userId); void onServiceDestroy(in Intent proxyIntent, int userId); @@ -41,7 +39,7 @@ interface IBActivityManagerService { Intent sendBroadcast(in Intent intent, String resolvedType, int userId); IBinder peekService(in Intent intent, String resolvedType, int userId); - void onActivityCreated(int taskId, IBinder token, IBinder activityRecord); + void onActivityCreated(int taskId, IBinder token, String activityToken); void onActivityResumed(IBinder token); void onActivityDestroyed(IBinder token); void onFinishActivity(IBinder token); diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBJobManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBJobManagerService.aidl similarity index 84% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBJobManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBJobManagerService.aidl index 97d9b36..9fd9b29 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/am/IBJobManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/am/IBJobManagerService.aidl @@ -1,19 +1,17 @@ // IBJobManagerService.aidl -package top.niunaijun.blackbox.core.system.am; +package com.vcore.core.system.am; import android.content.Intent; import android.content.ComponentName; import android.os.IBinder; import java.lang.String; import android.app.job.JobInfo; -import top.niunaijun.blackbox.entity.JobRecord; +import com.vcore.entity.JobRecord; // Declare any non-default types here with import statements - interface IBJobManagerService { JobInfo schedule(in JobInfo info, int userId); JobRecord queryJobRecord(String processName, int jobId, int userId); void cancelAll(String processName, int userId); int cancel(String processName, int jobId, int userId); - } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/device/IDeviceManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/device/IDeviceManagerService.aidl new file mode 100644 index 0000000..c4efcea --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/device/IDeviceManagerService.aidl @@ -0,0 +1,12 @@ +// IDeviceManagerService.aidl +package com.vcore.core.system.device; + +// Declare any non-default types here with import statements +interface IDeviceManagerService { + /** + * Demonstrates some basic types that you can use as parameters + * and return values in AIDL. + */ + void basicTypes(int anInt, long aLong, boolean aBoolean, float aFloat, + double aDouble, String aString); +} \ No newline at end of file diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/location/IBLocationManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/location/IBLocationManagerService.aidl similarity index 86% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/location/IBLocationManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/location/IBLocationManagerService.aidl index a7de050..34304b6 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/location/IBLocationManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/location/IBLocationManagerService.aidl @@ -1,12 +1,11 @@ // IFakeLocationManager.aidl -package top.niunaijun.blackbox.core.system.location; +package com.vcore.core.system.location; -import top.niunaijun.blackbox.entity.location.BLocation; -import top.niunaijun.blackbox.entity.location.BCell; +import com.vcore.entity.location.BLocation; +import com.vcore.entity.location.BCell; import java.util.List; - interface IBLocationManagerService { int getPattern(int userId, String pkg); diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/notification/IBNotificationManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/notification/IBNotificationManagerService.aidl similarity index 94% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/notification/IBNotificationManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/notification/IBNotificationManagerService.aidl index 8de080d..52f4bb8 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/notification/IBNotificationManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/notification/IBNotificationManagerService.aidl @@ -1,5 +1,5 @@ // IBNotificationManagerService.aidl -package top.niunaijun.blackbox.core.system.notification; +package com.vcore.core.system.notification; // Declare any non-default types here with import statements import android.app.Notification; @@ -7,7 +7,6 @@ import android.app.NotificationChannel; import android.app.NotificationChannelGroup; interface IBNotificationManagerService { - NotificationChannel getNotificationChannel(String channelId, int userId); List getNotificationChannels(String packageName, int userId); diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/os/IBStorageManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/os/IBStorageManagerService.aidl similarity index 87% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/os/IBStorageManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/os/IBStorageManagerService.aidl index 8b9e915..d97fc6b 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/os/IBStorageManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/os/IBStorageManagerService.aidl @@ -1,12 +1,11 @@ // IBStorageManagerService.aidl -package top.niunaijun.blackbox.core.system.os; +package com.vcore.core.system.os; import android.os.storage.StorageVolume; import java.lang.String; import android.net.Uri; // Declare any non-default types here with import statements - interface IBStorageManagerService { StorageVolume[] getVolumeList(int uid, String packageName, int flags, int userId); Uri getUriForFile(String file); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/BPackageSettings.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/BPackageSettings.aidl new file mode 100644 index 0000000..21ff1bc --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/BPackageSettings.aidl @@ -0,0 +1,5 @@ +// BPackageSettings.aidl +package com.vcore.core.system.pm; + +// Declare any non-default types here with import statements +parcelable BPackageSettings; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageInstallerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageInstallerService.aidl new file mode 100644 index 0000000..c109597 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageInstallerService.aidl @@ -0,0 +1,13 @@ +// IBPackageInstallerService.aidl +package com.vcore.core.system.pm; + +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; + +// Declare any non-default types here with import statements +interface IBPackageInstallerService { + int installPackageAsUser(in BPackageSettings ps, int userId); + int uninstallPackageAsUser(in BPackageSettings ps, boolean removeApp, int userId); + int clearPackage(in BPackageSettings ps, int userId); + int updatePackage(in BPackageSettings ps); +} diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBPackageManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageManagerService.aidl similarity index 91% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBPackageManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageManagerService.aidl index 1613405..05c73d5 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBPackageManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBPackageManagerService.aidl @@ -1,5 +1,5 @@ // IBPackageManagerService.aidl -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; // Declare any non-default types here with import statements import android.content.pm.ApplicationInfo; @@ -11,12 +11,13 @@ import android.content.pm.ProviderInfo; import android.content.Intent; import android.content.ComponentName; import java.util.List; -import top.niunaijun.blackbox.entity.pm.InstallResult; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.entity.pm.InstalledPackage; - +import com.vcore.entity.pm.InstallResult; +import com.vcore.entity.pm.InstallOption; +import com.vcore.entity.pm.InstalledPackage; interface IBPackageManagerService { + int getUidByPid(int pid); + ResolveInfo resolveService(in Intent intent, int flags, String resolvedType, int userId); ResolveInfo resolveActivity(in Intent intent, int flags, String resolvedType, int userId); ProviderInfo resolveContentProvider(String authority, int flag, int userId); diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBXposedManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBXposedManagerService.aidl similarity index 75% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBXposedManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBXposedManagerService.aidl index 86fa504..9196275 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/pm/IBXposedManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/pm/IBXposedManagerService.aidl @@ -1,9 +1,9 @@ // IBXposedManagerService.aidl -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import java.util.List; -import top.niunaijun.blackbox.entity.pm.InstalledModule; +import com.vcore.entity.pm.InstalledModule; interface IBXposedManagerService { boolean isXPEnable(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/BUserInfo.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/BUserInfo.aidl new file mode 100644 index 0000000..042c01a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/BUserInfo.aidl @@ -0,0 +1,5 @@ +// BUserInfo.aidl +package com.vcore.core.system.user; + +// Declare any non-default types here with import statements +parcelable BUserInfo; diff --git a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/user/IBUserManagerService.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/IBUserManagerService.aidl similarity index 75% rename from 520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/user/IBUserManagerService.aidl rename to 520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/IBUserManagerService.aidl index 896e865..d5f7fbb 100644 --- a/520ApkBox/Bcore/src/main/aidl/top/niunaijun/blackbox/core/system/user/IBUserManagerService.aidl +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/core/system/user/IBUserManagerService.aidl @@ -1,11 +1,10 @@ // IBUserManagerService.aidl -package top.niunaijun.blackbox.core.system.user; +package com.vcore.core.system.user; // Declare any non-default types here with import statements -import top.niunaijun.blackbox.core.system.user.BUserInfo; +import com.vcore.core.system.user.BUserInfo; import java.util.List; - interface IBUserManagerService { BUserInfo getUserInfo(int userId); boolean exists(int userId); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/AppConfig.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/AppConfig.aidl new file mode 100644 index 0000000..4ecff2f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/AppConfig.aidl @@ -0,0 +1,5 @@ +// AppConfig.aidl +package com.vcore.entity; + +// Declare any non-default types here with import statements +parcelable AppConfig; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/JobRecord.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/JobRecord.aidl new file mode 100644 index 0000000..4884e8a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/JobRecord.aidl @@ -0,0 +1,5 @@ +// JobRecord.aidl +package com.vcore.entity; + +// Declare any non-default types here with import statements +parcelable JobRecord; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/UnbindRecord.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/UnbindRecord.aidl new file mode 100644 index 0000000..f105d4e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/UnbindRecord.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity; + +parcelable UnbindRecord; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/PendingResultData.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/PendingResultData.aidl new file mode 100644 index 0000000..f3884e1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/PendingResultData.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.am; + +parcelable PendingResultData; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/ReceiverData.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/ReceiverData.aidl new file mode 100644 index 0000000..06f2a97 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/ReceiverData.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.am; + +parcelable ReceiverData; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningAppProcessInfo.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningAppProcessInfo.aidl new file mode 100644 index 0000000..07af8a4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningAppProcessInfo.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.am; + +parcelable RunningAppProcessInfo; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningServiceInfo.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningServiceInfo.aidl new file mode 100644 index 0000000..76c918f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/am/RunningServiceInfo.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.am; + +parcelable RunningServiceInfo; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/device/BDeviceConfig.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/device/BDeviceConfig.aidl new file mode 100644 index 0000000..38a47b9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/device/BDeviceConfig.aidl @@ -0,0 +1,5 @@ +// BDeviceConfig.aidl +package com.vcore.entity.device; + +// Declare any non-default types here with import statements +parcelable BDeviceConfig; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BCell.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BCell.aidl new file mode 100644 index 0000000..05c4f71 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BCell.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.location; + +parcelable BCell; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocation.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocation.aidl new file mode 100644 index 0000000..9d22312 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocation.aidl @@ -0,0 +1,4 @@ +package com.vcore.entity.location; + +// Declare any non-default types here with import statements +parcelable BLocation; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocationConfig.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocationConfig.aidl new file mode 100644 index 0000000..133d461 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/location/BLocationConfig.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.location; + +parcelable BLocationConfig; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallOption.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallOption.aidl new file mode 100644 index 0000000..bf2f7f4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallOption.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.pm; + +parcelable InstallOption; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallResult.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallResult.aidl new file mode 100644 index 0000000..7901163 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstallResult.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.pm; + +parcelable InstallResult; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledModule.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledModule.aidl new file mode 100644 index 0000000..d3ed2e0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledModule.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.pm; + +parcelable InstalledModule; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledPackage.aidl b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledPackage.aidl new file mode 100644 index 0000000..26710de --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/aidl/com/vcore/entity/pm/InstalledPackage.aidl @@ -0,0 +1,3 @@ +package com.vcore.entity.pm; + +parcelable InstalledPackage; \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.cpp new file mode 100644 index 0000000..023708c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.cpp @@ -0,0 +1,143 @@ +#define CORE_CLASS "com/vcore/core/NativeCore" +#include "BoxCore.h" +#include "Log.h" +#include "IO.h" +#include +#include "JniHook/JniHook.h" +#include "Hook/VMClassLoaderHook.h" +#include "Hook/UnixFileSystemHook.h" +#include "Hook/LinuxHook.h" +#include "Hook/SystemPropertiesHook.h" +#include "Hook/BinderHook.h" +#include "Hook/RuntimeHook.h" + + + +struct { + JavaVM *vm; + jclass NativeCoreClass; + jmethodID getCallingUidId; + jmethodID redirectPathString; + jmethodID redirectPathFile; + int api_level; +} VMEnv; + +JNIEnv *getEnv() { + JNIEnv *env; + VMEnv.vm->GetEnv(reinterpret_cast(&env), JNI_VERSION_1_6); + return env; +} + +JNIEnv *ensureEnvCreated() { + JNIEnv *env = getEnv(); + if (env == nullptr) { + VMEnv.vm->AttachCurrentThread(&env, nullptr); + } + return env; +} + +int BoxCore::getCallingUid(int orig) { + JNIEnv *env = ensureEnvCreated(); + return env->CallStaticIntMethod(VMEnv.NativeCoreClass, VMEnv.getCallingUidId, orig); +} + +jstring BoxCore::redirectPathString(JNIEnv *env, jstring path) { + env = ensureEnvCreated(); + return (jstring) env->CallStaticObjectMethod(VMEnv.NativeCoreClass, VMEnv.redirectPathString, path); +} + +jobject BoxCore::redirectPathFile(JNIEnv *env, jobject path) { + env = ensureEnvCreated(); + return env->CallStaticObjectMethod(VMEnv.NativeCoreClass, VMEnv.redirectPathFile, path); +} + +int BoxCore::getApiLevel() { + return VMEnv.api_level; +} + +JavaVM *BoxCore::getJavaVM() { + return VMEnv.vm; +} + +void nativeHook(JNIEnv *env) { + BaseHook::init(env); + UnixFileSystemHook::init(env); + LinuxHook::init(env); + VMClassLoaderHook::init(env); + + // SystemPropertiesHook会引起小米k40,安卓11上的抖音崩溃 + // SystemPropertiesHook::init(env); + RuntimeHook::init(env); + BinderHook::init(env); +} + +void hideXposed(JNIEnv *env, jclass clazz) { + ALOGD("Hiding Xposed!"); + VMClassLoaderHook::hideXposed(); +} + +void init(JNIEnv *env, jobject clazz, jint api_level) { + ALOGD("NativeCore init."); + VMEnv.api_level = api_level; + VMEnv.NativeCoreClass = (jclass) env->NewGlobalRef(env->FindClass(CORE_CLASS)); + VMEnv.getCallingUidId = env->GetStaticMethodID(VMEnv.NativeCoreClass, "getCallingUid", "(I)I"); + VMEnv.redirectPathString = env->GetStaticMethodID(VMEnv.NativeCoreClass, "redirectPath", "(Ljava/lang/String;)Ljava/lang/String;"); + VMEnv.redirectPathFile = env->GetStaticMethodID(VMEnv.NativeCoreClass, "redirectPath", "(Ljava/io/File;)Ljava/io/File;"); + JniHook::InitJniHook(env, api_level); +} + +// IO类添加重定向规则 +void addIORule(JNIEnv *env, jclass clazz, jstring target_path, jstring relocate_path) { + IO::addRule(env->GetStringUTFChars(target_path, JNI_FALSE),env->GetStringUTFChars(relocate_path, JNI_FALSE)); +} + +// IO类添加白名单规则 +void addWhiteList(JNIEnv *env, jclass clazz, jstring path) { + IO::addWhiteList(env->GetStringUTFChars(path, JNI_FALSE)); +} + +void enableIO(JNIEnv *env, jclass clazz) { + nativeHook(env); +} + +static JNINativeMethod gMethods[] = { + {"hideXposed", "()V", (void *) hideXposed}, + {"addIORule", "(Ljava/lang/String;Ljava/lang/String;)V", (void *) addIORule}, + {"enableIO", "()V", (void *) enableIO}, + {"init", "(I)V", (void *) init}, + {"addWhiteList", "(Ljava/lang/String;)V", (void *) addWhiteList}, +}; + +int registerNativeMethods(JNIEnv *env, const char *className,JNINativeMethod *gMethods, int numMethods) { + jclass clazz; + clazz = env->FindClass(className); + if (clazz == nullptr) { + return JNI_FALSE; + } + + if (env->RegisterNatives(clazz, gMethods, numMethods) < 0) { + return JNI_FALSE; + } + return JNI_TRUE; +} + +int registerNatives(JNIEnv *env) { + if (!registerNativeMethods(env, CORE_CLASS, gMethods, sizeof(gMethods) / sizeof(gMethods[0]))) { + return JNI_FALSE; + } + return JNI_TRUE; +} + +void registerMethod(JNIEnv *jenv) { + registerNatives(jenv); +} + +JNIEXPORT jint JNI_OnLoad(JavaVM *vm, void *reserved) { + JNIEnv *env; + VMEnv.vm = vm; + if (vm->GetEnv(reinterpret_cast(&env), JNI_VERSION_1_6) != JNI_OK) { + return JNI_EVERSION; + } + registerMethod(env); + return JNI_VERSION_1_6; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.h new file mode 100644 index 0000000..6069959 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/BoxCore.h @@ -0,0 +1,19 @@ +#ifndef BLACKBOX_BOXCORE_H +#define BLACKBOX_BOXCORE_H + +#include +#include + + +class BoxCore { +public: + static JavaVM *getJavaVM(); + static int getApiLevel(); + static int getCallingUid(int orig); + static jstring redirectPathString(JNIEnv *env, jstring path); + static jobject redirectPathFile(JNIEnv *env, jobject path); + static void replaceFD(JNIEnv *env, jobject fd); +}; + + +#endif // BLACKBOX_BOXCORE_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/CMakeLists.txt b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/CMakeLists.txt new file mode 100644 index 0000000..62ee679 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/CMakeLists.txt @@ -0,0 +1,54 @@ +# For more information about using CMake with Android Studio, read the +# documentation: https://d.android.com/studio/projects/add-native-code.html + +# Sets the minimum version of CMake required to build the native library. + +cmake_minimum_required(VERSION 3.4.1) +enable_language(ASM) +project(vcore) + +# Creates and names a library, sets it as either STATIC +# or SHARED, and provides the relative paths to its source code. +# You can define multiple libraries, and CMake builds them for you. +# Gradle automatically packages shared libraries with your APK. +include_directories(JniHook) +include_directories(./) +aux_source_directory(./ SRC1) +aux_source_directory(Hook SRC2) +aux_source_directory(JniHook SRC3) +add_compile_options(-w) + +add_library( # Sets the name of the library. + vcore + # Sets the library as a shared library. + SHARED + # Provides a relative path to your source file(s). + BoxCore.cpp + ${SRC1} + ${SRC2} + ${SRC3}) + +# Searches for a specified prebuilt library and stores the path as a +# variable. Because CMake includes system libraries in the search path by +# default, you only need to specify the name of the public NDK library +# you want to add. CMake verifies that the library exists before +# completing its build. + +find_library( # Sets the name of the path variable. + log-lib + + # Specifies the name of the NDK library that + # you want CMake to locate. + log) + +# Specifies libraries CMake should link to your target library. You +# can link multiple libraries, such as libraries you define in this +# build script, prebuilt third-party libraries, or system libraries. +find_package(shadowhook REQUIRED CONFIG) +target_link_libraries( # Specifies the target library. + vcore + # Links the target library to the log library + # included in the NDK. + ${log-lib} + z + shadowhook::shadowhook) \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.cpp new file mode 100644 index 0000000..e7e961a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.cpp @@ -0,0 +1,5 @@ +#include "BaseHook.h" + +void BaseHook::init(JNIEnv *env) { + +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.h new file mode 100644 index 0000000..6505bfb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BaseHook.h @@ -0,0 +1,12 @@ +#ifndef BLACKBOX_BASEHOOK_H +#define BLACKBOX_BASEHOOK_H + +#include +#include + +class BaseHook { +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_BASEHOOK_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.cpp new file mode 100644 index 0000000..1dd21a3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.cpp @@ -0,0 +1,15 @@ +#include "BinderHook.h" +#include +#include +#include "UnixFileSystemHook.h" +#import "JniHook/JniHook.h" + +HOOK_JNI(jint, getCallingUid, JNIEnv *env, jobject obj) { + int orig = orig_getCallingUid(env, obj); + return BoxCore::getCallingUid(orig); +} + +void BinderHook::init(JNIEnv *env) { + const char *clazz = "android/os/Binder"; + JniHook::HookJniFun(env, clazz, "getCallingUid", "()I", (void *) new_getCallingUid, (void **) (&orig_getCallingUid), true); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.h new file mode 100644 index 0000000..d9cb6ad --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/BinderHook.h @@ -0,0 +1,11 @@ +#ifndef BLACKBOX_BINDERHOOK_H +#define BLACKBOX_BINDERHOOK_H + +#include "BaseHook.h" + +class BinderHook : public BaseHook{ +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_BINDERHOOK_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.cpp new file mode 100644 index 0000000..7b3150a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.cpp @@ -0,0 +1,189 @@ +#include "LinuxHook.h" +#import "JniHook/JniHook.h" +#include "IO.h" + +HOOK_JNI(jboolean, access, JNIEnv *env, jobject obj, jstring path, jint mode) { + jstring redirect = IO::redirectPath(env, path); + return orig_access(env, obj, redirect, mode); +} + +HOOK_JNI(void, chmod, JNIEnv *env, jobject obj, jstring path, jint mode) { + jstring redirect = IO::redirectPath(env, path); + return orig_chmod(env, obj, redirect, mode); +} + +HOOK_JNI(void, chown, JNIEnv *env, jobject obj, jstring path, jint mode, jint gid) { + jstring redirect = IO::redirectPath(env, path); + return orig_chown(env, obj, redirect, mode, gid); +} + +HOOK_JNI(void, execv, JNIEnv *env, jobject obj, jstring filename, jobjectArray argv) { + jstring redirect = IO::redirectPath(env, filename); + return orig_execv(env, obj, redirect, argv); +} + +HOOK_JNI(void, execve, JNIEnv *env, jobject obj, jstring filename, jobjectArray argv, jobjectArray envp) { + jstring redirect = IO::redirectPath(env, filename); + return orig_execve(env, obj, redirect, argv, envp); +} + +HOOK_JNI(jbyteArray, getxattr, JNIEnv *env, jobject obj, jstring path, jstring name) { + jstring redirect = IO::redirectPath(env, path); + return orig_getxattr(env, obj, redirect, name); +} + +HOOK_JNI(void, lchown, JNIEnv *env, jobject obj, jstring path, jint uid, jint gid) { + jstring redirect = IO::redirectPath(env, path); + return orig_lchown(env, obj, redirect, uid, gid); +} + +HOOK_JNI(void, link, JNIEnv *env, jobject obj, jstring oldPath, jstring newPath) { + jstring redirectOldPath = IO::redirectPath(env, oldPath); + jstring redirectNewPath = IO::redirectPath(env, newPath); + return orig_link(env, obj, redirectOldPath, redirectNewPath); +} + +HOOK_JNI(jobjectArray, listxattr, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_listxattr(env, obj, redirect); +} + +HOOK_JNI(jobject, lstat, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_lstat(env, obj, redirect); +} + +HOOK_JNI(void, mkdir, JNIEnv *env, jobject obj, jstring path, jint mode) { + jstring redirect = IO::redirectPath(env, path); + return orig_mkdir(env, obj, redirect, mode); +} + +HOOK_JNI(void, mkfifo, JNIEnv *env, jobject obj, jstring path, jint mode) { + jstring redirect = IO::redirectPath(env, path); + return orig_mkfifo(env, obj, redirect, mode); +} + +HOOK_JNI(jobject, open, JNIEnv *env, jobject obj, jstring path, jint flags, jint mode) { + jstring redirect = IO::redirectPath(env, path); + return orig_open(env, obj, redirect, flags, mode); +} + +HOOK_JNI(jstring, readlink, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_readlink(env, obj, redirect); +} + +HOOK_JNI(jstring, realpath, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_realpath(env, obj, redirect); +} + +HOOK_JNI(void, remove, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_remove(env, obj, redirect); +} + +HOOK_JNI(void, removexattr, JNIEnv *env, jobject obj, jstring path, jstring name) { + jstring redirect = IO::redirectPath(env, path); + return orig_removexattr(env, obj, redirect, name); +} + +HOOK_JNI(void, rename, JNIEnv *env, jobject obj, jstring oldPath, jstring newPath) { + jstring redirectOldPath = IO::redirectPath(env, oldPath); + jstring redirectNewPath = IO::redirectPath(env, newPath); + return orig_rename(env, obj, redirectOldPath, redirectNewPath); +} + +HOOK_JNI(void, setxattr, JNIEnv *env, jobject obj, jstring path, jstring name, jbyteArray value, jint flags) { + jstring redirect = IO::redirectPath(env, path); + return orig_setxattr(env, obj, redirect, name, value, flags); +} + +HOOK_JNI(jobject, stat, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_stat(env, obj, redirect); +} + +HOOK_JNI(jobject, statvfs, JNIEnv *env, jobject obj, jstring path) { + jstring redirect = IO::redirectPath(env, path); + return orig_statvfs(env, obj, redirect); +} + +HOOK_JNI(void, symlink, JNIEnv *env, jobject obj, jstring oldPath, jstring newPath) { + jstring redirectOldPath = IO::redirectPath(env, oldPath); + jstring redirectNewPath = IO::redirectPath(env, newPath); + return orig_symlink(env, obj, redirectOldPath, redirectNewPath); +} + +HOOK_JNI(void, unlink, JNIEnv *env, jobject obj, jstring pathname) { + jstring redirect = IO::redirectPath(env, pathname); + return orig_unlink(env, obj, redirect); +} + +void LinuxHook::init(JNIEnv *env) { + JniHook::HookJniFun(env, "libcore/io/Linux", "access", "(Ljava/lang/String;I)Z", + (void *) new_access, (void **) (&orig_access), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "chmod", "(Ljava/lang/String;I)V", + (void *) new_chmod, (void **) (&orig_chmod), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "chown", "(Ljava/lang/String;II)V", + (void *) new_chown, (void **) (&orig_chown), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "execv", "(Ljava/lang/String;[Ljava/lang/String;)V", + (void *) new_execv, (void **) (&orig_execv), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "execve", "(Ljava/lang/String;[Ljava/lang/String;[Ljava/lang/String;)V", + (void *) new_execve, (void **) (&orig_execve), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "getxattr", "(Ljava/lang/String;Ljava/lang/String;)[B", + (void *) new_getxattr, (void **) (&orig_getxattr), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "lchown", "(Ljava/lang/String;II)V", + (void *) new_lchown, (void **) (&orig_lchown), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "link", "(Ljava/lang/String;Ljava/lang/String;)V", + (void *) new_link, (void **) (&orig_link), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "listxattr", "(Ljava/lang/String;)[Ljava/lang/String;", + (void *) new_listxattr, (void **) (&orig_listxattr), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "lstat", "(Ljava/lang/String;)Landroid/system/StructStat;", + (void *) new_lstat, (void **) (&orig_lstat), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "mkdir", "(Ljava/lang/String;I)V", + (void *) new_mkdir, (void **) (&orig_mkdir), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "mkfifo", "(Ljava/lang/String;I)V", + (void *) new_mkfifo, (void **) (&orig_mkfifo), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "open", "(Ljava/lang/String;II)Ljava/io/FileDescriptor;", + (void *) new_open, (void **) (&orig_open), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "readlink", "(Ljava/lang/String;)Ljava/lang/String;", + (void *) new_readlink, (void **) (&orig_readlink), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "realpath", "(Ljava/lang/String;)Ljava/lang/String;", + (void *) new_realpath, (void **) (&orig_realpath), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "remove", "(Ljava/lang/String;)V", + (void *) new_remove, (void **) (&orig_remove), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "removexattr", "(Ljava/lang/String;Ljava/lang/String;)V", + (void *) new_removexattr, (void **) (&orig_removexattr), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "rename", "(Ljava/lang/String;Ljava/lang/String;)V", + (void *) new_rename, (void **) (&orig_rename), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "stat", "(Ljava/lang/String;)Landroid/system/StructStat;", + (void *) new_stat, (void **) (&orig_stat), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "statvfs", "(Ljava/lang/String;)Landroid/system/StructStatVfs;", + (void *) new_statvfs, (void **) (&orig_statvfs), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "symlink", "(Ljava/lang/String;Ljava/lang/String;)V", + (void *) new_symlink, (void **) (&orig_symlink), false); + + JniHook::HookJniFun(env, "libcore/io/Linux", "unlink", "(Ljava/lang/String;)V", + (void *) new_unlink, (void **) (&orig_unlink), false); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.h new file mode 100644 index 0000000..74f63f5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/LinuxHook.h @@ -0,0 +1,11 @@ +#ifndef BLACKBOX_LINUXHOOK_H +#define BLACKBOX_LINUXHOOK_H + +#include "BaseHook.h" + +class LinuxHook : public BaseHook { +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_LINUXHOOK_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.cpp new file mode 100644 index 0000000..a83f56f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.cpp @@ -0,0 +1,31 @@ +#include "RuntimeHook.h" +#import "JniHook/JniHook.h" +#include "BoxCore.h" + +HOOK_JNI(jstring, nativeLoad, JNIEnv *env, jobject obj, jstring name, jobject class_loader) { + const char *nameC = env->GetStringUTFChars(name, JNI_FALSE); + ALOGD("nativeLoad: %s", nameC); + jstring result = orig_nativeLoad(env, obj, name, class_loader); + env->ReleaseStringUTFChars(name, nameC); + return result; +} + +HOOK_JNI(jstring, nativeLoadNew, JNIEnv *env, jobject obj, jstring name, jobject class_loader, + jobject caller) { + const char *nameC = env->GetStringUTFChars(name, JNI_FALSE); + ALOGD("nativeLoad: %s", nameC); + jstring result = orig_nativeLoadNew(env, obj, name, class_loader, caller); + env->ReleaseStringUTFChars(name, nameC); + return result; +} + +void RuntimeHook::init(JNIEnv *env) { + const char *className = "java/lang/Runtime"; + if (BoxCore::getApiLevel() >= __ANDROID_API_Q__) { + JniHook::HookJniFun(env, className, "nativeLoad","(Ljava/lang/String;Ljava/lang/ClassLoader;Ljava/lang/Class;)Ljava/lang/String;", + (void *) new_nativeLoadNew, (void **) (&orig_nativeLoadNew), true); + } else { + JniHook::HookJniFun(env, className, "nativeLoad","(Ljava/lang/String;Ljava/lang/ClassLoader;)Ljava/lang/String;", + (void *) new_nativeLoad, (void **) (&orig_nativeLoad), true); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.h new file mode 100644 index 0000000..2fd56dc --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/RuntimeHook.h @@ -0,0 +1,12 @@ +#ifndef BLACKBOX_RUNTIMEHOOK_H +#define BLACKBOX_RUNTIMEHOOK_H + +#include "BaseHook.h" +#include + +class RuntimeHook : public BaseHook { +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_RUNTIMEHOOK_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.cpp new file mode 100644 index 0000000..0592511 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.cpp @@ -0,0 +1,59 @@ +#include +#include "SystemPropertiesHook.h" +#include "IO.h" +#include "BoxCore.h" +#import "JniHook/JniHook.h" +#include "Log.h" + +static std::map prop_map; + +HOOK_JNI(jstring, native_get, JNIEnv *env, jobject obj, jstring key, jstring def) { + const char *key_str = env->GetStringUTFChars(key, JNI_FALSE); + const char *def_str = env->GetStringUTFChars(def, JNI_FALSE); + if (key == nullptr || def == nullptr) { + return orig_native_get(env, obj, key, def); + } + + auto ret = prop_map.find(key_str); + if (ret != prop_map.end()) { + const char *ret_value = ret->second.c_str(); + return env->NewStringUTF(ret_value); + } + + env->ReleaseStringUTFChars(key, key_str); + env->ReleaseStringUTFChars(key, def_str); + return orig_native_get(env, obj, key, def); +} + +HOOK_JNI(int, __system_property_get, const char *name, char *value) { + if (name == nullptr || value == nullptr) { + return orig___system_property_get(name, value); + } + + ALOGD(name, value); + auto ret = prop_map.find(name); + if (ret != prop_map.end()) { + const char *ret_value = ret->second.c_str(); + strcpy(value, ret_value); + return strlen(ret_value); + } + return orig___system_property_get(name, value); +} + +void SystemPropertiesHook::init(JNIEnv *env) { + prop_map.insert(map::value_type("ro.product.board", "umi")); + prop_map.insert(map::value_type("ro.product.brand", "Xiaomi")); + prop_map.insert(map::value_type("ro.product.device", "umi")); + prop_map.insert(map::value_type("ro.build.display.id","QKQ1.191117.002 test-keys")); + prop_map.insert(map::value_type("ro.build.host", "c5-miui-ota-bd074.bj")); + prop_map.insert(map::value_type("ro.build.id", "QKQ1.191117.002")); + prop_map.insert(map::value_type("ro.product.manufacturer", "Xiaomi")); + prop_map.insert(map::value_type("ro.product.model", "Mi 10")); + prop_map.insert(map::value_type("ro.product.name", "umi")); + prop_map.insert(map::value_type("ro.build.tags", "release-keys")); + prop_map.insert(map::value_type("ro.build.type", "user")); + prop_map.insert(map::value_type("ro.build.user", "builder")); + JniHook::HookJniFun(env, "android/os/SystemProperties","native_get", "(Ljava/lang/String;Ljava/lang/String;)Ljava/lang/String;", + (void *) new_native_get, (void **) (&orig_native_get), true); + shadowhook_hook_sym_name("libc.so", "__system_property_get",(void *)new___system_property_get,(void **) &orig___system_property_get); +} \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.h new file mode 100644 index 0000000..66d2d46 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/SystemPropertiesHook.h @@ -0,0 +1,13 @@ +#ifndef BLACKBOX_SYSTEMPROPERTIESHOOK_H +#define BLACKBOX_SYSTEMPROPERTIESHOOK_H + +#include +#include "BaseHook.h" +#include + +class SystemPropertiesHook : public BaseHook{ +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_SYSTEMPROPERTIESHOOK_H diff --git a/520ApkBox/BCore/src/main/cpp/Hook/UnixFileSystemHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.cpp similarity index 83% rename from 520ApkBox/BCore/src/main/cpp/Hook/UnixFileSystemHook.cpp rename to 520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.cpp index e7d70da..638e10c 100644 --- a/520ApkBox/BCore/src/main/cpp/Hook/UnixFileSystemHook.cpp +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.cpp @@ -1,7 +1,3 @@ -// -// Created by Milk on 4/9/21. -// - #include #include "UnixFileSystemHook.h" #import "JniHook/JniHook.h" @@ -17,16 +13,6 @@ HOOK_JNI(jstring, canonicalize0, JNIEnv *env, jobject obj, jstring path) { return orig_canonicalize0(env, obj, redirect); } -/* - * Class: java_io_UnixFileSystem - * Method: getBooleanAttributes0 - * Signature: (Ljava/lang/String;)I - */ -HOOK_JNI(jint, getBooleanAttributes0, JNIEnv *env, jobject obj, jstring abspath) { - jstring redirect = IO::redirectPath(env, abspath); - return orig_getBooleanAttributes0(env, obj, redirect); -} - /* * Class: java_io_UnixFileSystem * Method: getLastModifiedTime0 @@ -112,26 +98,28 @@ void UnixFileSystemHook::init(JNIEnv *env) { const char *className = "java/io/UnixFileSystem"; JniHook::HookJniFun(env, className, "canonicalize0", "(Ljava/lang/String;)Ljava/lang/String;", (void *) new_canonicalize0, (void **) (&orig_canonicalize0), false); -// JniHook::HookJniFun(env, className, "getBooleanAttributes0", "(Ljava/lang/String;)I", -// (void *) new_getBooleanAttributes0, -// (void **) (&orig_getBooleanAttributes0), false); + JniHook::HookJniFun(env, className, "getLastModifiedTime0", "(Ljava/io/File;)J", - (void *) new_getLastModifiedTime0, (void **) (&orig_getLastModifiedTime0), - false); + (void *) new_getLastModifiedTime0, (void **) (&orig_getLastModifiedTime0), false); + JniHook::HookJniFun(env, className, "setPermission0", "(Ljava/io/File;IZZ)Z", (void *) new_setPermission0, (void **) (&orig_setPermission0), false); + JniHook::HookJniFun(env, className, "createFileExclusively0", "(Ljava/lang/String;)Z", - (void *) new_createFileExclusively0, - (void **) (&orig_createFileExclusively0), false); + (void *) new_createFileExclusively0, (void **) (&orig_createFileExclusively0), false); + JniHook::HookJniFun(env, className, "list0", "(Ljava/io/File;)[Ljava/lang/String;", (void *) new_list0, (void **) (&orig_list0), false); + JniHook::HookJniFun(env, className, "createDirectory0", "(Ljava/io/File;)Z", (void *) new_createDirectory0, (void **) (&orig_createDirectory0), false); + JniHook::HookJniFun(env, className, "setLastModifiedTime0", "(Ljava/io/File;J)Z", - (void *) new_setLastModifiedTime0, (void **) (&orig_setLastModifiedTime0), - false); + (void *) new_setLastModifiedTime0, (void **) (&orig_setLastModifiedTime0),false); + JniHook::HookJniFun(env, className, "setReadOnly0", "(Ljava/io/File;)Z", (void *) new_setReadOnly0, (void **) (&orig_setReadOnly0), false); + JniHook::HookJniFun(env, className, "getSpace0", "(Ljava/io/File;I)J", (void *) new_getSpace0, (void **) (&orig_getSpace0), false); -} \ No newline at end of file +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.h new file mode 100644 index 0000000..0be7686 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/UnixFileSystemHook.h @@ -0,0 +1,11 @@ +#ifndef BLACKBOX_UNIXFILESYSTEMHOOK_H +#define BLACKBOX_UNIXFILESYSTEMHOOK_H + +#include "BaseHook.h" + +class UnixFileSystemHook : public BaseHook { +public: + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_UNIXFILESYSTEMHOOK_H diff --git a/520ApkBox/BCore/src/main/cpp/Hook/VMClassLoaderHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.cpp similarity index 82% rename from 520ApkBox/BCore/src/main/cpp/Hook/VMClassLoaderHook.cpp rename to 520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.cpp index 1135098..73c5ba4 100644 --- a/520ApkBox/BCore/src/main/cpp/Hook/VMClassLoaderHook.cpp +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.cpp @@ -1,19 +1,12 @@ -// -// Created by Milk on 2021/5/5. -// - -// -// Created by Milk on 5/5/21. -// - #include #include "VMClassLoaderHook.h" #import "JniHook/JniHook.h" + static bool hideXposedClass = false; HOOK_JNI(jobject, findLoadedClass, JNIEnv *env, jobject obj, jobject class_loader, jstring name) { const char * nameC = env->GetStringUTFChars(name, JNI_FALSE); -// ALOGD("findLoadedClass: %s", nameC); + // ALOGD("findLoadedClass: %s", nameC); if (hideXposedClass) { if (strstr(nameC, "de/robv/android/xposed/") || strstr(nameC, "me/weishu/epic") || @@ -33,8 +26,7 @@ HOOK_JNI(jobject, findLoadedClass, JNIEnv *env, jobject obj, jobject class_loade void VMClassLoaderHook::init(JNIEnv *env) { const char *className = "java/lang/VMClassLoader"; JniHook::HookJniFun(env, className, "findLoadedClass", "(Ljava/lang/ClassLoader;Ljava/lang/String;)Ljava/lang/Class;", - (void *) new_findLoadedClass, - (void **) (&orig_findLoadedClass), true); + (void *) new_findLoadedClass, (void **) (&orig_findLoadedClass), true); } void VMClassLoaderHook::hideXposed() { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.h new file mode 100644 index 0000000..07d860c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Hook/VMClassLoaderHook.h @@ -0,0 +1,13 @@ +#ifndef BLACKBOX_VMCLASSLOADERHOOK_H +#define BLACKBOX_VMCLASSLOADERHOOK_H + +#include "BaseHook.h" +#include + +class VMClassLoaderHook : public BaseHook { +public: + static void hideXposed(); + static void init(JNIEnv *env); +}; + +#endif // BLACKBOX_VMCLASSLOADERHOOK_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.cpp new file mode 100644 index 0000000..55cf778 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.cpp @@ -0,0 +1,82 @@ +// +// Created by Milk on 4/10/21. +// + +#include +#include +#include "IO.h" +#include "Log.h" +#include "JniHook/JniHook.h" + +list relocate_rule; +list white_rule; + +char *replace(const char *str, const char *src, const char *dst) { + const char *pos = str; + int count = 0; + while ((pos = strstr(pos, src))) { + count++; + pos += strlen(src); + } + + size_t result_len = strlen(str) + (strlen(dst) - strlen(src)) * count + 1; + char *result = (char *) malloc(result_len); + memset(result, 0, strlen(result)); + + const char *left = str; + const char *right; + + while ((right = strstr(left, src))) { + strncat(result, left, right - left); + strcat(result, dst); + right += strlen(src); + left = right; + } + strcat(result, left); + return result; +} + +//#ifdef __arm__ https://developer.android.com/games/optimize/64-bit?hl=zh-cn +HOOK_JNI(void *, openat, int fd, const char *pathname, int flags, int mode) { + // 执行 stack 清理(不可省略),只需调用一次 + // SHADOWHOOK_STACK_SCOPE(); + list::iterator white_iterator; + for (white_iterator = white_rule.begin(); + white_iterator != white_rule.end(); ++white_iterator) { + const char *info = *white_iterator; + if (strstr(pathname, info)) { + return orig_openat(fd, pathname, flags, mode); + } + } + list::iterator iterator; + for (iterator = relocate_rule.begin(); iterator != relocate_rule.end(); ++iterator) { + IO::RelocateInfo info = *iterator; + if (strstr(pathname, info.targetPath) && !strstr(pathname, "/blackbox/")) { + log_print_debug("redirectPath %s => %s", pathname, info.relocatePath); + return orig_openat(fd, info.relocatePath, flags, mode); + } + } + // 调用原函数 + return orig_openat(fd, pathname, flags, mode); +} + +jstring IO::redirectPath(JNIEnv *env, jstring path) { + return BoxCore::redirectPathString(env, path); +} + +jobject IO::redirectPath(JNIEnv *env, jobject path) { + return BoxCore::redirectPathFile(env, path); +} + +void IO::addWhiteList(const char *path) { + white_rule.push_back(path); +} + +void IO::addRule(const char *targetPath, const char *relocatePath) { + IO::RelocateInfo info{}; + info.targetPath = targetPath; + info.relocatePath = relocatePath; + relocate_rule.push_back(info); +} + + diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.h new file mode 100644 index 0000000..d56e83f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/IO.h @@ -0,0 +1,45 @@ +#ifndef BLACKBOX_IO_H +#define BLACKBOX_IO_H + +#if defined(__LP64__) +#define LINKER_PATH_L "/system/bin/linker64" +#define LINKER_PATH_Q "/apex/com.android.runtime/bin/linker64" +#define LIBC_PATH_L "/system/lib64/libc.so" +#define LIBC_PATH_Q "/apex/com.android.runtime/lib64/bionic/libc.so" +#else +#define LINKER_PATH_L "/system/bin/linker" +#define LINKER_PATH_Q "/apex/com.android.runtime/bin/linker" +#define LIBC_PATH_L "/system/lib/libc.so" +#define LIBC_PATH_Q "/apex/com.android.runtime/lib/bionic/libc.so" +#endif + +#include + +#include +#include +#include "BoxCore.h" + +using namespace std; + +class IO { +public: + static void init(JNIEnv *env); + + struct RelocateInfo { + const char *targetPath; + const char *relocatePath; + }; + + static void addRule(const char *targetPath, const char *relocatePath); + + static void addWhiteList(const char *path); + + static jstring redirectPath(JNIEnv *env, jstring path); + + static jobject redirectPath(JNIEnv *env, jobject path); + + static void replaceFD(JNIEnv *env, jobject fd); + +}; + +#endif // BLACKBOX_IO_H diff --git a/520ApkBox/BCore/src/main/cpp/JniHook/ArtMethod.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/ArtMethod.h similarity index 97% rename from 520ApkBox/BCore/src/main/cpp/JniHook/ArtMethod.h rename to 520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/ArtMethod.h index 3131085..b7cf9e4 100644 --- a/520ApkBox/BCore/src/main/cpp/JniHook/ArtMethod.h +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/ArtMethod.h @@ -1,6 +1,3 @@ -// -// Created by Milk on 3/7/21. -// #include #ifndef ARTHOOK_ART_METHOD_H @@ -37,4 +34,4 @@ static constexpr uint32_t kAccCorePlatformApi = 0x20000000; // field, met // Reuse the values of kAccSkipAccessChecks and kAccMiranda which are not used for native methods. static constexpr uint32_t kAccFastNative = 0x00080000; // method (runtime; native only) static constexpr uint32_t kAccCriticalNative = 0x00200000; // method (runtime; native only) -#endif //ARTHOOK_ART_METHOD_H +#endif // ARTHOOK_ART_METHOD_H diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.cpp b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.cpp new file mode 100644 index 0000000..b7d0206 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.cpp @@ -0,0 +1,267 @@ +#include +#include +#define JNIHOOKCLASS "com/vcore/jnihook/JniHook" +#define JNIMETHOOG_Utills "com/vcore/jnihook/MethodUtils" +#include "JniHook.h" +#include "Log.h" +#include "ArtMethod.h" + + + +static struct { + int api_level; + unsigned int art_field_size; + int art_field_flags_offset; + + unsigned int art_method_size; + int art_method_flags_offset; + int art_method_native_offset; + + int class_flags_offset; + + jclass method_utils_class; + jmethodID get_method_desc_id; + jmethodID get_method_declaring_class_id; + jmethodID get_method_name_id; +} HookEnv; + +static const char *GetMethodDesc(JNIEnv *env, jobject javaMethod) { + auto desc = reinterpret_cast(env->CallStaticObjectMethod(HookEnv.method_utils_class, HookEnv.get_method_desc_id, javaMethod)); + return env->GetStringUTFChars(desc, JNI_FALSE); +} + +static const char *GetMethodDeclaringClass(JNIEnv *env, jobject javaMethod) { + auto desc = reinterpret_cast(env->CallStaticObjectMethod(HookEnv.method_utils_class, HookEnv.get_method_declaring_class_id, javaMethod)); + return env->GetStringUTFChars(desc, JNI_FALSE); +} + +static const char *GetMethodName(JNIEnv *env, jobject javaMethod) { + auto desc = reinterpret_cast(env->CallStaticObjectMethod(HookEnv.method_utils_class, HookEnv.get_method_name_id, javaMethod)); + return env->GetStringUTFChars(desc, JNI_FALSE); +} + +inline static uint32_t GetAccessFlags(const char *art_method) { + return *reinterpret_cast(art_method + HookEnv.art_method_flags_offset); +} + +inline static bool SetAccessFlags(char *art_method, uint32_t flags) { + *reinterpret_cast(art_method + HookEnv.art_method_flags_offset) = flags; + return true; +} + +inline static bool AddAccessFlag(char *art_method, uint32_t flag) { + uint32_t old_flag = GetAccessFlags(art_method); + uint32_t new_flag = old_flag | flag; + return new_flag != old_flag && SetAccessFlags(art_method, new_flag); +} + +inline static bool ClearAccessFlag(char *art_method, uint32_t flag) { + uint32_t old_flag = GetAccessFlags(art_method); + uint32_t new_flag = old_flag & ~flag; + return new_flag != old_flag && SetAccessFlags(art_method, new_flag); +} + +inline static bool HasAccessFlag(char *art_method) { + uint32_t flags = GetAccessFlags(art_method); + return (flags & 256) == 256; +} + +inline static bool ClearFastNativeFlag(char *art_method) { + // FastNative + return HookEnv.api_level < __ANDROID_API_P__ && ClearAccessFlag(art_method, kAccFastNative); +} + +static void *GetArtMethod(JNIEnv *env, jclass clazz, jmethodID methodId) { + if (HookEnv.api_level >= __ANDROID_API_Q__) { + jclass executable = env->FindClass("java/lang/reflect/Executable"); + jfieldID artId = env->GetFieldID(executable, "artMethod", "J"); + jobject method = env->ToReflectedMethod(clazz, methodId, true); + return reinterpret_cast(env->GetLongField(method, artId)); + } else { + return methodId; + } +} + +static void *GetFieldMethod(JNIEnv *env, jobject field) { + if (HookEnv.api_level >= __ANDROID_API_Q__) { + jclass fieldClass = env->FindClass("java/lang/reflect/Field"); + jmethodID getArtField = env->GetMethodID(fieldClass, "getArtField", "()J"); + return reinterpret_cast(env->CallLongMethod(field, getArtField)); + } else { + return env->FromReflectedField(field); + } +} + +bool CheckFlags(void *artMethod) { + char *method = static_cast(artMethod); + if (!HasAccessFlag(method)) { + ALOGE("not native method"); + return false; + } + ClearFastNativeFlag(method); + return true; +} + +void JniHook::HookJniFun(JNIEnv *env, jobject java_method, void *new_fun, void **orig_fun, bool is_static) { + const char *class_name = GetMethodDeclaringClass(env, java_method); + const char *method_name = GetMethodName(env, java_method); + const char *sign = GetMethodDesc(env, java_method); + HookJniFun(env, class_name, method_name, sign, new_fun, orig_fun, is_static); +} + +void JniHook::HookJniFun(JNIEnv *env, const char *class_name, const char *method_name, const char *sign, void *new_fun, void **orig_fun, bool is_static) { + if (HookEnv.art_method_native_offset == 0) { + return; + } + + jclass clazz = env->FindClass(class_name); + if (!clazz) { + ALOGD("findClass fail: %s %s", class_name, method_name); + env->ExceptionClear(); + return; + } + + jmethodID method; + if (is_static) { + method = env->GetStaticMethodID(clazz, method_name, sign); + } else { + method = env->GetMethodID(clazz, method_name, sign); + } + + if (!method) { + env->ExceptionClear(); + ALOGD("get method id fail: %s %s", class_name, method_name); + return; + } + + JNINativeMethod gMethods[] = { + { method_name, sign, (void *) new_fun }, + }; + + auto artMethod = reinterpret_cast(GetArtMethod(env, clazz, method)); + // 不检查系统包 + if (!strncmp(class_name, "android.", 8) && !CheckFlags(artMethod)) { + ALOGE("check flags error. class:%s, method:%s", class_name, method_name); + return; + } + + *orig_fun = reinterpret_cast(artMethod[HookEnv.art_method_native_offset]); + if (env->RegisterNatives(clazz, gMethods, 1) < 0) { + ALOGE("JNI hook error. class:%s, method:%s", class_name, method_name); + return; + } + // FastNative + if (HookEnv.api_level == __ANDROID_API_O__ || HookEnv.api_level == __ANDROID_API_O_MR1__) { + AddAccessFlag((char *) artMethod, kAccFastNative); + } + ALOGD("Register class:%s, method:%s success!", class_name, method_name); +} + +__attribute__((section (".mytext"))) JNICALL void native_offset + (JNIEnv *env, jclass obj) { +} + +__attribute__((section (".mytext"))) JNICALL void native_offset2 + (JNIEnv *env, jclass obj) { +} + +__attribute__((section (".mytext"))) JNICALL void set_method_accessible(JNIEnv *env, jclass obj, jclass clazz, jobject method) { + jmethodID methodId = env->FromReflectedMethod(method); + char *art_method = static_cast(GetArtMethod(env, clazz, methodId)); + + AddAccessFlag(art_method, kAccPublic); + if (HookEnv.api_level >= __ANDROID_API_Q__) { + AddAccessFlag(art_method, kAccPublicApi); + } +} + +__attribute__((section (".mytext"))) JNICALL void set_field_accessible(JNIEnv *env, jclass obj, jclass clazz, jobject field) { + char *artField = static_cast(GetFieldMethod(env, field)); + AddAccessFlag(artField, kAccPublic); + + if (HookEnv.api_level >= __ANDROID_API_Q__) { + AddAccessFlag(artField, kAccPublicApi); + } + ClearAccessFlag(artField, kAccFinal); +} + +void registerNative(JNIEnv *env) { + jclass clazz = env->FindClass(JNIHOOKCLASS); + JNINativeMethod gMethods[] = { + {"nativeOffset", "()V", (void *) native_offset}, + {"nativeOffset2", "()V", (void *) native_offset2}, + }; + + if (env->RegisterNatives(clazz, gMethods, sizeof(gMethods) / sizeof(gMethods[0])) < 0) { + ALOGE("JNI register error."); + } +} + +void JniHook::InitJniHook(JNIEnv *env, int api_level) { + registerNative(env); + HookEnv.api_level = api_level; + + jclass clazz = env->FindClass(JNIHOOKCLASS); + jmethodID nativeOffsetId = env->GetStaticMethodID(clazz, "nativeOffset", "()V"); + jmethodID nativeOffset2Id = env->GetStaticMethodID(clazz, "nativeOffset2", "()V"); + + jfieldID nativeOffsetFieldId = env->GetStaticFieldID(clazz, "NATIVE_OFFSET", "I"); + jfieldID nativeOffsetField2Id = env->GetStaticFieldID(clazz, "NATIVE_OFFSET_2", "I"); + + void *nativeOffsetField = GetFieldMethod(env, env->ToReflectedField(clazz, nativeOffsetFieldId, true)); + void *nativeOffsetField2 = GetFieldMethod(env, env->ToReflectedField(clazz, nativeOffsetField2Id, true)); + HookEnv.art_field_size = (size_t) nativeOffsetField2 - (size_t) nativeOffsetField; + + void *nativeOffset = GetArtMethod(env, clazz, nativeOffsetId); + void *nativeOffset2 = GetArtMethod(env, clazz, nativeOffset2Id); + HookEnv.art_method_size = (size_t) nativeOffset2 - (size_t) nativeOffset; + + // calc native offset + auto artMethod = reinterpret_cast(nativeOffset); + for (int i = 0; i < HookEnv.art_method_size; ++i) { + if (reinterpret_cast(artMethod[i]) == native_offset) { + HookEnv.art_method_native_offset = i; + break; + } + } + + uint32_t flags = 0x0; + flags = flags | kAccPublic; + flags = flags | kAccStatic; + flags = flags | kAccNative; + flags = flags | kAccFinal; + if (api_level >= __ANDROID_API_Q__) { + flags = flags | kAccPublicApi; + } + + char *start = reinterpret_cast(artMethod); + for (int i = 1; i < HookEnv.art_method_size; ++i) { + auto value = *(uint32_t *) (start + i * sizeof(uint32_t)); + if (value == flags) { + HookEnv.art_method_flags_offset = i * sizeof(uint32_t); + break; + } + } + + flags = 0x0; + flags = flags | kAccPublic; + flags = flags | kAccStatic; + flags = flags | kAccFinal; + if (api_level >= __ANDROID_API_Q__) { + flags = flags | kAccPublicApi; + } + + char *fieldStart = reinterpret_cast(nativeOffsetField); + for (int i = 1; i < HookEnv.art_field_size; ++i) { + auto value = *(int32_t *) (fieldStart + i * sizeof(int32_t)); + if (value == flags) { + HookEnv.art_field_flags_offset = i * sizeof(int32_t); + break; + } + } + + HookEnv.method_utils_class = env->FindClass(JNIMETHOOG_Utills); + HookEnv.get_method_desc_id = env->GetStaticMethodID(HookEnv.method_utils_class, "getDesc", "(Ljava/lang/reflect/Method;)Ljava/lang/String;"); + HookEnv.get_method_declaring_class_id = env->GetStaticMethodID(HookEnv.method_utils_class, "getDeclaringClass", "(Ljava/lang/reflect/Method;)Ljava/lang/String;"); + HookEnv.get_method_name_id = env->GetStaticMethodID(HookEnv.method_utils_class, "getMethodName", "(Ljava/lang/reflect/Method;)Ljava/lang/String;"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.h new file mode 100644 index 0000000..ed6c8e6 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/JniHook/JniHook.h @@ -0,0 +1,17 @@ +#ifndef BLACKBOX_JNIHOOK_H +#define BLACKBOX_JNIHOOK_H + +#include "ArtMethod.h" + +#define HOOK_JNI(ret, func, ...) \ + ret (*orig_##func)(__VA_ARGS__); \ + ret new_##func(__VA_ARGS__) + +class JniHook { +public: + static void InitJniHook(JNIEnv *env, int api_level); + static void HookJniFun(JNIEnv *env, const char *class_name, const char *method_name, const char *sign, void *new_fun, void **orig_fun, bool is_static); + static void HookJniFun(JNIEnv *env, jobject java_method, void *new_fun, void **orig_fun, bool is_static); +}; + +#endif // BLACKBOX_JNIHOOK_H diff --git a/520ApkBox/BCore/src/main/cpp/Log.h b/520ApkBox-NewBlackbox/Bcore/src/main/cpp/Log.h similarity index 100% rename from 520ApkBox/BCore/src/main/cpp/Log.h rename to 520ApkBox-NewBlackbox/Bcore/src/main/cpp/Log.h diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ActivityThread.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ActivityThread.java new file mode 100644 index 0000000..e1d1ee8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ActivityThread.java @@ -0,0 +1,75 @@ +package android.app; + +import android.content.Context; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ProviderInfo; +import android.os.Handler; +import android.os.IBinder; +import android.util.ArrayMap; + +import java.lang.ref.WeakReference; +import java.util.Map; +import java.util.Objects; + +public class ActivityThread { + public H mH = null; + public AppBindData mBoundApplication; + public Application mInitialApplication; + public Instrumentation mInstrumentation; + public Map> mPackages; + public Map mActivities; + public ArrayMap mProviderMap; + + static class H extends Handler { } + + public static ActivityThread currentActivityThread() { + throw new RuntimeException(); + } + + public String getProcessName() { + throw new RuntimeException(); + } + + public Handler getHandler() { + throw new RuntimeException(); + } + + public ContentProviderHolder installProvider(Context context, ContentProviderHolder holder, ProviderInfo info, boolean noisy, + boolean noReleaseNeeded, boolean stable) { + throw new RuntimeException(); + } + + static final class AppBindData { } + + public static final class ActivityClientRecord { + public Activity activity; + public IBinder token; + public ActivityInfo activityInfo; + public Intent intent; + } + + public static final class ProviderKey { + public final String authority; + public final int userId; + + public ProviderKey(String authority, int userId) { + this.authority = authority; + this.userId = userId; + } + + @Override + public boolean equals(Object o) { + if (o instanceof ProviderKey) { + final ProviderKey other = (ProviderKey) o; + return Objects.equals(authority, other.authority) && userId == other.userId; + } + return false; + } + + @Override + public int hashCode() { + return ((authority != null) ? authority.hashCode() : 0) ^ userId; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ContentProviderHolder.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ContentProviderHolder.java new file mode 100644 index 0000000..7880855 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/app/ContentProviderHolder.java @@ -0,0 +1,11 @@ +package android.app; + +import android.content.IContentProvider; +import android.content.pm.ProviderInfo; +import android.os.IBinder; + +public class ContentProviderHolder { + public final ProviderInfo info = null; + public IContentProvider provider; + public IBinder connection; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/IContentProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/IContentProvider.java new file mode 100644 index 0000000..67505f1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/IContentProvider.java @@ -0,0 +1,5 @@ +package android.content; + +import android.os.IInterface; + +public interface IContentProvider extends IInterface { } \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncInfo.java new file mode 100644 index 0000000..236c7c2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncInfo.java @@ -0,0 +1,85 @@ +package android.content; + +import android.accounts.Account; +import android.os.Parcel; +import android.os.Parcelable; + +/** + * Information about the sync operation that is currently underway. + */ +public class SyncInfo implements Parcelable { + /** + * Used when the caller receiving this object doesn't have permission to access the accounts + * on device. + * @See Manifest.permission.GET_ACCOUNTS + */ + private static final Account REDACTED_ACCOUNT = new Account("*****", "*****"); + + /** @hide */ + public final int authorityId; + + /** + * The {@link Account} that is currently being synced. + */ + public final Account account; + + /** + * The authority of the provider that is currently being synced. + */ + public final String authority; + + /** + * The start time of the current sync operation in milliseconds since boot. + * This is represented in elapsed real time. + * See {@link android.os.SystemClock#elapsedRealtime()}. + */ + public final long startTime; + + /** + * Creates a SyncInfo object with an unusable Account. Used when the caller receiving this + * object doesn't have access to the accounts on the device. + * @See Manifest.permission.GET_ACCOUNTS + * @hide + */ + public static SyncInfo createAccountRedacted( + int authorityId, String authority, long startTime) { + throw new RuntimeException("Stub!"); + } + + /** @hide */ + public SyncInfo(int authorityId, Account account, String authority, long startTime) { + throw new RuntimeException("Stub!"); + } + + /** @hide */ + public SyncInfo(SyncInfo other) { + throw new RuntimeException("Stub!"); + } + + /** @hide */ + public int describeContents() { + return 0; + } + + /** @hide */ + public void writeToParcel(Parcel parcel, int flags) { + parcel.writeInt(authorityId); + parcel.writeParcelable(account, flags); + parcel.writeString(authority); + parcel.writeLong(startTime); + } + + SyncInfo(Parcel parcel) { + throw new RuntimeException("Stub!"); + } + + public static final Creator CREATOR = new Creator() { + public SyncInfo createFromParcel(Parcel in) { + return new SyncInfo(in); + } + + public SyncInfo[] newArray(int size) { + return new SyncInfo[size]; + } + }; +} diff --git a/520ApkBox/BCore/black-fake/src/main/java/android/content/SyncStatusInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncStatusInfo.java similarity index 92% rename from 520ApkBox/BCore/black-fake/src/main/java/android/content/SyncStatusInfo.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncStatusInfo.java index 20c00af..b07d1dc 100644 --- a/520ApkBox/BCore/black-fake/src/main/java/android/content/SyncStatusInfo.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/SyncStatusInfo.java @@ -26,9 +26,9 @@ public class SyncStatusInfo implements Parcelable { public boolean pending; public boolean initialize; - // Warning: It is up to the external caller to ensure there are - // no race conditions when accessing this list - private ArrayList periodicSyncTimes; + // Warning: It is up to the external caller to ensure there are + // no race conditions when accessing this list + private ArrayList periodicSyncTimes; private static final String TAG = "Sync"; @@ -36,10 +36,6 @@ public SyncStatusInfo(int authorityId) { this.authorityId = authorityId; } - public int getLastFailureMesgAsInt(int def) { - return 0; - } - public int describeContents() { return 0; } @@ -61,6 +57,7 @@ public void writeToParcel(Parcel parcel, int flags) { parcel.writeLong(initialFailureTime); parcel.writeInt(pending ? 1 : 0); parcel.writeInt(initialize ? 1 : 0); + if (periodicSyncTimes != null) { parcel.writeInt(periodicSyncTimes.size()); for (long periodicSyncTime : periodicSyncTimes) { @@ -76,6 +73,7 @@ public SyncStatusInfo(Parcel parcel) { if (version != VERSION && version != 1) { Log.w("SyncStatusInfo", "Unknown version: " + version); } + authorityId = parcel.readInt(); totalElapsedTime = parcel.readLong(); numSyncs = parcel.readInt(); @@ -91,6 +89,7 @@ public SyncStatusInfo(Parcel parcel) { initialFailureTime = parcel.readLong(); pending = parcel.readInt() != 0; initialize = parcel.readInt() != 0; + if (version == 1) { periodicSyncTimes = null; } else { @@ -98,8 +97,8 @@ public SyncStatusInfo(Parcel parcel) { if (N < 0) { periodicSyncTimes = null; } else { - periodicSyncTimes = new ArrayList(); - for (int i=0; i(); + for (int i = 0; i < N; i++) { periodicSyncTimes.add(parcel.readLong()); } } @@ -123,8 +122,9 @@ public SyncStatusInfo(SyncStatusInfo other) { initialFailureTime = other.initialFailureTime; pending = other.pending; initialize = other.initialize; + if (other.periodicSyncTimes != null) { - periodicSyncTimes = new ArrayList(other.periodicSyncTimes); + periodicSyncTimes = new ArrayList<>(other.periodicSyncTimes); } } @@ -138,9 +138,8 @@ public void setPeriodicSyncTime(int index, long when) { public long getPeriodicSyncTime(int index) { if (periodicSyncTimes != null && index < periodicSyncTimes.size()) { return periodicSyncTimes.get(index); - } else { - return 0; } + return 0; } public void removePeriodicSyncTime(int index) { @@ -171,4 +170,4 @@ private void ensurePeriodicSyncTimeSize(int index) { } } } -} \ No newline at end of file +} diff --git a/520ApkBox/BCore/black-fake/src/main/java/android/content/pm/ManifestDigest.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/ManifestDigest.java similarity index 91% rename from 520ApkBox/BCore/black-fake/src/main/java/android/content/pm/ManifestDigest.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/ManifestDigest.java index 46150c2..7ba468c 100644 --- a/520ApkBox/BCore/black-fake/src/main/java/android/content/pm/ManifestDigest.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/ManifestDigest.java @@ -5,16 +5,7 @@ import java.util.jar.Attributes; -/** - * Created by Milk on 2021/5/7. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class ManifestDigest implements Parcelable { - ManifestDigest(final byte[] digest) { throw new RuntimeException("Stub!"); } @@ -61,5 +52,4 @@ public ManifestDigest[] newArray(int size) { return new ManifestDigest[size]; } }; - -} \ No newline at end of file +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageParser.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageParser.java new file mode 100644 index 0000000..19143bc --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageParser.java @@ -0,0 +1,725 @@ +package android.content.pm; + +import android.annotation.SuppressLint; +import android.content.ComponentName; +import android.content.IntentFilter; +import android.content.res.TypedArray; +import android.os.Bundle; +import android.util.ArrayMap; +import android.util.ArraySet; +import android.util.DisplayMetrics; + +import java.io.File; +import java.io.PrintWriter; +import java.security.PublicKey; +import java.security.cert.Certificate; +import java.util.ArrayList; +import java.util.List; +import java.util.Set; + +public class PackageParser { + public final static int PARSE_IS_SYSTEM = 1; + public final static int PARSE_CHATTY = 1 << 1; + public final static int PARSE_MUST_BE_APK = 1 << 2; + public final static int PARSE_IGNORE_PROCESSES = 1 << 3; + public final static int PARSE_FORWARD_LOCK = 1 << 4; + public final static int PARSE_EXTERNAL_STORAGE = 1 << 5; + public final static int PARSE_IS_SYSTEM_DIR = 1 << 6; + public final static int PARSE_IS_PRIVILEGED = 1 << 7; + public final static int PARSE_COLLECT_CERTIFICATES = 1 << 8; + public final static int PARSE_TRUSTED_OVERLAY = 1 << 9; + + public static class NewPermissionInfo { + public final String name; + public final int sdkVersion; + public final int fileVersion; + + public NewPermissionInfo(String name, int sdkVersion, int fileVersion) { + throw new RuntimeException("Stub!"); + } + } + + public static class SplitPermissionInfo { + public final String rootPerm; + public final String[] newPerms; + public final int targetSdk; + + public SplitPermissionInfo(String rootPerm, String[] newPerms, int targetSdk) { + throw new RuntimeException("Stub!"); + } + } + + public static final PackageParser.NewPermissionInfo[] NEW_PERMISSIONS = new PackageParser.NewPermissionInfo[]{ + new PackageParser.NewPermissionInfo(android.Manifest.permission.WRITE_EXTERNAL_STORAGE, android.os.Build.VERSION_CODES.DONUT, 0), + new PackageParser.NewPermissionInfo(android.Manifest.permission.READ_PHONE_STATE, android.os.Build.VERSION_CODES.DONUT, 0) + }; + + static class ParsePackageItemArgs { + final Package owner; + final String[] outError; + final int nameRes; + final int labelRes; + final int iconRes; + final int logoRes; + final int bannerRes; + + String tag; + TypedArray sa; + + ParsePackageItemArgs(final Package owner, final String[] outError, final int nameRes, final int labelRes, final int iconRes, final int logoRes, final int bannerRes) { + throw new RuntimeException("Stub!"); + } + } + + static class ParseComponentArgs extends ParsePackageItemArgs { + final String[] sepProcesses; + final int processRes; + final int descriptionRes; + final int enabledRes; + int flags; + + ParseComponentArgs(final Package owner, final String[] outError, final int nameRes, final int labelRes, final int iconRes, final int logoRes, final int bannerRes, final String[] sepProcesses, final int processRes, final int descriptionRes, final int enabledRes) { + super(owner, outError, nameRes, labelRes, iconRes, logoRes, bannerRes); + throw new RuntimeException("Stub!"); + } + } + + public static class PackageLite { + public final String packageName; + public final int versionCode; + public final int installLocation; + public final VerifierInfo[] verifiers; + + // Names of any split APKs, ordered by parsed splitName. + public final String[] splitNames; + + /** + * Path where this package was found on disk. For monolithic packages + * this is path to single base APK file; for cluster packages this is + * path to the cluster directory. + */ + public final String codePath; + + // Path of base APK. + public final String baseCodePath; + // Paths of any split APKs, ordered by parsed splitName. + public final String[] splitCodePaths; + + // Revision code of base APK. + public final int baseRevisionCode; + // Revision codes of any split APKs, ordered by parsed splitName. + public final int[] splitRevisionCodes; + + public final boolean coreApp; + public final boolean multiArch; + public final boolean extractNativeLibs; + + public PackageLite(final String codePath, final ApkLite baseApk, final String[] splitNames, final String[] splitCodePaths, final int[] splitRevisionCodes) { + throw new RuntimeException("Stub!"); + } + + public List getAllCodePaths() { + throw new RuntimeException("Stub!"); + } + } + + public static class ApkLite { + public final String codePath; + public final String packageName; + public final String splitName; + public final int versionCode; + public final int revisionCode; + public final int installLocation; + public final VerifierInfo[] verifiers; + public final Signature[] signatures; + public final boolean coreApp; + public final boolean multiArch; + public final boolean extractNativeLibs; + + public ApkLite(final String codePath, final String packageName, final String splitName, final int versionCode, final int revisionCode, final int installLocation, final List verifiers, final Signature[] signatures, final boolean coreApp, final boolean multiArch, final boolean extractNativeLibs) { + throw new RuntimeException("Stub!"); + } + } + + /** + * For SDK_INT 29+ + */ + public Callback mCallback; + + public interface Callback { + boolean hasFeature(String feature); + } + + public static final class CallbackImpl implements Callback { + private final PackageManager mPm; + + public CallbackImpl(PackageManager pm) { + mPm = pm; + } + + @Override + public boolean hasFeature(String feature) { + return mPm.hasSystemFeature(feature); + } + } + + public void setCallback(Callback cb) { + mCallback = cb; + } + + /** + * For Android 5.0+ + */ + public PackageParser() { + throw new RuntimeException("Stub!"); + } + + public PackageParser(final String archiveSourcePath) { + throw new RuntimeException("Stub!"); + } + + public void setSeparateProcesses(final String[] procs) { + throw new RuntimeException("Stub!"); + } + + public void setOnlyCoreApps(final boolean onlyCoreApps) { + throw new RuntimeException("Stub!"); + } + + public void setDisplayMetrics(final DisplayMetrics metrics) { + throw new RuntimeException("Stub!"); + } + + public static boolean isApkFile(final File file) { + throw new RuntimeException("Stub!"); + } + + public static PackageInfo generatePackageInfo(final PackageParser.Package p, final int[] gids, final int flags, final long firstInstallTime, final long lastUpdateTime, final Set grantedPermissions, final PackageUserState state) { + throw new RuntimeException("Stub!"); + } + + public static boolean isAvailable(final PackageUserState state) { + throw new RuntimeException("Stub!"); + } + + public static PackageInfo generatePackageInfo(final PackageParser.Package p, final int[] gids, final int flags, final long firstInstallTime, final long lastUpdateTime, final Set grantedPermissions, final PackageUserState state, final int userId) { + throw new RuntimeException("Stub!"); + } + + /** + * Parse only lightweight details about the package at the given location. + * Automatically detects if the package is a monolithic style (single APK + * file) or cluster style (directory of APKs). + *

+ * This performs sanity checking on cluster style packages, such as + * requiring identical package name and version codes, a single base APK, + * and unique split names. + * + * @see PackageParser#parsePackage(File, int) + */ + public static PackageLite parsePackageLite(final File packageFile, final int flags) throws PackageParserException { + throw new RuntimeException("Stub!"); + } + + /** + * Parse the package at the given location. Automatically detects if the + * package is a monolithic style (single APK file) or cluster style + * (directory of APKs). + *

+ * This performs sanity checking on cluster style packages, such as + * requiring identical package name and version codes, a single base APK, + * and unique split names. + *

+ * Note that this does not perform signature verification; that + * must be done separately in {@link #collectCertificates(Package, int)}. + * + * @see #parsePackageLite(File, int) + * @since Android 5.0+ + */ + public Package parsePackage(final File packageFile, final int flags) throws PackageParserException { + throw new RuntimeException("Stub!"); + } + + /** + * @param sourceFile + * @param destCodePath + * @param metrics + * @param flags + * @return + * @since Android 2.3+ + */ + public Package parsePackage(final File sourceFile, final String destCodePath, final DisplayMetrics metrics, final int flags) { + throw new RuntimeException("Stub!"); + } + + public void collectManifestDigest(final Package pkg) throws PackageParserException { + throw new RuntimeException("Stub!"); + } + + public void collectCertificates(final Package pkg, final int flags) throws PackageParserException { + throw new RuntimeException("Stub!"); + } + + /** + * Utility method that retrieves lightweight details about a single APK + * file, including package name, split name, and install location. + * + * @param apkFile path to a single APK + * @param flags optional parse flags, such as + * {@link #PARSE_COLLECT_CERTIFICATES} + */ + public static ApkLite parseApkLite(final File apkFile, final int flags) throws PackageParserException { + throw new RuntimeException("Stub!"); + } + + /** + * Representation of a full package parsed from APK files on disk. A package + * consists of a single base APK, and zero or more split APKs. + */ + public final static class Package { + public String packageName; + + // Names of any split APKs, ordered by parsed splitName. + public String[] splitNames; + + // TODO: Work towards making these paths invariant. + public String volumeUuid; + + /** + * Path where this package was found on disk. For monolithic packages + * this is path to single base APK file; for cluster packages this is + * path to the cluster directory. + */ + public String codePath; + + // Path of base APK. + public String baseCodePath; + // Paths of any split APKs, ordered by parsed splitName. + public String[] splitCodePaths; + + // Revision code of base APK. + public int baseRevisionCode; + // Revision codes of any split APKs, ordered by parsed splitName. + public int[] splitRevisionCodes; + + // Flags of any split APKs; ordered by parsed splitName. + public int[] splitFlags; + + /** + * Private flags of any split APKs; ordered by parsed splitName. + * + * {@hide} + */ + public int[] splitPrivateFlags; + + public boolean baseHardwareAccelerated; + + // For now we only support one application per package. + public ApplicationInfo applicationInfo = new ApplicationInfo(); + + public final ArrayList permissions = new ArrayList<>(0); + public final ArrayList permissionGroups = new ArrayList<>(0); + public final ArrayList activities = new ArrayList<>(0); + public final ArrayList receivers = new ArrayList<>(0); + public final ArrayList providers = new ArrayList<>(0); + public final ArrayList services = new ArrayList<>(0); + public final ArrayList instrumentation = new ArrayList<>(0); + + public final ArrayList requestedPermissions = new ArrayList<>(); + + public ArrayList protectedBroadcasts; + + public ArrayList libraryNames = null; + public ArrayList usesLibraries = null; + public ArrayList usesOptionalLibraries = null; + public String[] usesLibraryFiles = null; + + public ArrayList preferredActivityFilters = null; + + public ArrayList mOriginalPackages = null; + public String mRealPackage = null; + public ArrayList mAdoptPermissions = null; + + // We store the application meta-data independently to avoid multiple unwanted references + public Bundle mAppMetaData = null; + + // The version code declared for this package. + public int mVersionCode; + + // The version name declared for this package. + public String mVersionName; + + // The shared user id that this package wants to use. + public String mSharedUserId; + + // The shared user label that this package wants to use. + public int mSharedUserLabel; + + // Signatures that were read from the package. + public Signature[] mSignatures; + public SigningDetails mSigningDetails; + public Certificate[][] mCertificates; + + // For use by package manager service for quick lookup of + // preferred up order. + public int mPreferredOrder = 0; + + // For use by package manager to keep track of where it needs to do dexopt. + // public final ArraySet mDexOptPerformed = new ArraySet<>(4); + + // For use by package manager to keep track of when a package was last used. + public long mLastPackageUsageTimeInMills; + + // User set enabled state. + // public int mSetEnabled = PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; + + // Whether the package has been stopped. + // public boolean mSetStopped = false; + + // Additional data supplied by callers. + public Object mExtras; + + // Applications hardware preferences + public ArrayList configPreferences = null; + + // Applications requested features + public ArrayList reqFeatures = null; + + // Applications requested feature groups + public ArrayList featureGroups = null; + + public int installLocation; + + public boolean coreApp; + + // An app that's required for all users and cannot be uninstalled for a user. + public boolean mRequiredForAllUsers; + + // The restricted account authenticator type that is used by this application. + public String mRestrictedAccountType; + + // The required account type without which this application will not function. + public String mRequiredAccountType; + + /** + * Digest suitable for comparing whether this package's manifest is the + * same as another. + */ + public ManifestDigest manifestDigest; + + public String mOverlayTarget; + public int mOverlayPriority; + public boolean mTrustedOverlay; + + /** + * Data used to feed the KeySetManagerService + */ + public ArraySet mSigningKeys; + public ArraySet mUpgradeKeySets; + public ArrayMap> mKeySetMapping; + + /** + * The install time abi override for this package, if any. + * + * TODO: This seems like a horrible place to put the abiOverride because + * this isn't something the packageParser parsers. However, this fits in with + * the rest of the PackageManager where package scanning randomly pushes + * and prods fields out of {@code this.applicationInfo}. + */ + public String cpuAbiOverride; + + public Package(String packageName) { + throw new RuntimeException("Stub!"); + } + + public List getAllCodePaths() { + throw new RuntimeException("Stub!"); + } + + /** + * Filtered set of {@link #getAllCodePaths()} that excludes + * resource-only APKs. + */ + public List getAllCodePathsExcludingResourceOnly() { + throw new RuntimeException("Stub!"); + } + + public void setPackageName(final String newName) { + throw new RuntimeException("Stub!"); + } + + public boolean hasComponentClassName(final String name) { + throw new RuntimeException("Stub!"); + } + + public boolean isForwardLocked() { + throw new RuntimeException("Stub!"); + } + + public boolean isSystemApp() { + throw new RuntimeException("Stub!"); + } + + public boolean isPrivilegedApp() { + throw new RuntimeException("Stub!"); + } + + public boolean isUpdatedSystemApp() { + throw new RuntimeException("Stub!"); + } + + public boolean canHaveOatDir() { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public static class Component { + public final Package owner; + public final ArrayList intents; + public final String className; + public Bundle metaData; + + ComponentName componentName; + String componentShortName; + + public Component(final Package owner) { + throw new RuntimeException("Stub!"); + } + + public Component(final ParsePackageItemArgs args, final PackageItemInfo outInfo) { + throw new RuntimeException("Stub!"); + } + + public Component(final ParseComponentArgs args, final ComponentInfo outInfo) { + throw new RuntimeException("Stub!"); + } + + public Component(final Component clone) { + throw new RuntimeException("Stub!"); + } + + public ComponentName getComponentName() { + throw new RuntimeException("Stub!"); + } + + public void appendComponentShortName(final StringBuilder sb) { + throw new RuntimeException("Stub!"); + } + + public void printComponentShortName(final PrintWriter pw) { + throw new RuntimeException("Stub!"); + } + + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + } + + public final static class Permission extends Component { + public final PermissionInfo info; + public boolean tree; + public PermissionGroup group; + + public Permission(final Package owner) { + super(owner); + throw new RuntimeException("Stub!"); + } + + public Permission(final Package owner, final PermissionInfo info) { + super(owner); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public final static class PermissionGroup extends Component { + public final PermissionGroupInfo info; + + public PermissionGroup(final Package owner) { + super(owner); + throw new RuntimeException("Stub!"); + } + + public PermissionGroup(final Package owner, final PermissionGroupInfo info) { + super(owner); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public final static class Activity extends Component { + public final ActivityInfo info; + + public Activity(final ParseComponentArgs args, final ActivityInfo info) { + super(args, info); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public final static class Service extends Component { + public final ServiceInfo info; + + public Service(final ParseComponentArgs args, final ServiceInfo info) { + super(args, info); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public final static class Provider extends Component { + public final ProviderInfo info; + public boolean syncable; + + public Provider(final ParseComponentArgs args, final ProviderInfo info) { + super(args, info); + throw new RuntimeException("Stub!"); + } + + public Provider(final Provider existingProvider) { + super(existingProvider); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public final static class Instrumentation extends Component { + public final InstrumentationInfo info; + + public Instrumentation(final ParsePackageItemArgs args, final InstrumentationInfo info) { + super(args, info); + throw new RuntimeException("Stub!"); + } + + @Override + public void setPackageName(final String packageName) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + @SuppressLint("ParcelCreator") + public static class IntentInfo extends IntentFilter { + public boolean hasDefault; + public int labelRes; + public CharSequence nonLocalizedLabel; + public int icon; + public int logo; + public int banner; + public int preferred; + } + + @SuppressLint("ParcelCreator") + public final static class ActivityIntentInfo extends IntentInfo { + public final Activity activity; + + public ActivityIntentInfo(final Activity activity) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + @SuppressLint("ParcelCreator") + public final static class ServiceIntentInfo extends IntentInfo { + public final Service service; + + public ServiceIntentInfo(final Service service) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + @SuppressLint("ParcelCreator") + public static final class ProviderIntentInfo extends IntentInfo { + public final Provider provider; + + public ProviderIntentInfo(final Provider provider) { + throw new RuntimeException("Stub!"); + } + + @Override + public String toString() { + throw new RuntimeException("Stub!"); + } + } + + public static class PackageParserException extends Exception { + public PackageParserException(int error, String detailMessage) { + super(detailMessage); + throw new RuntimeException("Stub!"); + } + + public PackageParserException(int error, String detailMessage, Throwable throwable) { + super(detailMessage, throwable); + throw new RuntimeException("Stub!"); + } + } + + public static class SigningDetails { + public static final SigningDetails UNKNOWN = null; + public Signature[] signatures; + public Signature[] pastSigningCertificates; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageUserState.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageUserState.java new file mode 100644 index 0000000..ceb1b7e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/PackageUserState.java @@ -0,0 +1,28 @@ +package android.content.pm; + +import android.util.ArraySet; + +public class PackageUserState { + public boolean stopped; + public boolean notLaunched; + public boolean installed; + public boolean hidden; // Is the app restricted by owner/admin + public int enabled; + public boolean blockUninstall; + + public String lastDisableAppCaller; + + public ArraySet disabledComponents; + public ArraySet enabledComponents; + + public int domainVerificationStatus; + public int appLinkGeneration; + + public PackageUserState() { + throw new RuntimeException("Stub!"); + } + + public PackageUserState(final PackageUserState o) { + throw new RuntimeException("Stub!"); + } +} diff --git a/520ApkBox/BCore/black-fake/src/main/java/android/content/pm/VerifierInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/VerifierInfo.java similarity index 89% rename from 520ApkBox/BCore/black-fake/src/main/java/android/content/pm/VerifierInfo.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/VerifierInfo.java index a8bfabc..3db1c2d 100644 --- a/520ApkBox/BCore/black-fake/src/main/java/android/content/pm/VerifierInfo.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/content/pm/VerifierInfo.java @@ -5,16 +5,7 @@ import java.security.PublicKey; -/** - * Created by Milk on 2021/5/7. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class VerifierInfo implements Parcelable { - public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { public VerifierInfo createFromParcel(final Parcel source) { return new VerifierInfo(source); @@ -42,4 +33,4 @@ public int describeContents() { public void writeToParcel(final Parcel dest, final int flags) { throw new RuntimeException("Stub!"); } -} \ No newline at end of file +} diff --git a/520ApkBox/BCore/black-fake/src/main/java/android/location/LocationRequest.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/location/LocationRequest.java similarity index 81% rename from 520ApkBox/BCore/black-fake/src/main/java/android/location/LocationRequest.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/android/location/LocationRequest.java index 6737f2f..85c7448 100644 --- a/520ApkBox/BCore/black-fake/src/main/java/android/location/LocationRequest.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/location/LocationRequest.java @@ -4,12 +4,6 @@ import android.os.Parcelable; public final class LocationRequest implements Parcelable { - - public String getProvider() { - return null; - } - - public static final Creator CREATOR = new Creator() { @Override public LocationRequest createFromParcel(Parcel in) { @@ -28,6 +22,5 @@ public int describeContents() { } @Override - public void writeToParcel(Parcel dest, int flags) { - } -} \ No newline at end of file + public void writeToParcel(Parcel dest, int flags) { } +} diff --git a/520ApkBox/BCore/black-fake/src/main/java/android/os/ParcelableException.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/os/ParcelableException.java similarity index 100% rename from 520ApkBox/BCore/black-fake/src/main/java/android/os/ParcelableException.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/android/os/ParcelableException.java diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/android/os/ServiceManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/os/ServiceManager.java new file mode 100644 index 0000000..e9b6276 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/android/os/ServiceManager.java @@ -0,0 +1,7 @@ +package android.os; + +public class ServiceManager { + public static IBinder getService(String name) { + throw new UnsupportedOperationException("Stub!"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/Reflector.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/Reflector.java new file mode 100644 index 0000000..58aafff --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/Reflector.java @@ -0,0 +1,342 @@ +package black; + +import android.os.Build; +import android.util.Log; + +import org.lsposed.hiddenapibypass.HiddenApiBypass; + +import java.lang.reflect.AccessibleObject; +import java.lang.reflect.Constructor; +import java.lang.reflect.Field; +import java.lang.reflect.Member; +import java.lang.reflect.Method; +import java.util.List; + +@SuppressWarnings({"WeakerAccess", "unchecked"}) +public class Reflector { + private static final String TAG = "Reflector"; + private final Class mClazz; + + private Reflector(Class clazz) { + mClazz = clazz; + } + + public Class getClazz() { + return mClazz; + } + + public static Reflector on(String name) { + return new Reflector(findClass(name)); + } + + public static MethodWrapper wrap(Method method) { + return new MethodWrapper<>(method); + } + + public static StaticMethodWrapper wrapStatic(Method method) { + return new StaticMethodWrapper<>(method); + } + + public MethodWrapper method(String name, Class... parameterTypes) { + return method(mClazz, name, parameterTypes); + } + + public static MethodWrapper method(Class clazz, String name, Class... parameterTypes) { + Method method = getMethod(clazz, name, parameterTypes); + if ((parameterTypes == null || parameterTypes.length == 0) && method == null) { + method = findMethodNoChecks(clazz, name); + } + return wrap(method); + } + + public StaticMethodWrapper staticMethod(String name, Class... parameterTypes) { + return staticMethod(mClazz, name, parameterTypes); + } + + public static StaticMethodWrapper staticMethod(Class clazz, String name, Class... parameterTypes) { + Method method = getMethod(clazz, name, parameterTypes); + if ((parameterTypes == null || parameterTypes.length == 0) && method == null) { + method = findMethodNoChecks(clazz, name); + } + return wrapStatic(method); + } + + public static FieldWrapper wrap(Field field) { + return new FieldWrapper<>(field); + } + + public FieldWrapper field(String name) { + return field(mClazz, name); + } + + public static FieldWrapper field(Class clazz, String name) { + return wrap(getField(clazz, name)); + } + + public static ConstructorWrapper wrap(Constructor constructor) { + return new ConstructorWrapper<>(constructor); + } + + public ConstructorWrapper constructor(Class... parameterTypes) { + return wrap(getConstructor(mClazz, parameterTypes)); + } + + public static Class findClass(String name) { + try { + return Class.forName(name); + } catch (ClassNotFoundException e) { + Log.e(TAG, e.getMessage()); + } + return null; + } + + public static Method getMethod(Class clazz, String name, Class... parameterTypes) { + return findMethod(clazz, name, parameterTypes); + } + + public static Method findMethod(Class clazz, String name, Class... parameterTypes) { + checkForFindMethod(parameterTypes); + return findMethodNoChecks(clazz, name, parameterTypes); + } + + public static Method findMethodNoChecks(Class clazz, String name, Class... parameterTypes) { + while (clazz != null) { + try { + Method method = clazz.getDeclaredMethod(name, parameterTypes); + method.setAccessible(true); + return method; + } catch (NoSuchMethodException e) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { + try { + Method method = HiddenApiBypass.getDeclaredMethod(clazz, name, parameterTypes); + method.setAccessible(true); + return method; + } catch (Exception ignored) { } + } + } + clazz = clazz.getSuperclass(); + } + return null; + } + + public static Method findMethodNoChecks(Class clazz, String name) { + try { + Method[] methods = clazz.getDeclaredMethods(); + for (Method method : methods) { + if (method.getName().equals(name)) { + method.setAccessible(true); + return method; + } + } + } catch (Throwable e) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { + List methods = HiddenApiBypass.getDeclaredMethods(clazz); + for (Method method : methods) { + if (method.getName().equals(name)) { + method.setAccessible(true); + return method; + } + } + } + } + return null; + } + + public static Field getField(Class clazz, String name) { + return findField(clazz, name); + } + + public static Field findField(Class clazz, String name) { + return findFieldNoChecks(clazz, name); + } + + public static Field findFieldNoChecks(Class clazz, String name) { + while (clazz != null) { + try { + Field field = clazz.getDeclaredField(name); + field.setAccessible(true); + return field; + } catch (NoSuchFieldException e) { + try { + return findInstanceField(clazz, name); + } catch (NoSuchFieldException ex) { + try { + return findStaticField(clazz, name); + } catch (NoSuchFieldException ignored) { } + } + } + clazz = clazz.getSuperclass(); + } + return null; + } + + public static Constructor getConstructor(Class clazz, Class... parameterTypes) { + return findConstructor(clazz, parameterTypes); + } + + public static Constructor findConstructor(Class clazz, Class... parameterTypes) { + checkForFindConstructor(parameterTypes); + return findConstructorNoChecks(clazz, parameterTypes); + } + + public static Constructor findConstructorNoChecks(Class clazz, Class... parameterTypes) { + try { + Constructor constructor = (Constructor) clazz.getDeclaredConstructor(parameterTypes); + constructor.setAccessible(true); + return constructor; + } catch (NoSuchMethodException e) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { + try { + Constructor constructor = (Constructor) HiddenApiBypass.getDeclaredConstructor(clazz, parameterTypes); + constructor.setAccessible(true); + return constructor; + } catch (Exception ignored) { } + } + } + return null; + } + + private static Field findInstanceField(Class clazz, String name) throws NoSuchFieldException { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { + List fields = HiddenApiBypass.getInstanceFields(clazz); + for (Field field : fields) { + if (field.getName().equals(name)) { + field.setAccessible(true); + return field; + } + } + } + throw new NoSuchFieldException(); + } + + private static Field findStaticField(Class clazz, String name) throws NoSuchFieldException { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) { + List fields = HiddenApiBypass.getStaticFields(clazz); + for (Field field : fields) { + if (field.getName().equals(name)) { + field.setAccessible(true); + return field; + } + } + } + throw new NoSuchFieldException(); + } + + private static void checkForFindMethod(Class... parameterTypes) { + if (parameterTypes != null) { + for (int i = 0; i < parameterTypes.length; i++) { + if (parameterTypes[i] == null) { + throw new NullPointerException("parameterTypes[" + i + "] == null"); + } + } + } + } + + private static void checkForFindConstructor(Class... parameterTypes) { + if (parameterTypes != null) { + for (int i = 0; i < parameterTypes.length; i++) { + if (parameterTypes[i] == null) { + throw new NullPointerException("parameterTypes[" + i + "] == null"); + } + } + } + } + + public static class MemberWrapper { + M member; + + MemberWrapper(M member) { + if (member == null) { + return; + } + + member.setAccessible(true); + this.member = member; + } + } + + public static class MethodWrapper extends MemberWrapper { + MethodWrapper(Method method) { + super(method); + } + + public T call(Object instance, Object... args) { + try { + return (T) member.invoke(instance, args); + } catch (Throwable e) { + e.printStackTrace(); + } + return null; + } + } + + public static class StaticMethodWrapper extends MemberWrapper { + StaticMethodWrapper(Method method) { + super(method); + } + + public T call(Object... args) { + try { + return (T) member.invoke(null, args); + } catch (Throwable e) { + e.printStackTrace(); + } + return null; + } + + public R callWithClass(Object... args) { + try { + return (R) member.invoke(null, args); + } catch (Throwable e) { + e.printStackTrace(); + } + return null; + } + } + + public static class FieldWrapper extends MemberWrapper { + FieldWrapper(Field field) { + super(field); + } + + public T get(Object instance) { + try { + return (T) member.get(instance); + } catch (Throwable e) { + e.printStackTrace(); + } + return null; + } + + public T get() { + return get(null); + } + + public void set(Object instance, Object value) { + try { + member.set(instance, value); + } catch (Throwable e) { + e.printStackTrace(); + } + } + + public void set(Object value) { + set(null, value); + } + } + + public static class ConstructorWrapper extends MemberWrapper> { + ConstructorWrapper(Constructor constructor) { + super(constructor); + } + + public T newInstance(Object... args) { + try { + return member.newInstance(args); + } catch (Throwable e) { + e.printStackTrace(); + } + return null; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/accounts/IAccountManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/accounts/IAccountManager.java new file mode 100644 index 0000000..59a3f5e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/accounts/IAccountManager.java @@ -0,0 +1,13 @@ +package black.android.accounts; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAccountManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.accounts.IAccountManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Activity.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Activity.java new file mode 100644 index 0000000..dc7568c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Activity.java @@ -0,0 +1,18 @@ +package black.android.app; + +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.os.IBinder; + +import black.Reflector; + +public class Activity { + public static final Reflector REF = Reflector.on("android.app.Activity"); + + public static Reflector.FieldWrapper mActivityInfo = REF.field("mActivityInfo"); + public static Reflector.FieldWrapper mFinished = REF.field("mFinished"); + public static Reflector.FieldWrapper mParent = REF.field("mParent"); + public static Reflector.FieldWrapper mResultCode = REF.field("mResultCode"); + public static Reflector.FieldWrapper mResultData = REF.field("mResultData"); + public static Reflector.FieldWrapper mToken = REF.field("mToken"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityClient.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityClient.java new file mode 100644 index 0000000..e8e1ab0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityClient.java @@ -0,0 +1,20 @@ +package black.android.app; + +import android.os.IInterface; + +import black.Reflector; + +public class ActivityClient { + public static final Reflector REF = Reflector.on("android.app.ActivityClient"); + + public static Reflector.FieldWrapper INTERFACE_SINGLETON = REF.field("INTERFACE_SINGLETON"); + + public static Reflector.StaticMethodWrapper getInstance = REF.staticMethod("getInstance"); + public static Reflector.StaticMethodWrapper getActivityClientController = REF.staticMethod("getActivityClientController"); + + public static class ActivityClientControllerSingleton { + public static final Reflector REF = Reflector.on("android.app.ActivityClient$ActivityClientControllerSingleton"); + + public static Reflector.FieldWrapper mKnownInstance = REF.field("mKnownInstance"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerNative.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerNative.java new file mode 100644 index 0000000..26c0fb7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerNative.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IInterface; + +import black.Reflector; + +public class ActivityManagerNative { + public static final Reflector REF = Reflector.on("android.app.ActivityManagerNative"); + + public static Reflector.FieldWrapper gDefault = REF.field("gDefault"); + + public static Reflector.StaticMethodWrapper getDefault = REF.staticMethod("getDefault"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerOreo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerOreo.java new file mode 100644 index 0000000..eb2fef4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityManagerOreo.java @@ -0,0 +1,9 @@ +package black.android.app; + +import black.Reflector; + +public class ActivityManagerOreo { + public static final Reflector REF = Reflector.on("android.app.ActivityManager"); + + public static Reflector.FieldWrapper IActivityManagerSingleton = REF.field("IActivityManagerSingleton"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityTaskManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityTaskManager.java new file mode 100644 index 0000000..ba43c9f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityTaskManager.java @@ -0,0 +1,9 @@ +package black.android.app; + +import black.Reflector; + +public class ActivityTaskManager { + public static final Reflector REF = Reflector.on("android.app.ActivityTaskManager"); + + public static Reflector.FieldWrapper IActivityTaskManagerSingleton = REF.field("IActivityTaskManagerSingleton"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThread.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThread.java new file mode 100644 index 0000000..6e0cec4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThread.java @@ -0,0 +1,87 @@ +package black.android.app; + +import android.app.Activity; +import android.app.Application; +import android.app.ContentProviderHolder; +import android.app.Instrumentation; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ApplicationInfo; +import android.content.pm.ProviderInfo; +import android.content.pm.ServiceInfo; +import android.os.Handler; +import android.os.IBinder; +import android.os.IInterface; + +import java.util.List; +import java.util.Map; + +import black.Reflector; + +public class ActivityThread { + public static final Reflector REF = Reflector.on("android.app.ActivityThread"); + + public static Reflector.FieldWrapper sPackageManager = REF.field("sPackageManager"); + public static Reflector.FieldWrapper sPermissionManager = REF.field("sPermissionManager"); + public static Reflector.FieldWrapper> mActivities = REF.field("mActivities"); + public static Reflector.FieldWrapper mBoundApplication = REF.field("mBoundApplication"); + public static Reflector.FieldWrapper mH = REF.field("mH"); + public static Reflector.FieldWrapper mInitialApplication = REF.field("mInitialApplication"); + public static Reflector.FieldWrapper mInstrumentation = REF.field("mInstrumentation"); + public static Reflector.FieldWrapper> mProviderMap = REF.field("mProviderMap"); + + public static Reflector.StaticMethodWrapper currentActivityThread = REF.staticMethod("currentActivityThread"); + + public static Reflector.MethodWrapper getApplicationThread = REF.method("getApplicationThread"); + public static Reflector.MethodWrapper getSystemContext = REF.method("getSystemContext"); + public static Reflector.MethodWrapper getLaunchingActivity = REF.method("getLaunchingActivity", IBinder.class); + public static Reflector.MethodWrapper performNewIntents = REF.method("performNewIntents", IBinder.class, List.class); + public static Reflector.MethodWrapper installProvider = REF.method("installProvider", Context.class, ContentProviderHolder.class, ProviderInfo.class, boolean.class, boolean.class, boolean.class); + + public static class CreateServiceData { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$CreateServiceData"); + + public static Reflector.FieldWrapper info = REF.field("info"); + } + + public static class H { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$H"); + + public static Reflector.FieldWrapper CREATE_SERVICE = REF.field("CREATE_SERVICE"); + public static Reflector.FieldWrapper EXECUTE_TRANSACTION = REF.field("EXECUTE_TRANSACTION"); + public static Reflector.FieldWrapper LAUNCH_ACTIVITY = REF.field("LAUNCH_ACTIVITY"); + } + + public static class AppBindData { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$AppBindData"); + + public static Reflector.FieldWrapper appInfo = REF.field("appInfo"); + public static Reflector.FieldWrapper info = REF.field("info"); + public static Reflector.FieldWrapper instrumentationName = REF.field("instrumentationName"); + public static Reflector.FieldWrapper processName = REF.field("processName"); + public static Reflector.FieldWrapper> providers = REF.field("providers"); + } + + public static class ProviderClientRecordP { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$ProviderClientRecord"); + + public static Reflector.FieldWrapper mNames = REF.field("mNames"); + public static Reflector.FieldWrapper mProvider = REF.field("mProvider"); + } + + public static class ActivityClientRecord { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$ActivityClientRecord"); + + public static Reflector.FieldWrapper activity = REF.field("activity"); + public static Reflector.FieldWrapper activityInfo = REF.field("activityInfo"); + public static Reflector.FieldWrapper intent = REF.field("intent"); + public static Reflector.FieldWrapper token = REF.field("token"); + public static Reflector.FieldWrapper packageInfo = REF.field("packageInfo"); + } + + public static class AndroidOs { + public static final Reflector REF = Reflector.on("android.app.ActivityThread$AndroidOs"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadNMR1.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadNMR1.java new file mode 100644 index 0000000..9c13751 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadNMR1.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IBinder; + +import java.util.List; + +import black.Reflector; + +public class ActivityThreadNMR1 { + public static final Reflector REF = Reflector.on("android.app.ActivityThread"); + + public static Reflector.MethodWrapper performNewIntents = REF.method("performNewIntents", IBinder.class, List.class, boolean.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadQ.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadQ.java new file mode 100644 index 0000000..5e366e1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ActivityThreadQ.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IBinder; + +import java.util.List; + +import black.Reflector; + +public class ActivityThreadQ { + public static final Reflector REF = Reflector.on("android.app.ActivityThread"); + + public static Reflector.MethodWrapper handleNewIntent = REF.method("handleNewIntent", IBinder.class, List.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/AppOpsManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/AppOpsManager.java new file mode 100644 index 0000000..31f7b23 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/AppOpsManager.java @@ -0,0 +1,11 @@ +package black.android.app; + +import android.os.IInterface; + +import black.Reflector; + +public class AppOpsManager { + public static final Reflector REF = Reflector.on("android.app.AppOpsManager"); + + public static Reflector.FieldWrapper mService = REF.field("mService"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationPackageManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationPackageManager.java new file mode 100644 index 0000000..cc46376 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationPackageManager.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.os.IInterface; + +import black.Reflector; + +public class ApplicationPackageManager { + public static final Reflector REF = Reflector.on("android.app.ApplicationPackageManager"); + + public static Reflector.FieldWrapper mPM = REF.field("mPM"); + public static Reflector.FieldWrapper mPermissionManager = REF.field("mPermissionManager"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationThreadNative.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationThreadNative.java new file mode 100644 index 0000000..2f043f9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ApplicationThreadNative.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ApplicationThreadNative { + public static final Reflector REF = Reflector.on("android.app.ApplicationThreadNative"); + + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImpl.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImpl.java new file mode 100644 index 0000000..aea6aec --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImpl.java @@ -0,0 +1,17 @@ +package black.android.app; + +import android.content.Context; +import android.content.pm.PackageManager; + +import black.Reflector; + +public class ContextImpl { + public static final Reflector REF = Reflector.on("android.app.ContextImpl"); + + public static Reflector.FieldWrapper mBasePackageName = REF.field("mBasePackageName"); + public static Reflector.FieldWrapper mPackageInfo = REF.field("mPackageInfo"); + public static Reflector.FieldWrapper mPackageManager = REF.field("mPackageManager"); + + public static Reflector.MethodWrapper setOuterContext = REF.method("setOuterContext", Context.class); + public static Reflector.MethodWrapper getAttributionSource = REF.method("getAttributionSource"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImplKitkat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImplKitkat.java new file mode 100644 index 0000000..7639f91 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ContextImplKitkat.java @@ -0,0 +1,9 @@ +package black.android.app; + +import black.Reflector; + +public class ContextImplKitkat { + public static final Reflector REF = Reflector.on("android.app.ContextImpl"); + + public static Reflector.FieldWrapper mOpPackageName = REF.field("mOpPackageName"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManager.java new file mode 100644 index 0000000..69b8861 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManager.java @@ -0,0 +1,24 @@ +package black.android.app; + +import android.content.Intent; +import android.content.pm.ProviderInfo; +import android.os.Bundle; +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IActivityManager { + public static final Reflector REF = Reflector.on("android.app.IActivityManager"); + + public static Reflector.MethodWrapper getTaskForActivity = REF.method("getTaskForActivity", IBinder.class, boolean.class); + public static Reflector.MethodWrapper setRequestedOrientation = REF.method("setRequestedOrientation", IBinder.class, int.class); + public static Reflector.MethodWrapper startActivity = REF.method("startActivity", Reflector.findClass("android.app.IApplicationThread"), String.class, Intent.class, String.class, IBinder.class, String.class, int.class, int.class, Reflector.findClass("android.app.ProfilerInfo"), Bundle.class); + + public static class ContentProviderHolder { + public static final Reflector REF = Reflector.on("android.app.IActivityManager$ContentProviderHolder"); + + public static Reflector.FieldWrapper info = REF.field("info"); + public static Reflector.FieldWrapper provider = REF.field("provider"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerL.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerL.java new file mode 100644 index 0000000..f85b432 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerL.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.content.Intent; +import android.os.IBinder; + +import black.Reflector; + +public class IActivityManagerL { + public static final Reflector REF = Reflector.on("android.app.IActivityManager"); + + public static Reflector.MethodWrapper finishActivity = REF.method("finishActivity", IBinder.class, int.class, Intent.class, boolean.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerN.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerN.java new file mode 100644 index 0000000..8b6d49a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityManagerN.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.content.Intent; +import android.os.IBinder; + +import black.Reflector; + +public class IActivityManagerN { + public static final Reflector REF = Reflector.on("android.app.IActivityManager"); + + public static Reflector.MethodWrapper finishActivity = REF.method("finishActivity", IBinder.class, int.class, Intent.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityTaskManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityTaskManager.java new file mode 100644 index 0000000..6cb0aa7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IActivityTaskManager.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IActivityTaskManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.IActivityTaskManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IAlarmManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IAlarmManager.java new file mode 100644 index 0000000..3c55df7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IAlarmManager.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAlarmManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.IAlarmManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IApplicationThread.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IApplicationThread.java new file mode 100644 index 0000000..bfa5395 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IApplicationThread.java @@ -0,0 +1,13 @@ +package black.android.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IApplicationThread { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.IApplicationThread$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ISearchManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ISearchManager.java new file mode 100644 index 0000000..9113708 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/ISearchManager.java @@ -0,0 +1,20 @@ +package black.android.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 19:57 + **/ +public class ISearchManager { + public static final Reflector REF = Reflector.on("android.app.ISearchManager"); + + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.ISearchManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IServiceConnectionO.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IServiceConnectionO.java new file mode 100644 index 0000000..92108e7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/IServiceConnectionO.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.content.ComponentName; +import android.os.IBinder; + +import black.Reflector; + +public class IServiceConnectionO { + public static final Reflector REF = Reflector.on("android.app.IServiceConnection"); + + public static Reflector.MethodWrapper connected = REF.method("connected", ComponentName.class, IBinder.class, boolean.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/LoadedApk.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/LoadedApk.java new file mode 100644 index 0000000..0a6fa25 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/LoadedApk.java @@ -0,0 +1,47 @@ +package black.android.app; + +import android.app.Application; +import android.app.Instrumentation; +//import android.content.IIntentReceiver; +import android.content.ServiceConnection; +import android.content.pm.ApplicationInfo; + +import java.lang.ref.WeakReference; + +import black.Reflector; +import black.android.content.IIntentReceiver; + +public class LoadedApk { + + public static final Reflector REF = Reflector.on("android.app.LoadedApk"); + + public static Reflector.FieldWrapper mApplicationInfo = REF.field("mApplicationInfo"); + public static Reflector.FieldWrapper mSecurityViolation = REF.field("mSecurityViolation"); + + public static Reflector.MethodWrapper getClassLoader = REF.method("getClassLoader"); + public static Reflector.MethodWrapper makeApplication = REF.method("makeApplication", boolean.class, Instrumentation.class); + + public static class ServiceDispatcher { + public static final Reflector REF = Reflector.on("android.app.LoadedApk$ServiceDispatcher"); + + public static Reflector.FieldWrapper mConnection = REF.field("mConnection"); + + public static class InnerConnection { + public static final Reflector REF = Reflector.on("android.app.LoadedApk$ServiceDispatcher$InnerConnection"); + + public static Reflector.FieldWrapper> mDispatcher = REF.field("mDispatcher"); + } + } + + public static class ReceiverDispatcher { + public static final Reflector REF = Reflector.on("android.app.LoadedApk$ReceiverDispatcher"); + + public static Reflector.FieldWrapper mIIntentReceiver = REF.field("mIIntentReceiver"); + + public static class InnerReceiver { + public static final Reflector REF = Reflector.on("android.app.LoadedApk$ReceiverDispatcher$InnerReceiver"); + + public static Reflector.FieldWrapper> mDispatcher = REF.field("mDispatcher"); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannel.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannel.java new file mode 100644 index 0000000..51f41ae --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannel.java @@ -0,0 +1,9 @@ +package black.android.app; + +import black.Reflector; + +public class NotificationChannel { + public static final Reflector REF = Reflector.on("android.app.NotificationChannel"); + + public static Reflector.FieldWrapper mId = REF.field("mId"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannelGroup.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannelGroup.java new file mode 100644 index 0000000..9d0331c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationChannelGroup.java @@ -0,0 +1,12 @@ +package black.android.app; + +import java.util.List; + +import black.Reflector; + +public class NotificationChannelGroup { + public static final Reflector REF = Reflector.on("android.app.NotificationChannelGroup"); + + public static Reflector.FieldWrapper> mChannels = REF.field("mChannels"); + public static Reflector.FieldWrapper mId = REF.field("mId"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationManager.java new file mode 100644 index 0000000..5beca2f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationManager.java @@ -0,0 +1,12 @@ +package black.android.app; + +import android.os.IInterface; + +import black.Reflector; + +public class NotificationManager { + public static final Reflector REF = Reflector.on("android.app.NotificationManager"); + + public static Reflector.FieldWrapper sService = REF.field("sService"); + public static Reflector.StaticMethodWrapper getService = REF.staticMethod("getService"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationO.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationO.java new file mode 100644 index 0000000..b865feb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/NotificationO.java @@ -0,0 +1,10 @@ +package black.android.app; + +import black.Reflector; + +public class NotificationO { + public static final Reflector REF = Reflector.on("android.app.Notification"); + + public static Reflector.FieldWrapper mChannelId = REF.field("mChannelId"); + public static Reflector.FieldWrapper mGroupKey = REF.field("mGroupKey"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Service.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Service.java new file mode 100644 index 0000000..40a7d3c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/Service.java @@ -0,0 +1,14 @@ +package black.android.app; + +import android.app.ActivityThread; +import android.app.Application; +import android.content.Context; +import android.os.IBinder; + +import black.Reflector; + +public class Service { + public static final Reflector REF = Reflector.on("android.app.Service"); + + public static Reflector.MethodWrapper attach = REF.method("attach", Context.class, ActivityThread.class, String.class, IBinder.class, Application.class, Object.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/admin/IDevicePolicyManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/admin/IDevicePolicyManager.java new file mode 100644 index 0000000..279ba7f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/admin/IDevicePolicyManager.java @@ -0,0 +1,13 @@ +package black.android.app.admin; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IDevicePolicyManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.admin.IDevicePolicyManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/IJobScheduler.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/IJobScheduler.java new file mode 100644 index 0000000..cda86f4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/IJobScheduler.java @@ -0,0 +1,13 @@ +package black.android.app.job; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IJobScheduler { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.job.IJobScheduler$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/JobInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/JobInfo.java new file mode 100644 index 0000000..c3f25cd --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/job/JobInfo.java @@ -0,0 +1,11 @@ +package black.android.app.job; + +import android.content.ComponentName; + +import black.Reflector; + +public class JobInfo { + public static final Reflector REF = Reflector.on("android.app.job.JobInfo"); + + public static Reflector.FieldWrapper service = REF.field("service"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/ClientTransaction.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/ClientTransaction.java new file mode 100644 index 0000000..d035c46 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/ClientTransaction.java @@ -0,0 +1,14 @@ +package black.android.app.servertransaction; + +import android.os.IBinder; + +import java.util.List; + +import black.Reflector; + +public class ClientTransaction { + public static final Reflector REF = Reflector.on("android.app.servertransaction.ClientTransaction"); + + public static Reflector.FieldWrapper> mActivityCallbacks = REF.field("mActivityCallbacks"); + public static Reflector.FieldWrapper mActivityToken = REF.field("mActivityToken"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/LaunchActivityItem.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/LaunchActivityItem.java new file mode 100644 index 0000000..17dc90b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/servertransaction/LaunchActivityItem.java @@ -0,0 +1,13 @@ +package black.android.app.servertransaction; + +import android.content.Intent; +import android.content.pm.ActivityInfo; + +import black.Reflector; + +public class LaunchActivityItem { + public static final Reflector REF = Reflector.on("android.app.servertransaction.LaunchActivityItem"); + + public static Reflector.FieldWrapper mInfo = REF.field("mInfo"); + public static Reflector.FieldWrapper mIntent = REF.field("mIntent"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/usage/IStorageStatsManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/usage/IStorageStatsManager.java new file mode 100644 index 0000000..7181003 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/app/usage/IStorageStatsManager.java @@ -0,0 +1,13 @@ +package black.android.app.usage; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IStorageStatsManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.app.usage.IStorageStatsManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/bluetooth/IBluetoothManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/bluetooth/IBluetoothManager.java new file mode 100644 index 0000000..52690d0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/bluetooth/IBluetoothManager.java @@ -0,0 +1,13 @@ +package black.android.bluetooth; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IBluetoothManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.bluetooth.IBluetoothManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSource.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSource.java new file mode 100644 index 0000000..945bc30 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSource.java @@ -0,0 +1,11 @@ +package black.android.content; + +import black.Reflector; + +public class AttributionSource { + public static final Reflector REF = Reflector.on("android.content.AttributionSource"); + + public static Reflector.FieldWrapper mAttributionSourceState = REF.field("mAttributionSourceState"); + + public static Reflector.MethodWrapper getNext = REF.method("getNext"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSourceState.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSourceState.java new file mode 100644 index 0000000..b7c6c7d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/AttributionSourceState.java @@ -0,0 +1,10 @@ +package black.android.content; + +import black.Reflector; + +public class AttributionSourceState { + public static final Reflector REF = Reflector.on("android.content.AttributionSourceState"); + + public static Reflector.FieldWrapper packageName = REF.field("packageName"); + public static Reflector.FieldWrapper uid = REF.field("uid"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/BroadcastReceiver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/BroadcastReceiver.java new file mode 100644 index 0000000..486def9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/BroadcastReceiver.java @@ -0,0 +1,46 @@ +package black.android.content; + +import android.os.Bundle; +import android.os.IBinder; + +import black.Reflector; + +public class BroadcastReceiver { + public static final Reflector REF = Reflector.on("android.content.BroadcastReceiver"); + + public static Reflector.MethodWrapper getPendingResult = REF.method("getPendingResult"); + public static Reflector.MethodWrapper setPendingResult = REF.method("setPendingResult", Reflector.findClass("android.content.BroadcastReceiver$PendingResult")); + + public static class PendingResultM { + public static final Reflector REF = Reflector.on("android.content.BroadcastReceiver$PendingResult"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(int.class, String.class, Bundle.class, int.class, boolean.class, boolean.class, IBinder.class, int.class, int.class); + + public static Reflector.FieldWrapper mAbortBroadcast = REF.field("mAbortBroadcast"); + public static Reflector.FieldWrapper mFinished = REF.field("mFinished"); + public static Reflector.FieldWrapper mFlags = REF.field("mFlags"); + public static Reflector.FieldWrapper mInitialStickyHint = REF.field("mInitialStickyHint"); + public static Reflector.FieldWrapper mOrderedHint = REF.field("mOrderedHint"); + public static Reflector.FieldWrapper mResultData = REF.field("mResultData"); + public static Reflector.FieldWrapper mResultExtras = REF.field("mResultExtras"); + public static Reflector.FieldWrapper mSendingUser = REF.field("mSendingUser"); + public static Reflector.FieldWrapper mToken = REF.field("mToken"); + public static Reflector.FieldWrapper mType = REF.field("mType"); + } + + public static class PendingResult { + public static final Reflector REF = Reflector.on("android.content.BroadcastReceiver$PendingResult"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(int.class, String.class, Bundle.class, int.class, boolean.class, boolean.class, IBinder.class, int.class); + + public static Reflector.FieldWrapper mAbortBroadcast = REF.field("mAbortBroadcast"); + public static Reflector.FieldWrapper mFinished = REF.field("mFinished"); + public static Reflector.FieldWrapper mInitialStickyHint = REF.field("mInitialStickyHint"); + public static Reflector.FieldWrapper mOrderedHint = REF.field("mOrderedHint"); + public static Reflector.FieldWrapper mResultData = REF.field("mResultData"); + public static Reflector.FieldWrapper mResultExtras = REF.field("mResultExtras"); + public static Reflector.FieldWrapper mSendingUser = REF.field("mSendingUser"); + public static Reflector.FieldWrapper mToken = REF.field("mToken"); + public static Reflector.FieldWrapper mType = REF.field("mType"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderClient.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderClient.java new file mode 100644 index 0000000..985a462 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderClient.java @@ -0,0 +1,11 @@ +package black.android.content; + +import android.os.IInterface; + +import black.Reflector; + +public class ContentProviderClient { + public static final Reflector REF = Reflector.on("android.content.ContentProviderClient"); + + public static Reflector.FieldWrapper mContentProvider = REF.field("mContentProvider"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderHolderOreo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderHolderOreo.java new file mode 100644 index 0000000..27db306 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderHolderOreo.java @@ -0,0 +1,11 @@ +package black.android.content; + +import android.os.IInterface; + +import black.Reflector; + +public class ContentProviderHolderOreo { + public static final Reflector REF = Reflector.on("android.app.ContentProviderHolder"); + + public static Reflector.FieldWrapper provider = REF.field("provider"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderNative.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderNative.java new file mode 100644 index 0000000..d0cf915 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentProviderNative.java @@ -0,0 +1,12 @@ +package black.android.content; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ContentProviderNative { + public static final Reflector REF = Reflector.on("android.content.ContentProviderNative"); + + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentResolver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentResolver.java new file mode 100644 index 0000000..1783e9b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/ContentResolver.java @@ -0,0 +1,9 @@ +package black.android.content; + +import black.Reflector; + +public class ContentResolver { + public static final Reflector REF = Reflector.on("android.content.ContentResolver"); + + public static Reflector.FieldWrapper mPackageName = REF.field("mPackageName"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IContentService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IContentService.java new file mode 100644 index 0000000..7ea8440 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IContentService.java @@ -0,0 +1,13 @@ +package black.android.content; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IContentService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.content.IContentService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IIntentReceiver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IIntentReceiver.java new file mode 100644 index 0000000..5bda277 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IIntentReceiver.java @@ -0,0 +1,12 @@ +package black.android.content; + +import android.content.Intent; +import android.os.Bundle; + +import black.Reflector; + +public class IIntentReceiver { + public static final Reflector REF = Reflector.on("android.content.IIntentReceiver"); + + public static Reflector.MethodWrapper performReceive = REF.method("performReceive", Intent.class, int.class, String.class, Bundle.class, boolean.class, boolean.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IRestrictionsManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IRestrictionsManager.java new file mode 100644 index 0000000..cdc022c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/IRestrictionsManager.java @@ -0,0 +1,13 @@ +package black.android.content; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IRestrictionsManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.content.IRestrictionsManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoL.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoL.java new file mode 100644 index 0000000..f143974 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoL.java @@ -0,0 +1,11 @@ +package black.android.content.pm; + +import black.Reflector; + +public class ApplicationInfoL { + public static final Reflector REF = Reflector.on("android.content.pm.ApplicationInfo"); + + public static Reflector.FieldWrapper primaryCpuAbi = REF.field("primaryCpuAbi"); + public static Reflector.FieldWrapper scanPublicSourceDir = REF.field("scanPublicSourceDir"); + public static Reflector.FieldWrapper scanSourceDir = REF.field("scanSourceDir"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoN.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoN.java new file mode 100644 index 0000000..6204b1f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ApplicationInfoN.java @@ -0,0 +1,11 @@ +package black.android.content.pm; + +import black.Reflector; + +public class ApplicationInfoN { + public static final Reflector REF = Reflector.on("android.content.pm.ApplicationInfo"); + + public static Reflector.FieldWrapper credentialEncryptedDataDir = REF.field("credentialEncryptedDataDir"); + public static Reflector.FieldWrapper credentialProtectedDataDir = REF.field("credentialProtectedDataDir"); + public static Reflector.FieldWrapper deviceProtectedDataDir = REF.field("deviceProtectedDataDir"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ILauncherApps.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ILauncherApps.java new file mode 100644 index 0000000..6294623 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ILauncherApps.java @@ -0,0 +1,13 @@ +package black.android.content.pm; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ILauncherApps { + public static class Stub { + public static final Reflector REF = Reflector.on("android.content.pm.ILauncherApps$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/IShortcutService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/IShortcutService.java new file mode 100644 index 0000000..275f7ca --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/IShortcutService.java @@ -0,0 +1,13 @@ +package black.android.content.pm; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IShortcutService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.content.pm.IShortcutService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParser.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParser.java new file mode 100644 index 0000000..d6f3723 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParser.java @@ -0,0 +1,28 @@ +package black.android.content.pm; + +import android.content.pm.ApplicationInfo; +import android.content.pm.Signature; +import android.util.DisplayMetrics; + +import java.io.File; + +import black.Reflector; + +public class PackageParser { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.MethodWrapper collectCertificates = REF.method("collectCertificates", android.content.pm.PackageParser.Package.class, int.class); + public static Reflector.MethodWrapper parsePackage = REF.method("parsePackage", File.class, String.class, DisplayMetrics.class, int.class); + + public static class Package { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser$Package"); + + public static Reflector.FieldWrapper applicationInfo = REF.field("applicationInfo"); + } + + public static class SigningDetails { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser$SigningDetails"); + + public static Reflector.FieldWrapper signatures = REF.field("signatures"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop.java new file mode 100644 index 0000000..86bba63 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop.java @@ -0,0 +1,17 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser; +import android.content.pm.PackageParser.Package; + +import java.io.File; + +import black.Reflector; + +public class PackageParserLollipop { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(); + + public static Reflector.MethodWrapper collectCertificates = REF.method("collectCertificates", Package.class, int.class); + public static Reflector.MethodWrapper parsePackage = REF.method("parsePackage", File.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop22.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop22.java new file mode 100644 index 0000000..70dedd8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserLollipop22.java @@ -0,0 +1,17 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser; +import android.content.pm.PackageParser.Package; + +import java.io.File; + +import black.Reflector; + +public class PackageParserLollipop22 { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(); + + public static Reflector.MethodWrapper collectCertificates = REF.method("collectCertificates", Package.class, int.class); + public static Reflector.MethodWrapper parsePackage = REF.method("parsePackage", File.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserMarshmallow.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserMarshmallow.java new file mode 100644 index 0000000..42d4e61 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserMarshmallow.java @@ -0,0 +1,17 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser; +import android.content.pm.PackageParser.Package; + +import java.io.File; + +import black.Reflector; + +public class PackageParserMarshmallow { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(); + + public static Reflector.MethodWrapper collectCertificates = REF.method("collectCertificates", Package.class, int.class); + public static Reflector.MethodWrapper parsePackage = REF.method("parsePackage", File.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserNougat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserNougat.java new file mode 100644 index 0000000..8d456a4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserNougat.java @@ -0,0 +1,11 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser; + +import black.Reflector; + +public class PackageParserNougat { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.StaticMethodWrapper collectCertificates = REF.staticMethod("collectCertificates", PackageParser.Package.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserPie.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserPie.java new file mode 100644 index 0000000..4abf244 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/PackageParserPie.java @@ -0,0 +1,17 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser; + +import java.io.File; + +import black.Reflector; + +public class PackageParserPie { + public static final Reflector REF = Reflector.on("android.content.pm.PackageParser"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(); + + public static Reflector.StaticMethodWrapper collectCertificates = REF.staticMethod("collectCertificates", PackageParser.Package.class, boolean.class); + + public static Reflector.MethodWrapper parsePackage = REF.method("parsePackage", File.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ParceledListSlice.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ParceledListSlice.java new file mode 100644 index 0000000..cabeb3d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/ParceledListSlice.java @@ -0,0 +1,16 @@ +package black.android.content.pm; + +import java.util.List; + +import black.Reflector; + +public class ParceledListSlice { + public static final Reflector REF = Reflector.on("android.content.pm.ParceledListSlice"); + + public static Reflector.ConstructorWrapper _new0 = REF.constructor(); + public static Reflector.ConstructorWrapper _new1 = REF.constructor(List.class); + + public static Reflector.MethodWrapper append = REF.method("append", Object.class); + public static Reflector.MethodWrapper> getList = REF.method("getList"); + public static Reflector.MethodWrapper setLastSlice = REF.method("setLastSlice", boolean.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/SigningInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/SigningInfo.java new file mode 100644 index 0000000..ebb2f47 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/SigningInfo.java @@ -0,0 +1,11 @@ +package black.android.content.pm; + +import android.content.pm.PackageParser.SigningDetails; + +import black.Reflector; + +public class SigningInfo { + public static final Reflector REF = Reflector.on("android.content.pm.SigningInfo"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(SigningDetails.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/UserInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/UserInfo.java new file mode 100644 index 0000000..cb16380 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/pm/UserInfo.java @@ -0,0 +1,11 @@ +package black.android.content.pm; + +import black.Reflector; + +public class UserInfo { + public static final Reflector REF = Reflector.on("android.content.pm.UserInfo"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(int.class, String.class, int.class); + + public static Reflector.FieldWrapper FLAG_PRIMARY = REF.field("FLAG_PRIMARY"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/res/AssetManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/res/AssetManager.java new file mode 100644 index 0000000..a37eeba --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/content/res/AssetManager.java @@ -0,0 +1,11 @@ +package black.android.content.res; + +import black.Reflector; + +public class AssetManager { + public static final Reflector REF = Reflector.on("android.content.res.AssetManager"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(); + + public static Reflector.MethodWrapper addAssetPath = REF.method("addAssetPath", String.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/ddm/DdmHandleAppName.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/ddm/DdmHandleAppName.java new file mode 100644 index 0000000..209dfd5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/ddm/DdmHandleAppName.java @@ -0,0 +1,9 @@ +package black.android.ddm; + +import black.Reflector; + +public class DdmHandleAppName { + public static final Reflector REF = Reflector.on("android.ddm.DdmHandleAppName"); + + public static Reflector.StaticMethodWrapper setAppName = REF.staticMethod("setAppName", String.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/graphics/Compatibility.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/graphics/Compatibility.java new file mode 100644 index 0000000..d8076c9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/graphics/Compatibility.java @@ -0,0 +1,9 @@ +package black.android.graphics; + +import black.Reflector; + +public class Compatibility { + public static final Reflector REF = Reflector.on("android.graphics.Compatibility"); + + public static Reflector.StaticMethodWrapper setTargetSdkVersion = REF.staticMethod("setTargetSdkVersion", int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/display/DisplayManagerGlobal.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/display/DisplayManagerGlobal.java new file mode 100644 index 0000000..aaec86e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/display/DisplayManagerGlobal.java @@ -0,0 +1,13 @@ +package black.android.hardware.display; + +import android.os.IInterface; + +import black.Reflector; + +public class DisplayManagerGlobal { + public static final Reflector REF = Reflector.on("android.hardware.display.DisplayManagerGlobal"); + + public static Reflector.FieldWrapper mDm = REF.field("mDm"); + + public static Reflector.StaticMethodWrapper getInstance = REF.staticMethod("getInstance"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/location/IContextHubService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/location/IContextHubService.java new file mode 100644 index 0000000..61939b1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/hardware/location/IContextHubService.java @@ -0,0 +1,13 @@ +package black.android.hardware.location; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IContextHubService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.hardware.location.IContextHubService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationListener.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationListener.java new file mode 100644 index 0000000..a7309ef --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationListener.java @@ -0,0 +1,18 @@ +package black.android.location; + +import android.location.Location; +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ILocationListener { + public static final Reflector REF = Reflector.on("android.location.ILocationListener"); + + public static Reflector.MethodWrapper onLocationChanged = REF.method("onLocationChanged", Location.class); + + public static class Stub { + public static final Reflector REF = Reflector.on("android.location.ILocationListener$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationManager.java new file mode 100644 index 0000000..d8c6acf --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/ILocationManager.java @@ -0,0 +1,13 @@ +package black.android.location; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ILocationManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.location.ILocationManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/LocationManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/LocationManager.java new file mode 100644 index 0000000..418ca57 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/LocationManager.java @@ -0,0 +1,24 @@ +package black.android.location; + +import black.Reflector; + +public class LocationManager { + public static class GnssStatusListenerTransport { + public static final Reflector REF = Reflector.on("android.location.LocationManager$GnssStatusListenerTransport"); + + public static Reflector.MethodWrapper onGnssStarted = REF.method("onGnssStarted"); + public static Reflector.MethodWrapper onNmeaReceived = REF.method("onNmeaReceived", long.class, String.class); + } + + public static class GpsStatusListenerTransport { + public static final Reflector REF = Reflector.on("android.location.LocationManager$GpsStatusListenerTransport"); + + public static Reflector.MethodWrapper onNmeaReceived = REF.method("onNmeaReceived", long.class, String.class); + } + + public static class LocationListenerTransport { + public static final Reflector REF = Reflector.on("android.location.LocationManager$LocationListenerTransport"); + + public static Reflector.FieldWrapper mListener = REF.field("mListener"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/provider/ProviderProperties.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/provider/ProviderProperties.java new file mode 100644 index 0000000..a1a78ca --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/location/provider/ProviderProperties.java @@ -0,0 +1,10 @@ +package black.android.location.provider; + +import black.Reflector; + +public class ProviderProperties { + public static final Reflector REF = Reflector.on("android.location.provider.ProviderProperties"); + + public static Reflector.FieldWrapper mHasNetworkRequirement = REF.field("mHasNetworkRequirement"); + public static Reflector.FieldWrapper mHasCellRequirement = REF.field("mHasCellRequirement"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/IMediaRouterService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/IMediaRouterService.java new file mode 100644 index 0000000..56300f1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/IMediaRouterService.java @@ -0,0 +1,13 @@ +package black.android.media; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IMediaRouterService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.media.IMediaRouterService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/session/ISessionManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/session/ISessionManager.java new file mode 100644 index 0000000..046732b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/media/session/ISessionManager.java @@ -0,0 +1,13 @@ +package black.android.media.session; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ISessionManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.media.session.ISessionManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IConnectivityManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IConnectivityManager.java new file mode 100644 index 0000000..23df3d4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IConnectivityManager.java @@ -0,0 +1,13 @@ +package black.android.net; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IConnectivityManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.net.IConnectivityManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IVpnManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IVpnManager.java new file mode 100644 index 0000000..bbaec55 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/IVpnManager.java @@ -0,0 +1,13 @@ +package black.android.net; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IVpnManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.net.IVpnManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/IWifiManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/IWifiManager.java new file mode 100644 index 0000000..c2ab4d5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/IWifiManager.java @@ -0,0 +1,13 @@ +package black.android.net.wifi; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IWifiManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.net.wifi.IWifiManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiInfo.java new file mode 100644 index 0000000..9747668 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiInfo.java @@ -0,0 +1,11 @@ +package black.android.net.wifi; + +import black.Reflector; + +public class WifiInfo { + public static final Reflector REF = Reflector.on("android.net.wifi.WifiInfo"); + + public static Reflector.FieldWrapper mBSSID = REF.field("mBSSID"); + public static Reflector.FieldWrapper mMacAddress = REF.field("mMacAddress"); + public static Reflector.FieldWrapper mWifiSsid = REF.field("mWifiSsid"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiSsid.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiSsid.java new file mode 100644 index 0000000..980ead3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/net/wifi/WifiSsid.java @@ -0,0 +1,9 @@ +package black.android.net.wifi; + +import black.Reflector; + +public class WifiSsid { + public static final Reflector REF = Reflector.on("android.net.wifi.WifiSsid"); + + public static Reflector.StaticMethodWrapper createFromAsciiEncoded = REF.staticMethod("createFromAsciiEncoded", String.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Build.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Build.java new file mode 100644 index 0000000..cd4f0f6 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Build.java @@ -0,0 +1,20 @@ +package black.android.os; + +import black.Reflector; + +public class Build { + public static final Reflector REF = Reflector.on("android.os.Build"); + + public static Reflector.FieldWrapper BOARD = REF.field("BOARD"); + public static Reflector.FieldWrapper BRAND = REF.field("BRAND"); + public static Reflector.FieldWrapper DEVICE = REF.field("DEVICE"); + public static Reflector.FieldWrapper DISPLAY = REF.field("DISPLAY"); + public static Reflector.FieldWrapper HOST = REF.field("HOST"); + public static Reflector.FieldWrapper ID = REF.field("ID"); + public static Reflector.FieldWrapper MANUFACTURER = REF.field("MANUFACTURER"); + public static Reflector.FieldWrapper MODEL = REF.field("MODEL"); + public static Reflector.FieldWrapper PRODUCT = REF.field("PRODUCT"); + public static Reflector.FieldWrapper TAGS = REF.field("TAGS"); + public static Reflector.FieldWrapper TYPE = REF.field("TYPE"); + public static Reflector.FieldWrapper USER = REF.field("USER"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Bundle.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Bundle.java new file mode 100644 index 0000000..86b99a4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Bundle.java @@ -0,0 +1,12 @@ +package black.android.os; + +import android.os.IBinder; + +import black.Reflector; + +public class Bundle { + public static final Reflector REF = Reflector.on("android.os.Bundle"); + + public static Reflector.MethodWrapper getIBinder = REF.method("getIBinder", String.class); + public static Reflector.MethodWrapper putIBinder = REF.method("putIBinder", String.class, IBinder.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Handler.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Handler.java new file mode 100644 index 0000000..7673978 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Handler.java @@ -0,0 +1,11 @@ +package black.android.os; + +import android.os.Handler.Callback; + +import black.Reflector; + +public class Handler { + public static final Reflector REF = Reflector.on("android.os.Handler"); + + public static Reflector.FieldWrapper mCallback = REF.field("mCallback"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IDeviceIdentifiersPolicyService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IDeviceIdentifiersPolicyService.java new file mode 100644 index 0000000..f5ec031 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IDeviceIdentifiersPolicyService.java @@ -0,0 +1,13 @@ +package black.android.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IDeviceIdentifiersPolicyService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.IDeviceIdentifiersPolicyService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/INetworkManagementService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/INetworkManagementService.java new file mode 100644 index 0000000..f59ed8b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/INetworkManagementService.java @@ -0,0 +1,13 @@ +package black.android.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class INetworkManagementService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.INetworkManagementService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IPowerManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IPowerManager.java new file mode 100644 index 0000000..49dee96 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IPowerManager.java @@ -0,0 +1,13 @@ +package black.android.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IPowerManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.IPowerManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IUserManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IUserManager.java new file mode 100644 index 0000000..1096a5a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IUserManager.java @@ -0,0 +1,13 @@ +package black.android.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IUserManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.IUserManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IVibratorManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IVibratorManagerService.java new file mode 100644 index 0000000..a3868e2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/IVibratorManagerService.java @@ -0,0 +1,13 @@ +package black.android.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IVibratorManagerService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.IVibratorManagerService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Process.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Process.java new file mode 100644 index 0000000..34e36f7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/Process.java @@ -0,0 +1,9 @@ +package black.android.os; + +import black.Reflector; + +public class Process { + public static final Reflector REF = Reflector.on("android.os.Process"); + + public static Reflector.StaticMethodWrapper setArgV0 = REF.staticMethod("setArgV0", String.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/ServiceManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/ServiceManager.java new file mode 100644 index 0000000..7cab3ae --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/ServiceManager.java @@ -0,0 +1,15 @@ +package black.android.os; + +import android.os.IBinder; + +import java.util.Map; + +import black.Reflector; + +public class ServiceManager { + public static final Reflector REF = Reflector.on("android.os.ServiceManager"); + + public static Reflector.FieldWrapper> sCache = REF.field("sCache"); + + public static Reflector.StaticMethodWrapper getService = REF.staticMethod("getService", String.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/StrictMode.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/StrictMode.java new file mode 100644 index 0000000..f95efba --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/StrictMode.java @@ -0,0 +1,13 @@ +package black.android.os; + +import black.Reflector; + +public class StrictMode { + public static final Reflector REF = Reflector.on("android.os.StrictMode"); + + public static Reflector.FieldWrapper DETECT_VM_FILE_URI_EXPOSURE = REF.field("DETECT_VM_FILE_URI_EXPOSURE"); + public static Reflector.FieldWrapper PENALTY_DEATH_ON_FILE_URI_EXPOSURE = REF.field("PENALTY_DEATH_ON_FILE_URI_EXPOSURE"); + public static Reflector.FieldWrapper sVmPolicyMask = REF.field("sVmPolicyMask"); + + public static Reflector.StaticMethodWrapper disableDeathOnFileUriExposure = REF.staticMethod("disableDeathOnFileUriExposure"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/SystemProperties.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/SystemProperties.java new file mode 100644 index 0000000..78204cb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/SystemProperties.java @@ -0,0 +1,11 @@ +package black.android.os; + +import black.Reflector; + +public class SystemProperties { + public static final Reflector REF = Reflector.on("android.os.SystemProperties"); + + public static Reflector.StaticMethodWrapper get0 = REF.staticMethod("get", String.class, String.class); + public static Reflector.StaticMethodWrapper get1 = REF.staticMethod("get", String.class); + public static Reflector.StaticMethodWrapper getInt = REF.staticMethod("getInt", String.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/UserHandle.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/UserHandle.java new file mode 100644 index 0000000..cb12964 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/UserHandle.java @@ -0,0 +1,9 @@ +package black.android.os; + +import black.Reflector; + +public class UserHandle { + public static final Reflector REF = Reflector.on("android.os.UserHandle"); + + public static Reflector.StaticMethodWrapper myUserId = REF.staticMethod("myUserId"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/mount/IMountService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/mount/IMountService.java new file mode 100644 index 0000000..559affb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/mount/IMountService.java @@ -0,0 +1,13 @@ +package black.android.os.mount; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IMountService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.storage.IMountService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/IStorageManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/IStorageManager.java new file mode 100644 index 0000000..7e1d5f8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/IStorageManager.java @@ -0,0 +1,13 @@ +package black.android.os.storage; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IStorageManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.storage.IStorageManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageManager.java new file mode 100644 index 0000000..66924cd --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageManager.java @@ -0,0 +1,11 @@ +package black.android.os.storage; + +import android.os.storage.StorageVolume; + +import black.Reflector; + +public class StorageManager { + public static final Reflector REF = Reflector.on("android.os.storage.StorageManager"); + + public static Reflector.StaticMethodWrapper getVolumeList = REF.staticMethod("getVolumeList", int.class, int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageVolume.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageVolume.java new file mode 100644 index 0000000..4fe532b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/os/storage/StorageVolume.java @@ -0,0 +1,12 @@ +package black.android.os.storage; + +import java.io.File; + +import black.Reflector; + +public class StorageVolume { + public static final Reflector REF = Reflector.on("android.os.storage.StorageVolume"); + + public static Reflector.FieldWrapper mInternalPath = REF.field("mInternalPath"); + public static Reflector.FieldWrapper mPath = REF.field("mPath"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/permission/IPermissionManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/permission/IPermissionManager.java new file mode 100644 index 0000000..17afb5f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/permission/IPermissionManager.java @@ -0,0 +1,13 @@ +package black.android.permission; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IPermissionManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.permission.IPermissionManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/providers/Settings.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/providers/Settings.java new file mode 100644 index 0000000..ef5d472 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/providers/Settings.java @@ -0,0 +1,43 @@ +package black.android.providers; + +import android.os.IInterface; + +import black.Reflector; + +public class Settings { + public static class System { + public static final Reflector REF = Reflector.on("android.provider.Settings$System"); + + public static Reflector.FieldWrapper sNameValueCache = REF.field("sNameValueCache"); + } + + public static class Secure { + public static final Reflector REF = Reflector.on("android.provider.Settings$Secure"); + + public static Reflector.FieldWrapper sNameValueCache = REF.field("sNameValueCache"); + } + + public static class ContentProviderHolder { + public static final Reflector REF = Reflector.on("android.provider.Settings$ContentProviderHolder"); + + public static Reflector.FieldWrapper mContentProvider = REF.field("mContentProvider"); + } + + public static class NameValueCacheOreo { + public static final Reflector REF = Reflector.on("android.provider.Settings$NameValueCache"); + + public static Reflector.FieldWrapper mProviderHolder = REF.field("mProviderHolder"); + } + + public static class NameValueCache { + public static final Reflector REF = Reflector.on("android.provider.Settings$NameValueCache"); + + public static Reflector.FieldWrapper mContentProvider = REF.field("mContentProvider"); + } + + public static class Global { + public static final Reflector REF = Reflector.on("android.provider.Settings$Global"); + + public static Reflector.FieldWrapper sNameValueCache = REF.field("sNameValueCache"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/role/IRoleManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/role/IRoleManager.java new file mode 100644 index 0000000..ff4aa78 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/role/IRoleManager.java @@ -0,0 +1,20 @@ +package black.android.role; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 19:48 + **/ +public class IRoleManager { + public static final Reflector TYPE = Reflector.on("android.app.role.IRoleManager"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("android.app.role.IRoleManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/security/net/config/NetworkSecurityConfigProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/security/net/config/NetworkSecurityConfigProvider.java new file mode 100644 index 0000000..19265e7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/security/net/config/NetworkSecurityConfigProvider.java @@ -0,0 +1,11 @@ +package black.android.security.net.config; + +import android.content.Context; + +import black.Reflector; + +public class NetworkSecurityConfigProvider { + public static final Reflector REF = Reflector.on("android.security.net.config.NetworkSecurityConfigProvider"); + + public static Reflector.StaticMethodWrapper install = REF.staticMethod("install", Context.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/service/persistentdata/IPersistentDataBlockService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/service/persistentdata/IPersistentDataBlockService.java new file mode 100644 index 0000000..c729b2d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/service/persistentdata/IPersistentDataBlockService.java @@ -0,0 +1,13 @@ +package black.android.service.persistentdata; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IPersistentDataBlockService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.service.persistentdata.IPersistentDataBlockService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/telephony/TelephonyManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/telephony/TelephonyManager.java new file mode 100644 index 0000000..4cb97be --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/telephony/TelephonyManager.java @@ -0,0 +1,16 @@ +package black.android.telephony; + +import android.os.IInterface; + +import black.Reflector; + +public class TelephonyManager { + public static final Reflector REF = Reflector.on("android.telephony.TelephonyManager"); + + public static Reflector.StaticMethodWrapper getSubscriberInfoService = REF.staticMethod("getSubscriberInfoService"); + + public static Reflector.FieldWrapper sServiceHandleCacheEnabled = REF.field("sServiceHandleCacheEnabled"); + public static Reflector.FieldWrapper sIPhoneSubInfo = REF.field("sIPhoneSubInfo"); + + public static Reflector.MethodWrapper getSubscriberInfo = REF.method("getSubscriberInfo"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/util/Singleton.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/util/Singleton.java new file mode 100644 index 0000000..bf3f045 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/util/Singleton.java @@ -0,0 +1,11 @@ +package black.android.util; + +import black.Reflector; + +public class Singleton { + public static final Reflector REF = Reflector.on("android.util.Singleton"); + + public static Reflector.FieldWrapper mInstance = REF.field("mInstance"); + + public static Reflector.MethodWrapper get = REF.method("get"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IAutoFillManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IAutoFillManager.java new file mode 100644 index 0000000..c8cf8eb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IAutoFillManager.java @@ -0,0 +1,13 @@ +package black.android.view; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAutoFillManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.view.autofill.IAutoFillManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IGraphicsStats.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IGraphicsStats.java new file mode 100644 index 0000000..dcd9c5e --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IGraphicsStats.java @@ -0,0 +1,13 @@ +package black.android.view; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IGraphicsStats { + public static class Stub { + public static final Reflector REF = Reflector.on("android.view.IGraphicsStats$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IWindowManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IWindowManager.java new file mode 100644 index 0000000..646a5a4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/IWindowManager.java @@ -0,0 +1,13 @@ +package black.android.view; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IWindowManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.view.IWindowManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/WindowManagerGlobal.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/WindowManagerGlobal.java new file mode 100644 index 0000000..42bcc59 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/WindowManagerGlobal.java @@ -0,0 +1,11 @@ +package black.android.view; + +import android.os.IInterface; + +import black.Reflector; + +public class WindowManagerGlobal { + public static final Reflector REF = Reflector.on("android.view.WindowManagerGlobal"); + + public static Reflector.FieldWrapper sWindowManagerService = REF.field("sWindowManagerService"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/accessibility/IAccessibilityManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/accessibility/IAccessibilityManager.java new file mode 100644 index 0000000..504c2a0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/android/view/accessibility/IAccessibilityManager.java @@ -0,0 +1,13 @@ +package black.android.view.accessibility; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAccessibilityManager { + public static class Stub { + public static final Reflector REF = Reflector.on("android.view.accessibility.IAccessibilityManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/R.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/R.java new file mode 100644 index 0000000..79d2e2c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/R.java @@ -0,0 +1,21 @@ +package black.com.android.internal; + +import black.Reflector; + +public class R { + public static class styleable { + public static final Reflector REF = Reflector.on("com.android.internal.R$styleable"); + + public static Reflector.FieldWrapper AccountAuthenticator = REF.field("AccountAuthenticator"); + public static Reflector.FieldWrapper AccountAuthenticator_accountPreferences = REF.field("AccountAuthenticator_accountPreferences"); + public static Reflector.FieldWrapper AccountAuthenticator_accountType = REF.field("AccountAuthenticator_accountType"); + public static Reflector.FieldWrapper AccountAuthenticator_customTokens = REF.field("AccountAuthenticator_customTokens"); + public static Reflector.FieldWrapper AccountAuthenticator_icon = REF.field("AccountAuthenticator_icon"); + public static Reflector.FieldWrapper AccountAuthenticator_label = REF.field("AccountAuthenticator_label"); + public static Reflector.FieldWrapper AccountAuthenticator_smallIcon = REF.field("AccountAuthenticator_smallIcon"); + public static Reflector.FieldWrapper Window = REF.field("Window"); + public static Reflector.FieldWrapper Window_windowFullscreen = REF.field("Window_windowFullscreen"); + public static Reflector.FieldWrapper Window_windowIsTranslucent = REF.field("Window_windowIsTranslucent"); + public static Reflector.FieldWrapper Window_windowShowWallpaper = REF.field("Window_windowShowWallpaper"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/app/IAppOpsService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/app/IAppOpsService.java new file mode 100644 index 0000000..4e1b95a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/app/IAppOpsService.java @@ -0,0 +1,13 @@ +package black.com.android.internal.app; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAppOpsService { + public static class Stub { + public static final Reflector REF = Reflector.on("com.android.internal.app.IAppOpsService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/appwidget/IAppWidgetService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/appwidget/IAppWidgetService.java new file mode 100644 index 0000000..c564be0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/appwidget/IAppWidgetService.java @@ -0,0 +1,13 @@ +package black.com.android.internal.appwidget; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IAppWidgetService { + public static class Stub { + public static final Reflector REF = Reflector.on("com.android.internal.appwidget.IAppWidgetService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/content/ReferrerIntent.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/content/ReferrerIntent.java new file mode 100644 index 0000000..bf807e4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/content/ReferrerIntent.java @@ -0,0 +1,11 @@ +package black.com.android.internal.content; + +import android.content.Intent; + +import black.Reflector; + +public class ReferrerIntent { + public static final Reflector REF = Reflector.on("com.android.internal.content.ReferrerIntent"); + + public static Reflector.ConstructorWrapper _new = REF.constructor(Intent.class, String.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/infra/AndroidFuture.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/infra/AndroidFuture.java new file mode 100644 index 0000000..9ff3a14 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/infra/AndroidFuture.java @@ -0,0 +1,16 @@ +package black.com.android.internal.infra; + +import android.content.Context; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/13 18:56 + **/ +public class AndroidFuture { + public static final Reflector REF = Reflector.on("com.android.internal.infra.AndroidFuture"); + public static Reflector.MethodWrapper complete = REF.method("complete", Object.class); + public static Reflector.ConstructorWrapper ctor = REF.constructor(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/net/VpnConfig.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/net/VpnConfig.java new file mode 100644 index 0000000..14043d6 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/net/VpnConfig.java @@ -0,0 +1,13 @@ +package black.com.android.internal.net; + +import java.util.List; + +import black.Reflector; + +public class VpnConfig { + public static final Reflector REF = Reflector.on("com.android.internal.net.VpnConfig"); + + public static Reflector.FieldWrapper user = REF.field("user"); + public static Reflector.FieldWrapper> disallowedApplications = REF.field("disallowedApplications"); + public static Reflector.FieldWrapper> allowedApplications = REF.field("allowedApplications"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/os/IVibratorService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/os/IVibratorService.java new file mode 100644 index 0000000..1586188 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/os/IVibratorService.java @@ -0,0 +1,13 @@ +package black.com.android.internal.os; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class IVibratorService { + public static class Stub { + public static final Reflector REF = Reflector.on("android.os.IVibratorService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ISub.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ISub.java new file mode 100644 index 0000000..e24e7c0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ISub.java @@ -0,0 +1,13 @@ +package black.com.android.internal.telephony; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ISub { + public static class Stub { + public static final Reflector REF = Reflector.on("com.android.internal.telephony.ISub$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephony.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephony.java new file mode 100644 index 0000000..61541a7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephony.java @@ -0,0 +1,13 @@ +package black.com.android.internal.telephony; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ITelephony { + public static class Stub { + public static final Reflector REF = Reflector.on("com.android.internal.telephony.ITelephony$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephonyRegistry.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephonyRegistry.java new file mode 100644 index 0000000..c15a647 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/com/android/internal/telephony/ITelephonyRegistry.java @@ -0,0 +1,13 @@ +package black.com.android.internal.telephony; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +public class ITelephonyRegistry { + public static class Stub { + public static final Reflector REF = Reflector.on("com.android.internal.telephony.ITelephonyRegistry$Stub"); + public static Reflector.StaticMethodWrapper asInterface = REF.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/dalvik/system/VMRuntime.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/dalvik/system/VMRuntime.java new file mode 100644 index 0000000..2b31aa8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/dalvik/system/VMRuntime.java @@ -0,0 +1,10 @@ +package black.dalvik.system; + +import black.Reflector; + +public class VMRuntime { + public static final Reflector REF = Reflector.on("dalvik.system.VMRuntime"); + + public static Reflector.StaticMethodWrapper getRuntime = REF.staticMethod("getRuntime"); + public static Reflector.MethodWrapper setTargetSdkVersion = REF.method("setTargetSdkVersion", int.class); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/libcore/io/Libcore.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/libcore/io/Libcore.java new file mode 100644 index 0000000..fdcb978 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/libcore/io/Libcore.java @@ -0,0 +1,9 @@ +package black.libcore.io; + +import black.Reflector; + +public class Libcore { + public static final Reflector REF = Reflector.on("libcore.io.Libcore"); + + public static Reflector.FieldWrapper os = REF.field("os"); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/flyme/IFlymePermissionService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/flyme/IFlymePermissionService.java new file mode 100644 index 0000000..2229e10 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/flyme/IFlymePermissionService.java @@ -0,0 +1,20 @@ +package black.oem.flyme; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/9 12:33 + **/ +public class IFlymePermissionService { + public static final Reflector TYPE = Reflector.on("meizu.security.IFlymePermissionService"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("meizu.security.IFlymePermissionService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPhysicalFlingManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPhysicalFlingManager.java new file mode 100644 index 0000000..590c15f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPhysicalFlingManager.java @@ -0,0 +1,20 @@ +package black.oem.vivo; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:12 + **/ +public class IPhysicalFlingManager { + public static final Reflector TYPE = Reflector.on("vivo.app.physicalfling.IPhysicalFlingManager"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("vivo.app.physicalfling.IPhysicalFlingManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPopupCameraManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPopupCameraManager.java new file mode 100644 index 0000000..2d9bc64 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IPopupCameraManager.java @@ -0,0 +1,20 @@ +package black.oem.vivo; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:21 + **/ +public class IPopupCameraManager { + public static final Reflector TYPE = Reflector.on("vivo.app.popupcamera.IPopupCameraManager"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("vivo.app.popupcamera.IPopupCameraManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISuperResolutionManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISuperResolutionManager.java new file mode 100644 index 0000000..19c0931 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISuperResolutionManager.java @@ -0,0 +1,20 @@ +package black.oem.vivo; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:27 + **/ +public class ISuperResolutionManager { + public static final Reflector TYPE = Reflector.on("vivo.app.superresolution.ISuperResolutionManager"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("vivo.app.superresolution.ISuperResolutionManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISystemDefenceManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISystemDefenceManager.java new file mode 100644 index 0000000..acc8c5f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/ISystemDefenceManager.java @@ -0,0 +1,20 @@ +package black.oem.vivo; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:32 + **/ +public class ISystemDefenceManager { + public static final Reflector TYPE = Reflector.on("vivo.app.systemdefence.ISystemDefenceManager"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("vivo.app.systemdefence.ISystemDefenceManager$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IVivoPermissonService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IVivoPermissonService.java new file mode 100644 index 0000000..ca2c7eb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/black/oem/vivo/IVivoPermissonService.java @@ -0,0 +1,20 @@ +package black.oem.vivo; + +import android.os.IBinder; +import android.os.IInterface; + +import black.Reflector; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:37 + **/ +public class IVivoPermissonService { + public static final Reflector TYPE = Reflector.on("vivo.app.security.IVivoPermissionService"); + + public static class Stub { + public static final Reflector TYPE = Reflector.on("vivo.app.security.IVivoPermissionService$Stub"); + public static Reflector.StaticMethodWrapper asInterface = TYPE.staticMethod("asInterface", IBinder.class); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/BlackBoxCore.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/BlackBoxCore.java similarity index 85% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/BlackBoxCore.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/BlackBoxCore.java index 668f444..7f0e6da 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/BlackBoxCore.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/BlackBoxCore.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox; +package com.vcore; import android.annotation.SuppressLint; import android.app.ActivityManager; @@ -20,53 +20,45 @@ import android.os.Looper; import android.os.Process; +import org.lsposed.hiddenapibypass.HiddenApiBypass; + import java.io.File; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; -import black.android.app.BRActivityThread; -import black.android.os.BRUserHandle; -import me.weishu.reflection.Reflection; -import top.canyie.pine.PineConfig; -import top.niunaijun.blackbox.app.LauncherActivity; -import top.niunaijun.blackbox.app.configuration.AppLifecycleCallback; -import top.niunaijun.blackbox.app.configuration.ClientConfiguration; -import top.niunaijun.blackbox.core.GmsCore; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.DaemonService; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.user.BUserHandle; -import top.niunaijun.blackbox.core.system.user.BUserInfo; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.entity.pm.InstallResult; -import top.niunaijun.blackbox.entity.pm.InstalledModule; -import top.niunaijun.blackbox.fake.delegate.ContentProviderDelegate; -import top.niunaijun.blackbox.fake.frameworks.BActivityManager; -import top.niunaijun.blackbox.fake.frameworks.BJobManager; -import top.niunaijun.blackbox.fake.frameworks.BPackageManager; -import top.niunaijun.blackbox.fake.frameworks.BStorageManager; -import top.niunaijun.blackbox.fake.frameworks.BUserManager; -import top.niunaijun.blackbox.fake.frameworks.BXposedManager; -import top.niunaijun.blackbox.fake.hook.HookManager; -import top.niunaijun.blackbox.proxy.ProxyManifest; -import top.niunaijun.blackbox.utils.FileUtils; -import top.niunaijun.blackbox.utils.ShellUtils; -import top.niunaijun.blackbox.utils.Slog; -import top.niunaijun.blackbox.utils.compat.BuildCompat; -import top.niunaijun.blackbox.utils.compat.BundleCompat; -import top.niunaijun.blackbox.utils.compat.XposedParserCompat; -import top.niunaijun.blackbox.utils.provider.ProviderCall; - -/** - * Created by Milk on 3/30/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import black.android.app.ActivityThread; +import black.android.os.UserHandle; +import com.vcore.app.LauncherActivity; +import com.vcore.app.configuration.AppLifecycleCallback; +import com.vcore.app.configuration.ClientConfiguration; +import com.vcore.core.GmsCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.DaemonService; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.core.system.user.BUserInfo; +import com.vcore.entity.pm.InstallOption; +import com.vcore.entity.pm.InstallResult; +import com.vcore.entity.pm.InstalledModule; +import com.vcore.fake.delegate.ContentProviderDelegate; +import com.vcore.fake.frameworks.BActivityManager; +import com.vcore.fake.frameworks.BJobManager; +import com.vcore.fake.frameworks.BPackageManager; +import com.vcore.fake.frameworks.BStorageManager; +import com.vcore.fake.frameworks.BUserManager; +import com.vcore.fake.frameworks.BXposedManager; +import com.vcore.fake.hook.HookManager; +import com.vcore.proxy.ProxyManifest; +import com.vcore.utils.FileUtils; +import com.vcore.utils.ShellUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.BundleCompat; +import com.vcore.utils.compat.XposedParserCompat; +import com.vcore.utils.provider.ProviderCall; + @SuppressLint({"StaticFieldLeak", "NewApi"}) public class BlackBoxCore extends ClientConfiguration { public static final String TAG = "BlackBoxCore"; @@ -80,7 +72,7 @@ public class BlackBoxCore extends ClientConfiguration { private final List mAppLifecycleCallbacks = new ArrayList<>(); private final Handler mHandler = new Handler(Looper.getMainLooper()); private final int mHostUid = Process.myUid(); - private final int mHostUserId = BRUserHandle.get().myUserId(); + private final int mHostUserId = UserHandle.myUserId.call(); public static BlackBoxCore get() { return sBlackBoxCore; @@ -122,7 +114,11 @@ public void doAttachBaseContext(Context context, ClientConfiguration clientConfi if (clientConfiguration == null) { throw new IllegalArgumentException("ClientConfiguration is null!"); } - Reflection.unseal(context); + + if (BuildCompat.isPie()) { + HiddenApiBypass.addHiddenApiExemptions("L"); + } + sContext = context; mClientConfiguration = clientConfiguration; initNotificationManager(); @@ -136,13 +132,11 @@ public void doAttachBaseContext(Context context, ClientConfiguration clientConfi } else { mProcessType = ProcessType.BAppClient; } + if (BlackBoxCore.get().isBlackProcess()) { BEnvironment.load(); - if (processName.endsWith("p0")) { -// android.os.Debug.waitForDebugger(); - } -// android.os.Debug.waitForDebugger(); } + if (isServerProcess()) { if (clientConfiguration.isEnableDaemonService()) { Intent intent = new Intent(); @@ -154,13 +148,12 @@ public void doAttachBaseContext(Context context, ClientConfiguration clientConfi } } } - PineConfig.debug = true; - PineConfig.debuggable = true; + + xcrash.XCrash.init(context); HookManager.get().init(); } public void doCreate() { - // fix contentProvider if (isBlackProcess()) { ContentProviderDelegate.init(); } @@ -170,7 +163,7 @@ public void doCreate() { } public static Object mainThread() { - return BRActivityThread.get().currentActivityThread(); + return ActivityThread.currentActivityThread.call(); } public void startActivity(Intent intent, int userId) { @@ -202,6 +195,7 @@ public boolean launchApk(String packageName, int userId) { if (launchIntentForPackage == null) { return false; } + startActivity(launchIntentForPackage, userId); return true; } @@ -351,10 +345,12 @@ public IBinder getService(String name) { if (binder != null && binder.isBinderAlive()) { return binder; } + Bundle bundle = new Bundle(); bundle.putString("_B_|_server_name_", name); Bundle vm = ProviderCall.callSafely(ProxyManifest.getBindProvider(), "VM", null, bundle); binder = BundleCompat.getBinder(vm, "_B_|_server_"); + Slog.d(TAG, "getService: " + name + ", " + binder); mServices.put(name, binder); return binder; @@ -429,6 +425,7 @@ private static String getProcessName(Context context) { break; } } + if (processName == null) { throw new RuntimeException("processName = null"); } @@ -447,9 +444,9 @@ private void initNotificationManager() { NotificationManager nm = (NotificationManager) BlackBoxCore.getContext().getSystemService(Context.NOTIFICATION_SERVICE); String CHANNEL_ONE_ID = BlackBoxCore.getContext().getPackageName() + ".blackbox_core"; String CHANNEL_ONE_NAME = "blackbox_core"; + if (BuildCompat.isOreo()) { - NotificationChannel notificationChannel = new NotificationChannel(CHANNEL_ONE_ID, - CHANNEL_ONE_NAME, NotificationManager.IMPORTANCE_HIGH); + NotificationChannel notificationChannel = new NotificationChannel(CHANNEL_ONE_ID, CHANNEL_ONE_NAME, NotificationManager.IMPORTANCE_HIGH); notificationChannel.enableLights(true); notificationChannel.setLightColor(Color.RED); notificationChannel.setShowBadge(true); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/BActivityThread.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/BActivityThread.java new file mode 100644 index 0000000..d6c6d23 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/BActivityThread.java @@ -0,0 +1,571 @@ +package com.vcore.app; + +import android.annotation.SuppressLint; +import android.app.Activity; +import android.app.Application; +import android.app.Instrumentation; +import android.app.Service; +import android.app.job.JobService; +import android.content.BroadcastReceiver; +import android.content.ComponentName; +import android.content.ContentProviderClient; +import android.content.Context; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ApplicationInfo; +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; +import android.content.pm.ProviderInfo; +import android.content.pm.ServiceInfo; +import android.os.Binder; +import android.os.Build; +import android.os.ConditionVariable; +import android.os.Handler; +import android.os.IBinder; +import android.os.IInterface; +import android.os.Looper; +import android.os.RemoteException; +import android.os.StrictMode; +import android.util.Log; +import android.webkit.WebView; + +import java.lang.reflect.Field; +import java.security.Security; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Collections; +import java.util.List; +import java.util.Map; + +import black.android.app.ActivityManagerNative; +import black.android.app.ActivityThread; +import black.android.app.ActivityThreadNMR1; +import black.android.app.ActivityThreadQ; +import black.android.app.ContextImpl; +import black.android.app.LoadedApk; +import black.android.graphics.Compatibility; +import black.android.security.net.config.NetworkSecurityConfigProvider; +import black.com.android.internal.content.ReferrerIntent; +import black.dalvik.system.VMRuntime; + +import com.vcore.BlackBoxCore; +import com.vcore.app.configuration.AppLifecycleCallback; +import com.vcore.app.dispatcher.AppServiceDispatcher; +import com.vcore.core.CrashHandler; +import com.vcore.core.IBActivityThread; +import com.vcore.core.IOCore; +import com.vcore.core.NativeCore; +import com.vcore.core.env.VirtualRuntime; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.entity.AppConfig; +import com.vcore.entity.am.ReceiverData; +import com.vcore.fake.delegate.AppInstrumentation; +import com.vcore.fake.delegate.ContentProviderDelegate; +import com.vcore.fake.hook.HookManager; +import com.vcore.fake.service.HCallbackProxy; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.ActivityManagerCompat; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.ContextCompat; +import com.vcore.utils.compat.StrictModeCompat; + +public class BActivityThread extends IBActivityThread.Stub { + public static final String TAG = "BActivityThread"; + + private AppBindData mBoundApplication; + private Application mInitialApplication; + private AppConfig mAppConfig; + private final List mProviders = new ArrayList<>(); + private final Handler mH = BlackBoxCore.get().getHandler(); + private static final Object mConfigLock = new Object(); + + public static boolean isThreadInit() { + return true; + } + + private static final class SBActivityThreadHolder { + static final BActivityThread sBActivityThread = new BActivityThread(); + } + + public static BActivityThread currentActivityThread() { + return SBActivityThreadHolder.sBActivityThread; + } + + public static AppConfig getAppConfig() { + synchronized (mConfigLock) { + return currentActivityThread().mAppConfig; + } + } + + public static List getProviders() { + return currentActivityThread().mProviders; + } + + public static String getAppProcessName() { + if (getAppConfig() != null) { + return getAppConfig().processName; + } else if (currentActivityThread().mBoundApplication != null) { + return currentActivityThread().mBoundApplication.processName; + } + return null; + } + + public static String getAppPackageName() { + if (getAppConfig() != null) { + return getAppConfig().packageName; + } else if (currentActivityThread().mInitialApplication != null) { + return currentActivityThread().mInitialApplication.getPackageName(); + } + return null; + } + + public static Application getApplication() { + return currentActivityThread().mInitialApplication; + } + + public static int getAppPid() { + return getAppConfig() == null ? -1 : getAppConfig().bPID; + } + + public static int getBUid() { + return getAppConfig() == null ? BUserHandle.AID_APP_START : getAppConfig().bUID; + } + + public static int getBAppId() { + return BUserHandle.getAppId(getBUid()); + } + + public static int getCallingBUid() { + return getAppConfig() == null ? BlackBoxCore.getHostUid() : getAppConfig().callingBUid; + } + + public static int getUid() { + return getAppConfig() == null ? -1 : getAppConfig().uid; + } + + public static int getUserId() { + return getAppConfig() == null ? 0 : getAppConfig().userId; + } + + public void initProcess(AppConfig appConfig) { + synchronized (mConfigLock) { + if (this.mAppConfig != null && !this.mAppConfig.packageName.equals(appConfig.packageName)) { + // 该进程已被attach + throw new RuntimeException("Reject init process: " + appConfig.processName + ", this process is: " + this.mAppConfig.processName); + } + + this.mAppConfig = appConfig; + IBinder iBinder = asBinder(); + try { + iBinder.linkToDeath(new DeathRecipient() { + @Override + public void binderDied() { + synchronized (mConfigLock) { + try { + iBinder.linkToDeath(this, 0); + } catch (RemoteException ignored) { } + mAppConfig = null; + } + } + }, 0); + } catch (RemoteException e) { + e.printStackTrace(); + } + } + } + + public boolean isInit() { + return mBoundApplication != null; + } + + public Service createService(ServiceInfo serviceInfo, IBinder token) { + if (!BActivityThread.currentActivityThread().isInit()) { + BActivityThread.currentActivityThread().bindApplication(serviceInfo.packageName, serviceInfo.processName); + } + + ClassLoader classLoader = LoadedApk.getClassLoader.call(mBoundApplication.info); + Service service; + try { + service = (Service) classLoader.loadClass(serviceInfo.name).newInstance(); + } catch (Exception e) { + e.printStackTrace(); + Slog.e(TAG, "Unable to instantiate service " + serviceInfo.name + ": " + e); + return null; + } + + try { + Context context = BlackBoxCore.getContext().createPackageContext(serviceInfo.packageName, + Context.CONTEXT_INCLUDE_CODE | Context.CONTEXT_IGNORE_SECURITY); + + ContextImpl.setOuterContext.call(context, service); + black.android.app.Service.attach.call(service, context, BlackBoxCore.mainThread(), serviceInfo.name, token, mInitialApplication, + ActivityManagerNative.getDefault.call()); + + ContextCompat.fix(context); + service.onCreate(); + return service; + } catch (Exception e) { + throw new RuntimeException("Unable to create service " + serviceInfo.name + ": " + e, e); + } + } + + public JobService createJobService(ServiceInfo serviceInfo) { + if (!BActivityThread.currentActivityThread().isInit()) { + BActivityThread.currentActivityThread().bindApplication(serviceInfo.packageName, serviceInfo.processName); + } + + ClassLoader classLoader = LoadedApk.getClassLoader.call(mBoundApplication.info); + JobService service; + try { + service = (JobService) classLoader.loadClass(serviceInfo.name).newInstance(); + } catch (Exception e) { + e.printStackTrace(); + Slog.e(TAG, "Unable to create JobService " + serviceInfo.name + ": " + e); + return null; + } + + try { + Context context = BlackBoxCore.getContext().createPackageContext(serviceInfo.packageName, Context.CONTEXT_INCLUDE_CODE | + Context.CONTEXT_IGNORE_SECURITY); + + ContextImpl.setOuterContext.call(context, service); + black.android.app.Service.attach.call(service, context, BlackBoxCore.mainThread(), serviceInfo.name, + BActivityThread.currentActivityThread().getActivityThread(), mInitialApplication, ActivityManagerNative.getDefault.call()); + + ContextCompat.fix(context); + service.onCreate(); + service.onBind(null); + return service; + } catch (Exception e) { + throw new RuntimeException( + "Unable to create JobService " + serviceInfo.name + + ": " + e, e); + } + } + + public void bindApplication(final String packageName, final String processName) { + if (Looper.myLooper() != Looper.getMainLooper()) { + final ConditionVariable conditionVariable = new ConditionVariable(); + + BlackBoxCore.get().getHandler().post(() -> { + handleBindApplication(packageName, processName); + conditionVariable.open(); + }); + conditionVariable.block(); + } else { + handleBindApplication(packageName, processName); + } + } + + @SuppressLint("NewApi") + public synchronized void handleBindApplication(String packageName, String processName) { + if (isInit()) + return; + try { + CrashHandler.create(); + } catch (Throwable ignored) { } + + PackageInfo packageInfo = BlackBoxCore.getBPackageManager().getPackageInfo(packageName, PackageManager.GET_PROVIDERS, BActivityThread.getUserId()); + ApplicationInfo applicationInfo = packageInfo.applicationInfo; + if (packageInfo.providers == null) { + packageInfo.providers = new ProviderInfo[]{}; + } + mProviders.addAll(Arrays.asList(packageInfo.providers)); + + Object boundApplication = ActivityThread.mBoundApplication.get(BlackBoxCore.mainThread()); + Context packageContext = createPackageContext(applicationInfo); + Object loadedApk = ContextImpl.mPackageInfo.get(packageContext); + + LoadedApk.mSecurityViolation.set(loadedApk, false); + LoadedApk.mApplicationInfo.set(loadedApk, applicationInfo); + + int targetSdkVersion = applicationInfo.targetSdkVersion; + if (targetSdkVersion < Build.VERSION_CODES.GINGERBREAD) { + StrictMode.ThreadPolicy newPolicy = new StrictMode.ThreadPolicy.Builder(StrictMode.getThreadPolicy()).permitNetwork().build(); + StrictMode.setThreadPolicy(newPolicy); + } + + if (BuildCompat.isN()) { + if (targetSdkVersion < Build.VERSION_CODES.N) { + StrictModeCompat.disableDeathOnFileUriExposure(); + } + } + + if (BuildCompat.isPie()) { + WebView.setDataDirectorySuffix(getUserId() + ":" + packageName + ":" + processName); + } + + VirtualRuntime.setupRuntime(processName, applicationInfo); + VMRuntime.setTargetSdkVersion.call(VMRuntime.getRuntime.call(), applicationInfo.targetSdkVersion); + if (BuildCompat.isS()) { + Compatibility.setTargetSdkVersion.call(applicationInfo.targetSdkVersion); + } + + NativeCore.init(Build.VERSION.SDK_INT); + assert packageContext != null; + IOCore.get().enableRedirect(packageContext); + + AppBindData bindData = new AppBindData(); + bindData.appInfo = applicationInfo; + bindData.processName = processName; + bindData.info = loadedApk; + bindData.providers = mProviders; + + ActivityThread.AppBindData.instrumentationName.set(boundApplication, new ComponentName(bindData.appInfo.packageName, Instrumentation.class.getName())); + ActivityThread.AppBindData.appInfo.set(boundApplication, bindData.appInfo); + ActivityThread.AppBindData.info.set(boundApplication, bindData.info); + ActivityThread.AppBindData.processName.set(boundApplication, bindData.processName); + ActivityThread.AppBindData.providers.set(boundApplication, bindData.providers); + mBoundApplication = bindData; + + // SSL适配 + Security.removeProvider("AndroidNSSP"); + NetworkSecurityConfigProvider.install.call(packageContext); + Application application; + try { + onBeforeCreateApplication(packageName, processName, packageContext); + application = LoadedApk.makeApplication.call(loadedApk, false, null); + + mInitialApplication = application; + ActivityThread.mInitialApplication.set(BlackBoxCore.mainThread(), mInitialApplication); + ContextCompat.fix((Context) ActivityThread.getSystemContext.call(BlackBoxCore.mainThread())); + ContextCompat.fix(mInitialApplication); + installProviders(mInitialApplication, bindData.processName, bindData.providers); + //fix wechat + if (Build.VERSION.SDK_INT >= 24 && "com.tencent.mm:recovery".equals(processName)) { + try { + Field field = application.getClassLoader().loadClass("com.tencent.recovery.Recovery").getField("context"); + field.setAccessible(true); + if (field.get(null) != null) { + return; + } + field.set(null, application.getBaseContext()); + } catch (Throwable e) { + e.printStackTrace(); + } + } + onBeforeApplicationOnCreate(packageName, processName, application); + AppInstrumentation.get().callApplicationOnCreate(application); + onAfterApplicationOnCreate(packageName, processName, application); + HookManager.get().checkEnv(HCallbackProxy.class); + } catch (Exception e) { + e.printStackTrace(); + throw new RuntimeException("Unable to makeApplication", e); + } + } + + public static Context createPackageContext(ApplicationInfo info) { + try { + return BlackBoxCore.getContext().createPackageContext(info.packageName, Context.CONTEXT_INCLUDE_CODE | Context.CONTEXT_IGNORE_SECURITY); + } catch (Exception e) { + e.printStackTrace(); + } + return null; + } + + private void installProviders(Context context, String processName, List provider) { + long origId = Binder.clearCallingIdentity(); + try { + for (ProviderInfo providerInfo : provider) { + try { + if (processName.equals(providerInfo.processName) || providerInfo.processName.equals(context.getPackageName()) || providerInfo.multiprocess) { + installProvider(BlackBoxCore.mainThread(), context, providerInfo, null); + Log.d(TAG, "providerInfo.authority: " + providerInfo.authority); + } + } catch (Throwable ignored) { } + } + } finally { + Binder.restoreCallingIdentity(origId); + ContentProviderDelegate.init(); + } + } + + public Object getPackageInfo() { + return mBoundApplication.info; + } + + public static void installProvider(Object mainThread, Context context, ProviderInfo providerInfo, Object holder) { + ActivityThread.installProvider.call(mainThread, context, holder, providerInfo, false, true, true); + } + + /*public void loadXposed(Context context) { + String vPackageName = getAppPackageName(); + String vProcessName = getAppProcessName(); + + if (!TextUtils.isEmpty(vPackageName) && !TextUtils.isEmpty(vProcessName) && BXposedManager.get().isXPEnable()) { + boolean isFirstApplication = vPackageName.equals(vProcessName); + + List installedModules = BXposedManager.get().getInstalledModules(); + for (InstalledModule installedModule : installedModules) { + if (!installedModule.enable) { + continue; + } + + try { + XposedInit.loadModule(installedModule.getApplication().sourceDir, context.getClassLoader()); + } catch (Throwable e) { + e.printStackTrace(); + } + } + + try { + XposedInit.onPackageLoad(vPackageName, vProcessName, context.getApplicationInfo(), isFirstApplication, context.getClassLoader()); + } catch (Throwable ignored) { } + } + if (BlackBoxCore.get().isHideXposed()) { + NativeCore.hideXposed(); + } + } +*/ + @Override + public IBinder getActivityThread() { + return ActivityThread.getApplicationThread.call(BlackBoxCore.mainThread()); + } + + @Override + public void bindApplication() { + if (!isInit()) { + bindApplication(getAppPackageName(), getAppProcessName()); + } + } + + @Override + public void stopService(Intent intent) { + AppServiceDispatcher.get().stopService(intent); + } + + @Override + public void restartJobService(String selfId) { } + + @Override + public IBinder acquireContentProviderClient(ProviderInfo providerInfo) { + if (!isInit()) { + bindApplication(BActivityThread.getAppConfig().packageName, BActivityThread.getAppConfig().processName); + } + + String[] split = providerInfo.authority.split(";"); + for (String auth : split) { + ContentProviderClient contentProviderClient = BlackBoxCore.getContext().getContentResolver().acquireContentProviderClient(auth); + IInterface iInterface = black.android.content.ContentProviderClient.mContentProvider.get(contentProviderClient); + + if (iInterface == null) { + continue; + } + return iInterface.asBinder(); + } + return null; + } + + @Override + public IBinder peekService(Intent intent) { + return AppServiceDispatcher.get().peekService(intent); + } + + @Override + public void finishActivity(final IBinder token) { + mH.post(() -> { + Map activities = ActivityThread.mActivities.get(BlackBoxCore.mainThread()); + if (activities.isEmpty()) { + return; + } + + Object clientRecord = activities.get(token); + if (clientRecord == null) { + return; + } + + Activity activity = getActivityByToken(token); + while (activity.getParent() != null) { + activity = activity.getParent(); + } + + int resultCode = black.android.app.Activity.mResultCode.get(activity); + Intent resultData = black.android.app.Activity.mResultData.get(activity); + ActivityManagerCompat.finishActivity(token, resultCode, resultData); + black.android.app.Activity.mFinished.set(activity, true); + }); + } + + @Override + public void handleNewIntent(final IBinder token, final Intent intent) { + mH.post(() -> { + Intent newIntent; + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP_MR1) { + newIntent = ReferrerIntent._new.newInstance(BlackBoxCore.getHostPkg()); + } else { + newIntent = intent; + } + + Object mainThread = BlackBoxCore.mainThread(); + if (ActivityThread.performNewIntents != null) { + ActivityThread.performNewIntents.call(mainThread, token, Collections.singletonList(newIntent)); + } else if (ActivityThreadNMR1.performNewIntents != null) { + ActivityThreadNMR1.performNewIntents.call(mainThread, token, Collections.singletonList(newIntent), true); + } else if (ActivityThreadQ.handleNewIntent != null) { + ActivityThreadQ.handleNewIntent.call(mainThread, token, Collections.singletonList(newIntent)); + } + }); + } + + @Override + public void scheduleReceiver(ReceiverData data) { + if (!isInit()) { + bindApplication(); + } + mH.post(() -> { + BroadcastReceiver mReceiver = null; + Intent intent = data.intent; + ActivityInfo activityInfo = data.activityInfo; + BroadcastReceiver.PendingResult pendingResult = data.data.build(); + + try { + Context baseContext = mInitialApplication.getBaseContext(); + ClassLoader classLoader = baseContext.getClassLoader(); + intent.setExtrasClassLoader(classLoader); + + mReceiver = (BroadcastReceiver) classLoader.loadClass(activityInfo.name).newInstance(); + black.android.content.BroadcastReceiver.setPendingResult.call(mReceiver, pendingResult); + mReceiver.onReceive(baseContext, intent); + + BroadcastReceiver.PendingResult finish = black.android.content.BroadcastReceiver.getPendingResult.call(mReceiver); + if (finish != null) { + finish.finish(); + } + BlackBoxCore.getBActivityManager().finishBroadcast(data.data); + } catch (Throwable throwable) { + throwable.printStackTrace(); + Slog.e(TAG, "Error receiving broadcast " + intent + " in " + mReceiver); + } + }); + } + + public static Activity getActivityByToken(IBinder token) { + Map iBinderObjectMap = ActivityThread.mActivities.get(BlackBoxCore.mainThread()); + return ActivityThread.ActivityClientRecord.activity.get(iBinderObjectMap.get(token)); + } + + private void onBeforeCreateApplication(String packageName, String processName, Context context) { + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.beforeCreateApplication(packageName, processName, context, BActivityThread.getUserId()); + } + } + + private void onBeforeApplicationOnCreate(String packageName, String processName, Application application) { + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.beforeApplicationOnCreate(packageName, processName, application, BActivityThread.getUserId()); + } + } + + private void onAfterApplicationOnCreate(String packageName, String processName, Application application) { + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.afterApplicationOnCreate(packageName, processName, application, BActivityThread.getUserId()); + } + } + + public static class AppBindData { + String processName; + ApplicationInfo appInfo; + List providers; + Object info; + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/LauncherActivity.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/LauncherActivity.java similarity index 83% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/LauncherActivity.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/LauncherActivity.java index 3f9c78c..19d7851 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/LauncherActivity.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/LauncherActivity.java @@ -1,20 +1,23 @@ -package top.niunaijun.blackbox.app; +package com.vcore.app; import android.app.Activity; +import android.app.ActivityManager; import android.content.Intent; import android.content.pm.PackageInfo; import android.graphics.drawable.Drawable; import android.os.Bundle; +import android.text.TextUtils; import androidx.annotation.Nullable; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.R; -import top.niunaijun.blackbox.utils.Slog; +import java.util.List; + +import com.vcore.BlackBoxCore; +import com.vcore.R; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.fake.frameworks.BActivityManager; +import com.vcore.utils.Slog; -/** - * Created by BlackBox on 2022/2/24. - */ public class LauncherActivity extends Activity { public static final String TAG = "SplashScreen"; @@ -22,6 +25,7 @@ public class LauncherActivity extends Activity { public static final String KEY_PKG = "launch_pkg"; public static final String KEY_USER_ID = "launch_user_id"; private boolean isRunning = false; + private boolean UnRunning = false; public static void launch(Intent intent, int userId) { Intent splash = new Intent(); @@ -36,12 +40,14 @@ public static void launch(Intent intent, int userId) { @Override protected void onCreate(@Nullable Bundle savedInstanceState) { + //这里解决多进程问题 super.onCreate(savedInstanceState); Intent intent = getIntent(); if (intent == null) { finish(); return; } + Intent launchIntent = intent.getParcelableExtra(KEY_INTENT); String packageName = intent.getStringExtra(KEY_PKG); int userId = intent.getIntExtra(KEY_USER_ID, 0); @@ -54,15 +60,17 @@ protected void onCreate(@Nullable Bundle savedInstanceState) { } Drawable drawable = packageInfo.applicationInfo.loadIcon(BlackBoxCore.getPackageManager()); setContentView(R.layout.activity_launcher); -// findViewById(R.id.iv_icon).setBackgroundDrawable(drawable); + +// findViewById(R.id.iv_icon) +// .setBackground(drawable); new Thread(() -> BlackBoxCore.getBActivityManager().startActivity(launchIntent, userId)).start(); } @Override protected void onPause() { - finish(); super.onPause(); isRunning = true; + finish(); } @Override diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/AppLifecycleCallback.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/AppLifecycleCallback.java new file mode 100644 index 0000000..5b745e0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/AppLifecycleCallback.java @@ -0,0 +1,42 @@ +package com.vcore.app.configuration; + +import android.app.Activity; +import android.app.Application; +import android.content.Context; +import android.os.Bundle; +import android.util.Log; + +import de.robv.android.xposed.XC_MethodHook; +import de.robv.android.xposed.XposedHelpers; +import com.vcore.BlackBoxCore; + +public class AppLifecycleCallback implements Application.ActivityLifecycleCallbacks { + public void beforeCreateApplication(String packageName, String processName, Context context, int userId) { } + + public void beforeApplicationOnCreate(String packageName, String processName, Application application, int userId) { + + } + + public void afterApplicationOnCreate(String packageName, String processName, Application application, int userId) { } + + @Override + public void onActivityCreated(Activity activity, Bundle savedInstanceState) { } + + @Override + public void onActivityStarted(Activity activity) { } + + @Override + public void onActivityResumed(Activity activity) { } + + @Override + public void onActivityPaused(Activity activity) { } + + @Override + public void onActivityStopped(Activity activity) { } + + @Override + public void onActivitySaveInstanceState(Activity activity, Bundle outState) { } + + @Override + public void onActivityDestroyed(Activity activity) { } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/configuration/ClientConfiguration.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/ClientConfiguration.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/configuration/ClientConfiguration.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/ClientConfiguration.java index 9587e08..040e015 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/configuration/ClientConfiguration.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/configuration/ClientConfiguration.java @@ -1,17 +1,8 @@ -package top.niunaijun.blackbox.app.configuration; +package com.vcore.app.configuration; import java.io.File; -/** - * Created by Milk on 5/4/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public abstract class ClientConfiguration { - public boolean isHideRoot() { return false; } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppJobServiceDispatcher.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppJobServiceDispatcher.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppJobServiceDispatcher.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppJobServiceDispatcher.java index 51ea0d2..d0da415 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppJobServiceDispatcher.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppJobServiceDispatcher.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.app.dispatcher; +package com.vcore.app.dispatcher; import android.app.job.JobParameters; import android.app.job.JobService; @@ -7,18 +7,10 @@ import java.util.HashMap; import java.util.Map; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.entity.JobRecord; - -/** - * Created by Milk on 4/1/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.entity.JobRecord; + public class AppJobServiceDispatcher { private static final AppJobServiceDispatcher sServiceDispatcher = new AppJobServiceDispatcher(); private final Map mJobRecords = new HashMap<>(); @@ -30,8 +22,9 @@ public static AppJobServiceDispatcher get() { public boolean onStartJob(JobParameters params) { try { JobService jobService = getJobService(params.getJobId()); - if (jobService == null) + if (jobService == null) { return false; + } return jobService.onStartJob(params); } catch (Exception e) { e.printStackTrace(); @@ -41,14 +34,17 @@ public boolean onStartJob(JobParameters params) { public boolean onStopJob(JobParameters params) { JobService jobService = getJobService(params.getJobId()); - if (jobService == null) + if (jobService == null) { return false; - boolean b = jobService.onStopJob(params); + } + + boolean isStopJob = jobService.onStopJob(params); jobService.onDestroy(); + synchronized (mJobRecords) { mJobRecords.remove(params.getJobId()); } - return b; + return isStopJob; } public void onConfigurationChanged(Configuration newConfig) { @@ -60,11 +56,11 @@ public void onConfigurationChanged(Configuration newConfig) { } public void onDestroy() { -// for (JobRecord jobRecord : mJobRecords.values()) { -// if (jobRecord.mJobService != null) { -// jobRecord.mJobService.onDestroy(); -// } -// } + for (JobRecord jobRecord : mJobRecords.values()) { + if (jobRecord.mJobService != null) { + jobRecord.mJobService.onDestroy(); + } + } } public void onLowMemory() { @@ -89,11 +85,18 @@ JobService getJobService(int jobId) { if (jobRecord != null && jobRecord.mJobService != null) { return jobRecord.mJobService; } + try { JobRecord record = BlackBoxCore.getBJobManager().queryJobRecord(BActivityThread.getAppProcessName(), jobId); + if (record == null) { + return null; + } + record.mJobService = BActivityThread.currentActivityThread().createJobService(record.mServiceInfo); - if (record.mJobService == null) + if (record.mJobService == null) { return null; + } + mJobRecords.put(jobId, record); return record.mJobService; } catch (Throwable t) { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppServiceDispatcher.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppServiceDispatcher.java similarity index 76% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppServiceDispatcher.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppServiceDispatcher.java index 8c2b0c0..7a29ee8 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/app/dispatcher/AppServiceDispatcher.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/app/dispatcher/AppServiceDispatcher.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.app.dispatcher; +package com.vcore.app.dispatcher; import android.app.Service; import android.content.Intent; @@ -10,53 +10,39 @@ import java.util.HashMap; import java.util.Map; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.entity.ServiceRecord; -import top.niunaijun.blackbox.entity.UnbindRecord; -import top.niunaijun.blackbox.proxy.record.ProxyServiceRecord; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.entity.ServiceRecord; +import com.vcore.entity.UnbindRecord; +import com.vcore.proxy.record.ProxyServiceRecord; -import static android.app.Service.START_NOT_STICKY; - - -/** - * Created by Milk on 4/1/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class AppServiceDispatcher { - public static final String TAG = "AppServiceDispatcher"; - private static final AppServiceDispatcher sServiceDispatcher = new AppServiceDispatcher(); - - private Map mService = new HashMap<>(); + private final Map mService = new HashMap<>(); + private final Handler mHandler = BlackBoxCore.get().getHandler(); public static AppServiceDispatcher get() { return sServiceDispatcher; } - private final Handler mHandler = BlackBoxCore.get().getHandler(); - public IBinder onBind(Intent proxyIntent) { ProxyServiceRecord serviceRecord = ProxyServiceRecord.create(proxyIntent); Intent intent = serviceRecord.mServiceIntent; ServiceInfo serviceInfo = serviceRecord.mServiceInfo; - if (intent == null || serviceInfo == null) + if (intent == null || serviceInfo == null) { return null; - -// Log.d(TAG, "onBind: " + component.toString()); + } Service service = getOrCreateService(serviceRecord); - if (service == null) + if (service == null) { return null; + } intent.setExtrasClassLoader(service.getClassLoader()); ServiceRecord record = findRecord(intent); record.incrementAndGetBindCount(intent); + if (record.hasBinder(intent)) { if (record.isRebind()) { service.onRebind(intent); @@ -75,27 +61,20 @@ public IBinder onBind(Intent proxyIntent) { return null; } - public int onStartCommand(Intent proxyIntent, int flags, int startId) { + public void onStartCommand(Intent proxyIntent) { ProxyServiceRecord stubRecord = ProxyServiceRecord.create(proxyIntent); if (stubRecord.mServiceIntent == null || stubRecord.mServiceInfo == null) { - return START_NOT_STICKY; + return; } -// Log.d(TAG, "onStartCommand: " + component.toString()); Service service = getOrCreateService(stubRecord); - if (service == null) - return START_NOT_STICKY; + if (service == null) { + return; + } stubRecord.mServiceIntent.setExtrasClassLoader(service.getClassLoader()); + ServiceRecord record = findRecord(stubRecord.mServiceIntent); record.setStartId(stubRecord.mStartId); - try { - int i = service.onStartCommand(stubRecord.mServiceIntent, flags, stubRecord.mStartId); - BlackBoxCore.getBActivityManager().onStartCommand(proxyIntent, stubRecord.mUserId); - return i; - } catch (Throwable e) { - e.printStackTrace(); - } - return START_NOT_STICKY; } public void onDestroy() { @@ -109,7 +88,6 @@ public void onDestroy() { } } mService.clear(); -// Log.d(TAG, "onDestroy: "); } public void onConfigurationChanged(Configuration newConfig) { @@ -122,7 +100,6 @@ public void onConfigurationChanged(Configuration newConfig) { } } } -// Log.d(TAG, "onConfigurationChanged"); } public void onLowMemory() { @@ -135,7 +112,6 @@ public void onLowMemory() { } } } -// Log.d(TAG, "onLowMemory"); } public void onTrimMemory(int level) { @@ -148,44 +124,42 @@ public void onTrimMemory(int level) { } } } - // Log.d(TAG, "onTrimMemory"); } - public boolean onUnbind(Intent proxyIntent) { + public void onUnbind(Intent proxyIntent) { ProxyServiceRecord stubRecord = ProxyServiceRecord.create(proxyIntent); if (stubRecord.mServiceIntent == null || stubRecord.mServiceInfo == null) { - return false; + return; } - Intent intent = stubRecord.mServiceIntent; + Intent intent = stubRecord.mServiceIntent; try { UnbindRecord unbindRecord = BlackBoxCore.getBActivityManager().onServiceUnbind(proxyIntent, BActivityThread.getUserId()); - if (unbindRecord == null) - return false; + if (unbindRecord == null) { + return; + } Service service = getOrCreateService(stubRecord); - if (service == null) - return false; - + if (service == null) { + return; + } stubRecord.mServiceIntent.setExtrasClassLoader(service.getClassLoader()); ServiceRecord record = findRecord(intent); - boolean destroy = unbindRecord.getStartId() == 0; + if (destroy || record.decreaseConnectionCount(intent)) { - boolean b = service.onUnbind(intent); if (destroy) { service.onDestroy(); + BlackBoxCore.getBActivityManager().onServiceDestroy(proxyIntent, BActivityThread.getUserId()); mService.remove(new Intent.FilterComparison(intent)); } record.setRebind(true); -// Log.d(TAG, "onUnbind:" + stubRecord.mServiceIntent.getComponent().toString()); } } catch (Throwable e) { e.printStackTrace(); } - return false; } public IBinder peekService(Intent intent) { @@ -197,11 +171,15 @@ public IBinder peekService(Intent intent) { } public void stopService(Intent intent) { - if (intent == null) + if (intent == null) { return; + } + ServiceRecord record = findRecord(intent); - if (record == null) + if (record == null) { return; + } + if (record.getService() != null) { boolean destroy = record.getStartId() > 0; try { @@ -229,9 +207,12 @@ private Service getOrCreateService(ProxyServiceRecord proxyServiceRecord) { if (record != null && record.getService() != null) { return record.getService(); } + Service service = BActivityThread.currentActivityThread().createService(serviceInfo, token); - if (service == null) + if (service == null) { return null; + } + record = new ServiceRecord(); record.setService(service); mService.put(new Intent.FilterComparison(intent), record); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/CrashHandler.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/CrashHandler.java new file mode 100644 index 0000000..646faf8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/CrashHandler.java @@ -0,0 +1,26 @@ +package com.vcore.core; + +import androidx.annotation.NonNull; + +import com.vcore.BlackBoxCore; + +public class CrashHandler implements Thread.UncaughtExceptionHandler { + private final Thread.UncaughtExceptionHandler mDefaultHandler; + + public static void create() { + new CrashHandler(); + } + + public CrashHandler() { + mDefaultHandler = Thread.getDefaultUncaughtExceptionHandler(); + Thread.setDefaultUncaughtExceptionHandler(this); + } + + @Override + public void uncaughtException(@NonNull Thread t, @NonNull Throwable e) { + if (BlackBoxCore.get().getExceptionHandler() != null) { + BlackBoxCore.get().getExceptionHandler().uncaughtException(t, e); + } + mDefaultHandler.uncaughtException(t, e); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/GmsCore.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/GmsCore.java similarity index 89% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/GmsCore.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/GmsCore.java index 60d50f5..2228b60 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/GmsCore.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/GmsCore.java @@ -1,16 +1,14 @@ -package top.niunaijun.blackbox.core; +package com.vcore.core; import android.content.pm.PackageManager; import java.util.HashSet; import java.util.Set; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.entity.pm.InstallResult; +import com.vcore.BlackBoxCore; +import com.vcore.entity.pm.InstallResult; public class GmsCore { - private static final String TAG = "GmsCore"; - private static final HashSet GOOGLE_APP = new HashSet<>(); private static final HashSet GOOGLE_SERVICE = new HashSet<>(); public static final String GMS_PKG = "com.google.android.gms"; @@ -38,10 +36,6 @@ public class GmsCore { GOOGLE_SERVICE.add("com.google.android.syncadapters.calendar"); } - public static boolean isGoogleService(String packageName) { - return GOOGLE_SERVICE.contains(packageName); - } - public static boolean isGoogleAppOrService(String str) { return GOOGLE_APP.contains(str) || GOOGLE_SERVICE.contains(str); } @@ -52,12 +46,13 @@ private static InstallResult installPackages(Set list, int userId) { if (blackBoxCore.isInstalled(packageName, userId)) { continue; } + try { BlackBoxCore.getContext().getPackageManager().getApplicationInfo(packageName, 0); - } catch (PackageManager.NameNotFoundException e) { - // Ignore + } catch (PackageManager.NameNotFoundException ignored) { continue; } + InstallResult installResult = blackBoxCore.installPackageAsUser(packageName, userId); if (!installResult.success) { return installResult; @@ -97,13 +92,11 @@ public static void remove(String packageName) { GOOGLE_APP.remove(packageName); } - public static boolean isSupportGms() { try { BlackBoxCore.getPackageManager().getPackageInfo(GMS_PKG, 0); return true; - } catch (PackageManager.NameNotFoundException ignored) { - } + } catch (PackageManager.NameNotFoundException ignored) { } return false; } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/IOCore.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/IOCore.java new file mode 100644 index 0000000..b9409e0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/IOCore.java @@ -0,0 +1,187 @@ +package com.vcore.core; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.content.pm.ApplicationInfo; +import android.content.pm.PackageManager; +import android.os.Environment; +import android.os.Process; +import android.text.TextUtils; + +import java.io.File; +import java.util.HashSet; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.Objects; +import java.util.Set; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.core.env.BEnvironment; +import com.vcore.utils.FileUtils; +import com.vcore.utils.TrieTree; + +@SuppressLint("SdCardPath") +public class IOCore { + public static final String TAG = "IOCore"; + + private static final IOCore sIOCore = new IOCore(); + private static final TrieTree mTrieTree = new TrieTree(); + private static final TrieTree sBlackTree = new TrieTree(); + private final Map mRedirectMap = new LinkedHashMap<>(); + + public static IOCore get() { + return sIOCore; + } + + // 路径前缀匹配,重定向 + // /data/data/com.google/ -----> /data/data/com.virtual/data/com.google/ + public void addRedirect(String origPath, String redirectPath) { + if (TextUtils.isEmpty(origPath) || TextUtils.isEmpty(redirectPath) || mRedirectMap.get(origPath) != null) { + return; + } + // Add the key to TrieTree + mTrieTree.add(origPath); + mRedirectMap.put(origPath, redirectPath); + File redirectFile = new File(redirectPath); + if (!redirectFile.exists()) { + FileUtils.mkdirs(redirectPath); + } + NativeCore.addIORule(origPath, redirectPath); + } + + public void addBlackRedirect(String path) { + if (TextUtils.isEmpty(path)) { + return; + } + sBlackTree.add(path); + NativeCore.addWhiteList(path); + } + + public String redirectPath(String path) { + if (TextUtils.isEmpty(path)) { + return path; + } + if (path.contains("/blackbox/")) { + return path; + } + String search = sBlackTree.search(path); + if (!TextUtils.isEmpty(search)) { + return search; + } + + // Search the key from TrieTree + String key = mTrieTree.search(path); + if (!TextUtils.isEmpty(key)) { + path = path.replace(key, Objects.requireNonNull(mRedirectMap.get(key))); + } + return path; + } + + public File redirectPath(File path) { + if (path == null) { + return null; + } + String pathStr = path.getAbsolutePath(); + return new File(redirectPath(pathStr)); + } + + public String redirectPath(String path, Map rule) { + if (TextUtils.isEmpty(path)) { + return path; + } + // Search the key from TrieTree + String key = mTrieTree.search(path); + if (!TextUtils.isEmpty(key)) { + path = path.replace(key, Objects.requireNonNull(rule.get(key))); + } + return path; + } + + // 由于正常情况Application已完成重定向,以下重定向是怕代码写死。 + public void enableRedirect(Context context) { + Map rule = new LinkedHashMap<>(); + Set blackRule = new HashSet<>(); + + try { + // 修改所有已安装的路径, 支持xposed module + int systemUserId = BlackBoxCore.getHostUserId(); + List installedApplications = BlackBoxCore.getBPackageManager().getInstalledApplications(PackageManager.GET_META_DATA, BActivityThread.getUserId()); + for (ApplicationInfo packageInfo : installedApplications) { + rule.put(String.format("/data/data/%s/lib", packageInfo.packageName), packageInfo.nativeLibraryDir); + rule.put(String.format("/data/user/%d/%s/lib", systemUserId, packageInfo.packageName), packageInfo.nativeLibraryDir); + + rule.put(String.format("/data/data/%s", packageInfo.packageName), packageInfo.dataDir); + rule.put(String.format("/data/user/%d/%s", systemUserId, packageInfo.packageName), packageInfo.dataDir); + } + + if (BlackBoxCore.getContext().getExternalCacheDir() != null && context.getExternalCacheDir() != null) { + File external = BEnvironment.getExternalUserDir(BActivityThread.getUserId()); + + // sdcard + rule.put("/sdcard", external.getAbsolutePath()); + rule.put(String.format("/storage/emulated/%d", systemUserId), external.getAbsolutePath()); + + blackRule.add("/sdcard/Pictures"); + blackRule.add(String.format("/storage/emulated/%d/Pictures", systemUserId)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_PODCASTS)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_RINGTONES)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_ALARMS)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_NOTIFICATIONS)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_PICTURES)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_MOVIES)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_DOWNLOADS)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_DCIM)); + blackRule.add(String.format("/storage/emulated/%d/%s", systemUserId, Environment.DIRECTORY_MUSIC)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_PODCASTS)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_RINGTONES)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_ALARMS)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_NOTIFICATIONS)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_PICTURES)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_MOVIES)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_DOWNLOADS)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_DCIM)); + blackRule.add(String.format("/sdcard/%s", Environment.DIRECTORY_MUSIC)); + } + + if (BlackBoxCore.get().isHideRoot()) { + hideRoot(rule); + } + proc(rule); + } catch (Exception e) { + e.printStackTrace(); + } + for (String key : rule.keySet()) { + get().addRedirect(key, rule.get(key)); + } + for (String s : blackRule) { + get().addBlackRedirect(s); + } + NativeCore.enableIO(); + } + + private void hideRoot(Map rule) { + rule.put("/system/app/Superuser.apk", "/system/app/Superuser.apk-fake"); + rule.put("/sbin/su", "/sbin/su-fake"); + rule.put("/system/bin/su", "/system/bin/su-fake"); + rule.put("/system/xbin/su", "/system/xbin/su-fake"); + rule.put("/data/local/xbin/su", "/data/local/xbin/su-fake"); + rule.put("/data/local/bin/su", "/data/local/bin/su-fake"); + rule.put("/system/sd/xbin/su", "/system/sd/xbin/su-fake"); + rule.put("/system/bin/failsafe/su", "/system/bin/failsafe/su-fake"); + rule.put("/data/local/su", "/data/local/su-fake"); + rule.put("/su/bin/su", "/su/bin/su-fake"); + } + + private void proc(Map rule) { + int appPid = BActivityThread.getAppPid(); + int pid = Process.myPid(); + String selfProc = "/proc/self/"; + String proc = "/proc/" + pid + "/"; + + String cmdline = new File(BEnvironment.getProcDir(appPid), "cmdline").getAbsolutePath(); + rule.put(proc + "cmdline", cmdline); + rule.put(selfProc + "cmdline", cmdline); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/NativeCore.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/NativeCore.java new file mode 100644 index 0000000..b375130 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/NativeCore.java @@ -0,0 +1,63 @@ +package com.vcore.core; + +import android.os.Binder; +import android.os.Process; + +import androidx.annotation.Keep; + +import java.io.File; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; + +public class NativeCore { + public static final String TAG = "NativeCore"; + + static { + System.loadLibrary("vcore"); + } + + public static native void init(int apiLevel); + + public static native void enableIO(); + + public static native void addWhiteList(String path); + + public static native void addIORule(String targetPath, String relocatePath); + + private static native void nativeIORedirect(String origPath, String newPath); + + public static native void hideXposed(); + + @Keep + public static int getCallingUid(int origCallingUid) { + // 系统uid + if (origCallingUid > 0 && origCallingUid < Process.FIRST_APPLICATION_UID) { + return origCallingUid; + } + // 非用户应用 + if (origCallingUid > Process.LAST_APPLICATION_UID) { + return origCallingUid; + } + + if (origCallingUid == BlackBoxCore.getHostUid()) { + int callingPid = Binder.getCallingPid(); + int bUid = BlackBoxCore.getBPackageManager().getUidByPid(callingPid); + if (bUid != -1) { + return bUid; + } + return BActivityThread.getCallingBUid(); + } + return origCallingUid; + } + + @Keep + public static String redirectPath(String path) { + return IOCore.get().redirectPath(path); + } + + @Keep + public static File redirectPath(File path) { + return IOCore.get().redirectPath(path); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/AppSystemEnv.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/AppSystemEnv.java similarity index 82% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/AppSystemEnv.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/AppSystemEnv.java index 7d9bb7f..a3b2897 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/AppSystemEnv.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/AppSystemEnv.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.env; +package com.vcore.core.env; import android.content.ComponentName; import android.os.Build; @@ -6,17 +6,8 @@ import java.util.ArrayList; import java.util.List; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.utils.compat.BuildCompat; - -/** - * Created by Milk on 4/21/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.BlackBoxCore; + public class AppSystemEnv { private static final List sSystemPackages = new ArrayList<>(); private static final List sSuPackages = new ArrayList<>(); @@ -34,17 +25,21 @@ public class AppSystemEnv { sSystemPackages.add("com.android.talkback"); sSystemPackages.add("com.miui.gallery"); - // google Gboard + // Google Gboard sSystemPackages.add("com.google.android.inputmethod.latin"); // sSystemPackages.add(BlackBoxCore.getHostPkg()); // 华为 sSystemPackages.add("com.huawei.webview"); - // oppo + // MIUI + sSystemPackages.add("com.miui.contentcatcher"); + sSystemPackages.add("com.miui.catcherpatch"); + + // Oppo sSystemPackages.add("com.coloros.safecenter"); - // su + // Su sSuPackages.add("com.noshufou.android.su"); sSuPackages.add("com.noshufou.android.su.elite"); sSuPackages.add("eu.chainfire.supersu"); @@ -53,8 +48,6 @@ public class AppSystemEnv { sSuPackages.add("com.yellowes.su"); sXposedPackages.add("de.robv.android.xposed.installer"); - - // sPreInstallPackages.add("com.huawei.hwid"); if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && Build.VERSION.SDK_INT < 29){ //解决Android 9三星浏览器闪退问题 }else{ @@ -73,10 +66,8 @@ public static boolean isOpenPackage(ComponentName componentName) { public static boolean isBlackPackage(String packageName) { if (BlackBoxCore.get().isHideRoot() && sSuPackages.contains(packageName)) { return true; - } else if (BlackBoxCore.get().isHideXposed() && sXposedPackages.contains(packageName)) { - return true; } - return false; + return BlackBoxCore.get().isHideXposed() && sXposedPackages.contains(packageName); } public static List getPreInstallPackages() { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/BEnvironment.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/BEnvironment.java similarity index 90% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/BEnvironment.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/BEnvironment.java index efc77f2..e0756eb 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/env/BEnvironment.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/BEnvironment.java @@ -1,27 +1,16 @@ -package top.niunaijun.blackbox.core.env; +package com.vcore.core.env; import java.io.File; import java.util.Locale; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.utils.FileUtils; - -/** - * Created by Milk on 4/22/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.utils.FileUtils; + public class BEnvironment { private static final File sVirtualRoot = new File(BlackBoxCore.getContext().getCacheDir().getParent(), "blackbox"); private static final File sExternalVirtualRoot = BlackBoxCore.getContext().getExternalFilesDir("blackbox"); - public static File JUNIT_JAR = new File(getCacheDir(), "junit.apk"); - public static File EMPTY_JAR = new File(getCacheDir(), "empty.apk"); - public static void load() { FileUtils.mkdirs(sVirtualRoot); FileUtils.mkdirs(sExternalVirtualRoot); @@ -74,6 +63,10 @@ public static File getFakeLocationConf() { return new File(getSystemDir(), "fake-location.conf"); } + public static File getFakeDeviceConf() { + return new File(getSystemDir(), "fake-device.conf"); + } + public static File getPackageConf(String packageName) { return new File(getAppDir(packageName), "package.conf"); } @@ -94,7 +87,6 @@ public static File getExternalDataDir(String packageName, int userId) { return new File(getExternalUserDir(userId), String.format(Locale.CHINA, "Android/data/%s", packageName)); } - public static File getDataDir(String packageName, int userId) { return new File(sVirtualRoot, String.format(Locale.CHINA, "data/user/%d/%s", userId, packageName)); } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/VirtualRuntime.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/VirtualRuntime.java new file mode 100644 index 0000000..d1fb878 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/env/VirtualRuntime.java @@ -0,0 +1,30 @@ +package com.vcore.core.env; + +import android.content.pm.ApplicationInfo; + +import black.android.ddm.DdmHandleAppName; +import black.android.os.Process; + +public class VirtualRuntime { + private static String sInitialPackageName; + private static String sProcessName; + + public static String getProcessName() { + return sProcessName; + } + + public static String getInitialPackageName() { + return sInitialPackageName; + } + + public static void setupRuntime(String processName, ApplicationInfo appInfo) { + if (sProcessName != null) { + return; + } + + sInitialPackageName = appInfo.packageName; + sProcessName = processName; + Process.setArgV0.call(processName); + DdmHandleAppName.setAppName.call(processName, 0); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BProcessManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BProcessManagerService.java new file mode 100644 index 0000000..2f4896f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BProcessManagerService.java @@ -0,0 +1,372 @@ +package com.vcore.core.system; + +import android.app.ActivityManager; +import android.content.Context; +import android.content.pm.ApplicationInfo; +import android.os.Binder; +import android.os.Bundle; +import android.os.IBinder; +import android.os.Process; +import android.os.RemoteException; + +import java.io.File; +import java.io.IOException; +import java.util.ArrayList; +import java.util.HashMap; +import java.util.HashSet; +import java.util.List; +import java.util.Map; +import java.util.Set; + +import com.vcore.BlackBoxCore; + +import com.vcore.core.IBActivityThread; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.notification.BNotificationManagerService; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.entity.AppConfig; +import com.vcore.proxy.ProxyManifest; +import com.vcore.utils.FileUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.ApplicationThreadCompat; +import com.vcore.utils.compat.BundleCompat; +import com.vcore.utils.provider.ProviderCall; + +public class BProcessManagerService implements ISystemService { + public static final String TAG = "BProcessManager"; + + public static final BProcessManagerService sBProcessManagerService = new BProcessManagerService(); + private final Map> mProcessMap = new HashMap<>(); + private final List mPidsSelfLocked = new ArrayList<>(); + private final Object mProcessLock = new Object(); + + public static BProcessManagerService get() { + return sBProcessManagerService; + } + + public ProcessRecord startProcessLocked(String packageName, String processName, int userId, int bPID, int callingPid) { + ApplicationInfo info = BPackageManagerService.get().getApplicationInfo(packageName, 0, userId); + if (info == null) { + return null; + } + + ProcessRecord app; + int bUID = BUserHandle.getUid(userId, BPackageManagerService.get().getAppId(packageName)); + synchronized (mProcessLock) { + Map bProcess = mProcessMap.get(bUID); + + if (bProcess == null) { + bProcess = new HashMap<>(); + } + + if (bPID == -1) { + app = bProcess.get(processName); + if (app != null) { + if (app.initLock != null) { + app.initLock.block(); + } + + if (app.bActivityThread != null) { + return app; + } + } + bPID = getUsingBPidL(); + Slog.d(TAG, "init bUid = " + bUID + ", bPid = " + bPID); + } + + if (bPID == -1) { + throw new RuntimeException("No processes available"); + } + + app = new ProcessRecord(info, processName); + app.uid = Process.myUid(); + app.bPID = bPID; + app.bUID = BPackageManagerService.get().getAppId(packageName); + app.callingBUid = getBUidByPidOrPackageName(callingPid, packageName); + app.userId = userId; + + bProcess.put(processName, app); + mPidsSelfLocked.add(app); + + synchronized (mProcessMap) { + mProcessMap.put(bUID, bProcess); + } + + if (!initAppProcessL(app)) { + bProcess.remove(processName); + mPidsSelfLocked.remove(app); + app = null; + } else { + app.pid = getPid(BlackBoxCore.getContext(), ProxyManifest.getProcessName(app.bPID)); + + Slog.d(TAG, "init pid = " + app.pid); + } + } + return app; + } + + private void killProcess(final ProcessRecord app) { + if (app.pid > 0) { + Process.killProcess(app.pid); + } else { + try { + ActivityManager manager = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); + List runningAppProcesses = manager.getRunningAppProcesses(); + for (ActivityManager.RunningAppProcessInfo runningAppProcess : runningAppProcesses) { + int bPID = parseBPid(runningAppProcess.processName); + if (bPID != -1 && app.bPID == bPID) { + Slog.d(TAG, "force kill process: " + app.processName + ", pid: " + runningAppProcess.pid + ", bPID: " + bPID); + Process.killProcess(runningAppProcess.pid); + } + } + } catch (Throwable e) { + e.printStackTrace(); + } + } + } + + private int getUsingBPidL() { + ActivityManager manager = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); + List runningAppProcesses = manager.getRunningAppProcesses(); + Set usingPs = new HashSet<>(); + + for (ActivityManager.RunningAppProcessInfo runningAppProcess : runningAppProcesses) { + int i = parseBPid(runningAppProcess.processName); + usingPs.add(i); + } + + for (int i = 0; i < ProxyManifest.FREE_COUNT; i++) { + if (usingPs.contains(i)) { + continue; + } + return i; + } + return -1; + } + + public void restartAppProcess(String packageName, String processName, int userId) { + synchronized (mProcessLock) { + int callingPid = Binder.getCallingPid(); + ProcessRecord app = findProcessByPid(callingPid); + if (app != null) { + killProcess(app); + } + + String stubProcessName = getProcessName(BlackBoxCore.getContext(), callingPid); + int bPID = parseBPid(stubProcessName); + startProcessLocked(packageName, processName, userId, bPID, callingPid); + } + } + + private int parseBPid(String stubProcessName) { + String prefix; + if (stubProcessName == null) { + return -1; + } else { + prefix = BlackBoxCore.getHostPkg() + ":p"; + } + + if (stubProcessName.startsWith(prefix)) { + try { + return Integer.parseInt(stubProcessName.substring(prefix.length())); + } catch (NumberFormatException ignored) { } + } + return -1; + } + + private boolean initAppProcessL(ProcessRecord record) { + Slog.d(TAG, "initProcess: " + record.processName); + AppConfig appConfig = record.getClientConfig(); + Bundle bundle = new Bundle(); + bundle.putParcelable(AppConfig.KEY, appConfig); + Bundle init = ProviderCall.callSafely(record.getProviderAuthority(), "_Black_|_init_process_", null, bundle); + + IBinder appThread = BundleCompat.getBinder(init, "_Black_|_client_"); + if (appThread == null || !appThread.isBinderAlive()) { + return false; + } + + attachClientL(record, appThread); + createProc(record); + return true; + } + + private void attachClientL(final ProcessRecord app, final IBinder appThread) { + IBActivityThread activityThread = IBActivityThread.Stub.asInterface(appThread); + if (activityThread == null) { + killProcess(app); + return; + } + + try { + appThread.linkToDeath(new IBinder.DeathRecipient() { + @Override + public void binderDied() { + Slog.d(TAG, "App Died: " + app.processName); + appThread.unlinkToDeath(this, 0); + onProcessDie(app); + } + }, 0); + } catch (RemoteException e) { + e.printStackTrace(); + } + + app.bActivityThread = activityThread; + try { + app.appThread = ApplicationThreadCompat.asInterface(activityThread.getActivityThread()); + } catch (RemoteException e) { + e.printStackTrace(); + } + app.initLock.open(); + } + + public void onProcessDie(ProcessRecord record) { + synchronized (mProcessLock) { + killProcess(record); + Map process = mProcessMap.get(record.bUID); + if (process != null) { + process.remove(record.processName); + if (process.isEmpty()) { + mProcessMap.remove(record.bUID); + } + } + + mPidsSelfLocked.remove(record); + removeProc(record); + BNotificationManagerService.get().deletePackageNotification(record.getPackageName(), record.userId); + } + } + + public ProcessRecord findProcessRecord(String packageName, String processName, int userId) { + synchronized (mProcessMap) { + int appId = BPackageManagerService.get().getAppId(packageName); + int bUID = BUserHandle.getUid(userId, appId); + + Map processRecordMap = mProcessMap.get(bUID); + if (processRecordMap == null) { + return null; + } + return processRecordMap.get(processName); + } + } + + public void killAllByPackageName(String packageName) { + synchronized (mProcessLock) { + synchronized (mPidsSelfLocked) { + List tmp = new ArrayList<>(mPidsSelfLocked); + int appId = BPackageManagerService.get().getAppId(packageName); + for (ProcessRecord processRecord : mPidsSelfLocked) { + int appId1 = BUserHandle.getAppId(processRecord.bUID); + if (appId == appId1) { + mProcessMap.remove(processRecord.bUID); + killProcess(processRecord); + tmp.remove(processRecord); + } + } + mPidsSelfLocked.clear(); + mPidsSelfLocked.addAll(tmp); + } + } + } + + public void killPackageAsUser(String packageName, int userId) { + synchronized (mProcessLock) { + int bUID = BUserHandle.getUid(userId, BPackageManagerService.get().getAppId(packageName)); + Map process = mProcessMap.get(bUID); + if (process == null) { + return; + } + + for (ProcessRecord value : process.values()) { + killProcess(value); + mPidsSelfLocked.remove(value); + } + mProcessMap.remove(bUID); + } + } + + public List getPackageProcessAsUser(String packageName, int userId) { + synchronized (mProcessMap) { + int bUID = BUserHandle.getUid(userId, BPackageManagerService.get().getAppId(packageName)); + Map process = mProcessMap.get(bUID); + if (process == null) { + return new ArrayList<>(); + } + return new ArrayList<>(process.values()); + } + } + + public int getBUidByPidOrPackageName(int pid, String packageName) { + ProcessRecord callingProcess = findProcessByPid(pid); + if (callingProcess == null) { + return BPackageManagerService.get().getAppId(packageName); + } + return BUserHandle.getAppId(callingProcess.bUID); + } + + public int getUserIdByCallingPid(int callingPid) { + ProcessRecord callingProcess = findProcessByPid(callingPid); + if (callingProcess == null) { + return 0; + } + return callingProcess.userId; + } + + public ProcessRecord findProcessByPid(int pid) { + synchronized (mPidsSelfLocked) { + for (ProcessRecord processRecord : mPidsSelfLocked) { + if (processRecord.pid == pid) { + return processRecord; + } + } + return null; + } + } + + private static String getProcessName(Context context, int pid) { + String processName = null; + ActivityManager am = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); + for (ActivityManager.RunningAppProcessInfo info : am.getRunningAppProcesses()) { + if (info.pid == pid) { + processName = info.processName; + break; + } + } + if (processName == null) { + throw new RuntimeException("processName = null"); + } + return processName; + } + + public static int getPid(Context context, String processName) { + try { + ActivityManager manager = (ActivityManager) context.getSystemService(Context.ACTIVITY_SERVICE); + List runningAppProcesses = manager.getRunningAppProcesses(); + for (ActivityManager.RunningAppProcessInfo runningAppProcess : runningAppProcesses) { + if (runningAppProcess.processName.equals(processName)) { + return runningAppProcess.pid; + } + } + } catch (Throwable e) { + e.printStackTrace(); + } + return -1; + } + + private static void createProc(ProcessRecord record) { + File cmdline = new File(BEnvironment.getProcDir(record.bPID), "cmdline"); + try { + FileUtils.writeToFile(record.processName.getBytes(), cmdline); + } catch (IOException ignored) { } + } + + private static void removeProc(ProcessRecord record) { + FileUtils.deleteDir(BEnvironment.getProcDir(record.bPID)); + } + + @Override + public void systemReady() { + FileUtils.deleteDir(BEnvironment.getProcDir()); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BlackBoxSystem.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BlackBoxSystem.java new file mode 100644 index 0000000..8bf56b4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/BlackBoxSystem.java @@ -0,0 +1,70 @@ +package com.vcore.core.system; + +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; + +import java.util.ArrayList; +import java.util.List; +import java.util.concurrent.atomic.AtomicBoolean; + +import com.vcore.BlackBoxCore; +import com.vcore.core.env.AppSystemEnv; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.accounts.BAccountManagerService; +import com.vcore.core.system.am.BActivityManagerService; +import com.vcore.core.system.am.BJobManagerService; +import com.vcore.core.system.location.BLocationManagerService; +import com.vcore.core.system.notification.BNotificationManagerService; +import com.vcore.core.system.os.BStorageManagerService; +import com.vcore.core.system.pm.BPackageInstallerService; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.BXposedManagerService; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.core.system.user.BUserManagerService; +import com.vcore.entity.pm.InstallOption; + +public class BlackBoxSystem { + private final List mServices = new ArrayList<>(); + private final static AtomicBoolean isStartup = new AtomicBoolean(false); + + private static final class SBlackBoxSystemHolder { + static final BlackBoxSystem sBlackBoxSystem = new BlackBoxSystem(); + } + + public static BlackBoxSystem getSystem() { + return SBlackBoxSystemHolder.sBlackBoxSystem; + } + + public void startup() { + if (isStartup.getAndSet(true)) { + return; + } + + BEnvironment.load(); + mServices.add(BPackageManagerService.get()); + mServices.add(BUserManagerService.get()); + mServices.add(BActivityManagerService.get()); + mServices.add(BJobManagerService.get()); + mServices.add(BStorageManagerService.get()); + mServices.add(BPackageInstallerService.get()); + mServices.add(BXposedManagerService.get()); + mServices.add(BProcessManagerService.get()); + mServices.add(BAccountManagerService.get()); + mServices.add(BLocationManagerService.get()); + mServices.add(BNotificationManagerService.get()); + + for (ISystemService service : mServices) { + service.systemReady(); + } + + List preInstallPackages = AppSystemEnv.getPreInstallPackages(); + for (String preInstallPackage : preInstallPackages) { + try { + if (!BPackageManagerService.get().isInstalled(preInstallPackage, BUserHandle.USER_ALL)) { + PackageInfo packageInfo = BlackBoxCore.getPackageManager().getPackageInfo(preInstallPackage, 0); + BPackageManagerService.get().installPackageAsUser(packageInfo.applicationInfo.sourceDir, InstallOption.installBySystem(), BUserHandle.USER_ALL); + } + } catch (PackageManager.NameNotFoundException ignored) { } + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/DaemonService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/DaemonService.java similarity index 86% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/DaemonService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/DaemonService.java index 6a3660d..8d0d7ce 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/DaemonService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/DaemonService.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system; +package com.vcore.core.system; import android.app.NotificationManager; import android.app.Service; @@ -9,18 +9,9 @@ import androidx.core.app.NotificationCompat; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.utils.compat.BuildCompat; +import com.vcore.BlackBoxCore; +import com.vcore.utils.compat.BuildCompat; - -/** - * Created by Milk on 3/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class DaemonService extends Service { public static final String TAG = "DaemonService"; private static final int NOTIFY_ID = BlackBoxCore.getHostPkg().hashCode(); @@ -30,11 +21,6 @@ public IBinder onBind(Intent intent) { return null; } - @Override - public void onCreate() { - super.onCreate(); - } - @Override public int onStartCommand(Intent intent, int flags, int startId) { Intent innerIntent = new Intent(this, DaemonInnerService.class); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ISystemService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ISystemService.java new file mode 100644 index 0000000..735bf75 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ISystemService.java @@ -0,0 +1,5 @@ +package com.vcore.core.system; + +public interface ISystemService { + void systemReady(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ProcessRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ProcessRecord.java new file mode 100644 index 0000000..516cb3b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ProcessRecord.java @@ -0,0 +1,58 @@ +package com.vcore.core.system; + +import android.content.pm.ApplicationInfo; +import android.os.Binder; +import android.os.ConditionVariable; +import android.os.IInterface; + +import java.util.Arrays; + +import com.vcore.core.IBActivityThread; +import com.vcore.entity.AppConfig; +import com.vcore.proxy.ProxyManifest; + +public class ProcessRecord extends Binder { + public final ApplicationInfo info; + final public String processName; + public IBActivityThread bActivityThread; + public IInterface appThread; + public int uid; + public int pid; + public int bUID; + public int bPID; + public int callingBUid; + public int userId; + + public final ConditionVariable initLock = new ConditionVariable(); + + public ProcessRecord(ApplicationInfo info, String processName) { + this.info = info; + this.processName = processName; + } + + @Override + public int hashCode() { + return Arrays.hashCode(new Object[]{processName, pid, bUID, bPID, uid, pid, userId}); + } + + public String getProviderAuthority() { + return ProxyManifest.getProxyAuthorities(bPID); + } + + public AppConfig getClientConfig() { + AppConfig config = new AppConfig(); + config.packageName = info.packageName; + config.processName = processName; + config.bPID = bPID; + config.bUID = bUID; + config.uid = uid; + config.callingBUid = callingBUid; + config.userId = userId; + config.token = this; + return config; + } + + public String getPackageName() { + return info.packageName; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ServiceManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ServiceManager.java new file mode 100644 index 0000000..f8c6e40 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/ServiceManager.java @@ -0,0 +1,71 @@ +package com.vcore.core.system; + +import android.os.IBinder; + +import java.util.HashMap; +import java.util.Map; + +import com.vcore.BlackBoxCore; +import com.vcore.core.system.accounts.BAccountManagerService; +import com.vcore.core.system.am.BActivityManagerService; +import com.vcore.core.system.am.BJobManagerService; +import com.vcore.core.system.location.BLocationManagerService; +import com.vcore.core.system.notification.BNotificationManagerService; +import com.vcore.core.system.os.BStorageManagerService; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.BXposedManagerService; +import com.vcore.core.system.user.BUserManagerService; + +public class ServiceManager { + public static final String ACTIVITY_MANAGER = "activity_manager"; + public static final String JOB_MANAGER = "job_manager"; + public static final String PACKAGE_MANAGER = "package_manager"; + public static final String STORAGE_MANAGER = "storage_manager"; + public static final String USER_MANAGER = "user_manager"; + public static final String XPOSED_MANAGER = "xposed_manager"; + public static final String ACCOUNT_MANAGER = "account_manager"; + public static final String LOCATION_MANAGER = "location_manager"; + public static final String NOTIFICATION_MANAGER = "notification_manager"; + + private final Map mCaches = new HashMap<>(); + + private static final class SServiceManagerHolder { + static final ServiceManager sServiceManager = new ServiceManager(); + } + + public static ServiceManager get() { + return SServiceManagerHolder.sServiceManager; + } + + public static IBinder getService(String name) { + return get().getServiceInternal(name); + } + + private ServiceManager() { + mCaches.put(ACTIVITY_MANAGER, BActivityManagerService.get()); + mCaches.put(JOB_MANAGER, BJobManagerService.get()); + mCaches.put(PACKAGE_MANAGER, BPackageManagerService.get()); + mCaches.put(STORAGE_MANAGER, BStorageManagerService.get()); + mCaches.put(USER_MANAGER, BUserManagerService.get()); + mCaches.put(XPOSED_MANAGER, BXposedManagerService.get()); + mCaches.put(ACCOUNT_MANAGER, BAccountManagerService.get()); + mCaches.put(LOCATION_MANAGER, BLocationManagerService.get()); + mCaches.put(NOTIFICATION_MANAGER, BNotificationManagerService.get()); + } + + public IBinder getServiceInternal(String name) { + return mCaches.get(name); + } + + public static void initBlackManager() { + BlackBoxCore.get().getService(ACTIVITY_MANAGER); + BlackBoxCore.get().getService(JOB_MANAGER); + BlackBoxCore.get().getService(PACKAGE_MANAGER); + BlackBoxCore.get().getService(STORAGE_MANAGER); + BlackBoxCore.get().getService(USER_MANAGER); + BlackBoxCore.get().getService(XPOSED_MANAGER); + BlackBoxCore.get().getService(ACCOUNT_MANAGER); + BlackBoxCore.get().getService(LOCATION_MANAGER); + BlackBoxCore.get().getService(NOTIFICATION_MANAGER); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/SystemCallProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/SystemCallProvider.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/SystemCallProvider.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/SystemCallProvider.java index 01a264e..ad77c46 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/SystemCallProvider.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/SystemCallProvider.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system; +package com.vcore.core.system; import android.content.ContentProvider; import android.content.ContentValues; @@ -9,17 +9,9 @@ import androidx.annotation.NonNull; import androidx.annotation.Nullable; -import top.niunaijun.blackbox.utils.Slog; -import top.niunaijun.blackbox.utils.compat.BundleCompat; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BundleCompat; -/** - * Created by Milk on 3/31/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class SystemCallProvider extends ContentProvider { public static final String TAG = "SystemCallProvider"; diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccount.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccount.java new file mode 100644 index 0000000..c557d35 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccount.java @@ -0,0 +1,66 @@ +package com.vcore.core.system.accounts; + +import android.accounts.Account; +import android.os.Parcel; +import android.os.Parcelable; + +import java.util.HashMap; +import java.util.LinkedHashMap; + +public class BAccount implements Parcelable { + public Account account; + public String password; + public HashMap accountUserData = new LinkedHashMap<>(); + public HashMap visibility = new LinkedHashMap<>(); + public HashMap authTokens = new LinkedHashMap<>(); + public long updateLastAuthenticatedTime; + + public boolean isMatch(Account account) { + if (account == null) { + return false; + } + return account.equals(this.account); + } + + public void insertExtra(String key, String value) { + this.accountUserData.put(key, value); + } + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeParcelable(this.account, flags); + dest.writeString(this.password); + dest.writeSerializable(this.accountUserData); + dest.writeSerializable(this.visibility); + dest.writeSerializable(this.authTokens); + dest.writeLong(this.updateLastAuthenticatedTime); + } + + public BAccount() { } + + protected BAccount(Parcel in) { + this.account = in.readParcelable(Account.class.getClassLoader()); + this.password = in.readString(); + this.accountUserData = (HashMap) in.readSerializable(); + this.visibility = (HashMap) in.readSerializable(); + this.authTokens = (HashMap) in.readSerializable(); + this.updateLastAuthenticatedTime = in.readLong(); + } + + public static final Creator CREATOR = new Creator() { + @Override + public BAccount createFromParcel(Parcel source) { + return new BAccount(source); + } + + @Override + public BAccount[] newArray(int size) { + return new BAccount[size]; + } + }; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccountManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccountManagerService.java new file mode 100644 index 0000000..2312c57 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BAccountManagerService.java @@ -0,0 +1,1746 @@ +package com.vcore.core.system.accounts; + +import android.accounts.AbstractAccountAuthenticator; +import android.accounts.Account; +import android.accounts.AccountManager; +import android.accounts.AuthenticatorDescription; +import android.accounts.IAccountAuthenticator; +import android.accounts.IAccountAuthenticatorResponse; +import android.accounts.IAccountManagerResponse; +import android.annotation.SuppressLint; +import android.content.ClipData; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.ServiceConnection; +import android.content.pm.PackageManager; +import android.content.pm.ResolveInfo; +import android.content.pm.ServiceInfo; +import android.content.res.Resources; +import android.content.res.TypedArray; +import android.content.res.XmlResourceParser; +import android.os.Binder; +import android.os.Bundle; +import android.os.Handler; +import android.os.IBinder; +import android.os.Looper; +import android.os.Parcel; +import android.os.Parcelable; +import android.os.RemoteException; +import android.os.SystemClock; +import android.text.TextUtils; +import android.util.AttributeSet; +import android.util.Log; +import android.util.Xml; + +import androidx.annotation.NonNull; +import androidx.core.util.AtomicFile; +import androidx.core.util.Preconditions; + +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.HashMap; +import java.util.Iterator; +import java.util.LinkedHashMap; +import java.util.LinkedList; +import java.util.List; +import java.util.Map; +import java.util.Objects; + +import com.vcore.BlackBoxCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.PackageMonitor; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.utils.ArrayUtils; +import com.vcore.utils.CloseUtils; +import com.vcore.utils.FileUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.AccountManagerCompat; + + +@SuppressLint("InlinedApi") +public class BAccountManagerService extends IBAccountManagerService.Stub implements ISystemService, PackageMonitor { + private static final String TAG = "AccountManagerService"; + private static final BAccountManagerService sService = new BAccountManagerService(); + private static final Account[] EMPTY_ACCOUNT_ARRAY = new Account[]{}; + + // Messages that can be sent on mHandler + private static final int MESSAGE_TIMED_OUT = 3; + + private final BPackageManagerService mPms; + private final Map mUserAccountsMap = new HashMap<>(); + private final AuthenticatorCache mAuthenticatorCache = new AuthenticatorCache(); + + private final LinkedList mTokenCaches = new LinkedList<>(); + private final LinkedHashMap mSessions = new LinkedHashMap<>(); + private final Handler mHandler = new Handler(Looper.getMainLooper()); + + private final Context mContext; + + public static BAccountManagerService get() { + return sService; + } + + public BAccountManagerService() { + this.mContext = BlackBoxCore.getContext(); + this.mPms = BPackageManagerService.get(); + } + + @Override + public void systemReady() { + loadAccounts(); + loadAuthenticatorCache(null); + mPms.addPackageMonitor(this); + } + + @Override + public void onPackageUninstalled(String packageName, boolean isRemove, int userId) { + loadAuthenticatorCache(null); + } + + @Override + public void onPackageInstalled(String packageName, int userId) { + loadAuthenticatorCache(packageName); + } + + private void loadAccounts() { + Parcel parcel = Parcel.obtain(); + InputStream is = null; + try { + File userInfoConf = BEnvironment.getAccountsConf(); + if (!userInfoConf.exists()) { + return; + } + + is = new FileInputStream(BEnvironment.getAccountsConf()); + byte[] bytes = FileUtils.toByteArray(is); + parcel.unmarshall(bytes, 0, bytes.length); + parcel.setDataPosition(0); + + HashMap accountsMap = parcel.readHashMap(BUserAccounts.class.getClassLoader()); + if (accountsMap == null) { + return; + } + + synchronized (mUserAccountsMap) { + mUserAccountsMap.clear(); + for (Integer key : accountsMap.keySet()) { + mUserAccountsMap.put(key, accountsMap.get(key)); + } + } + } catch (Exception e) { + e.printStackTrace(); + } finally { + parcel.recycle(); + CloseUtils.close(is); + } + } + + private void saveAllAccounts() { + synchronized (mUserAccountsMap) { + Parcel parcel = Parcel.obtain(); + AtomicFile atomicFile = new AtomicFile(BEnvironment.getAccountsConf()); + FileOutputStream fileOutputStream = null; + + try { + parcel.writeMap(mUserAccountsMap); + try { + fileOutputStream = atomicFile.startWrite(); + FileUtils.writeParcelToOutput(parcel, fileOutputStream); + atomicFile.finishWrite(fileOutputStream); + } catch (IOException e) { + e.printStackTrace(); + atomicFile.failWrite(fileOutputStream); + } finally { + CloseUtils.close(fileOutputStream); + } + } finally { + parcel.recycle(); + } + } + } + + @Override + public String getPassword(Account account, int userId) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "getPassword: " + account + ", caller's uid " + Binder.getCallingUid() + ", pid " + Binder.getCallingPid()); + } + + if (account == null) { + throw new IllegalArgumentException("account is null"); + } + BUserAccounts accounts = getUserAccounts(userId); + return readPasswordInternal(accounts, account); + } + + @Override + public String getUserData(Account account, String key, int userId) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + String msg = String.format("getUserData( account: %s, key: %s, callerUid: %s, pid: %s", account, key, Binder.getCallingUid(), + Binder.getCallingPid()); + Log.v(TAG, msg); + } + + Objects.requireNonNull(account, "account cannot be null"); + Objects.requireNonNull(key, "key cannot be null"); + BUserAccounts accounts = getUserAccounts(userId); + return readUserDataInternal(accounts, account, key); + } + + @Override + public AuthenticatorDescription[] getAuthenticatorTypes(int userId) { + // Only allow the system process to read accounts of other users + BUserAccounts userAccounts = getUserAccounts(userId); + List authenticatorDescriptions = new ArrayList<>(); + synchronized (userAccounts.lock) { + for (BAccount account : userAccounts.accounts) { + AuthenticatorInfo authenticatorInfo = mAuthenticatorCache.authenticators.get(account.account.type); + if (authenticatorInfo != null) { + authenticatorDescriptions.add(authenticatorInfo.desc); + } + } + } + return authenticatorDescriptions.toArray(new AuthenticatorDescription[]{}); + } + + @Override + public Account[] getAccountsForPackage(String packageName, int uid, int userId) { + // Only allow the system process to read accounts of other users + BUserAccounts userAccounts = getUserAccounts(userId); + List accounts = new ArrayList<>(); + synchronized (userAccounts.lock) { + for (BAccount account : userAccounts.accounts) { + Integer visibility = account.visibility.get(packageName); + if (visibility != null && visibility == AccountManager.VISIBILITY_VISIBLE) { + accounts.add(account.account); + } + } + } + return accounts.toArray(new Account[]{}); + } + + @Override + public Account[] getAccountsByTypeForPackage(String type, String packageName, int userId) { + // Only allow the system process to read accounts of other users + BUserAccounts userAccounts = getUserAccounts(userId); + List accounts = new ArrayList<>(); + synchronized (userAccounts.lock) { + for (BAccount account : userAccounts.accounts) { + if (account.account.type.equals(type)) { + Integer visibility = account.visibility.get(packageName); + if (visibility != null && visibility == AccountManager.VISIBILITY_VISIBLE) { + accounts.add(account.account); + } + } + } + } + return accounts.toArray(new Account[]{}); + } + + @Override + public Account[] getAccountsAsUser(String accountType, int userId) { + BUserAccounts userAccounts = getUserAccounts(userId); + List accounts = new ArrayList<>(); + synchronized (userAccounts.lock) { + for (BAccount account : userAccounts.accounts) { + if (account.account.type.equals(accountType)) { + accounts.add(account.account); + } + } + } + return accounts.toArray(new Account[]{}); + } + + @Override + public void getAccountByTypeAndFeatures(IAccountManagerResponse response, String accountType, String[] features, int userId) { + if (response == null) { + throw new IllegalArgumentException("response is null"); + } + + if (accountType == null) { + throw new IllegalArgumentException("accountType is null"); + } + + String opPackageName = getCallingPackageName(); + BUserAccounts userAccounts = getUserAccounts(userId); + + if (ArrayUtils.isEmpty(features)) { + Account[] accountsWithManagedNotVisible = getAccountsFromCache(userAccounts, accountType, opPackageName, + true /* include managed not visible */); + handleGetAccountsResult(response, accountsWithManagedNotVisible, opPackageName, userId); + return; + } + + IAccountManagerResponse retrieveAccountsResponse = + new IAccountManagerResponse.Stub() { + @Override + public void onResult(Bundle value) { + Parcelable[] parcelables = value.getParcelableArray(AccountManager.KEY_ACCOUNTS); + + Account[] accounts = new Account[parcelables.length]; + for (int i = 0; i < parcelables.length; i++) { + accounts[i] = (Account) parcelables[i]; + } + handleGetAccountsResult(response, accounts, opPackageName, userId); + } + + @Override + public void onError(int errorCode, String errorMessage) { + // Will not be called in this case. + } + }; + new GetAccountsByTypeAndFeatureSession(userAccounts, retrieveAccountsResponse, accountType, features, userId, opPackageName, + true /* include managed not visible */) + .bind(); + } + + @Override + public void getAccountsByFeatures(IAccountManagerResponse response, String type, String[] features, int userId) { + if (response == null) { + throw new IllegalArgumentException("response is null"); + } + + if (type == null) { + throw new IllegalArgumentException("accountType is null"); + } + + String opPackageName = getCallingPackageName(); + // Check visibleAccountTypes + BUserAccounts userAccounts = getUserAccounts(userId); + if (features == null || features.length == 0) { + Account[] accounts = getAccountsFromCache(userAccounts, type, opPackageName, false); + + Bundle result = new Bundle(); + result.putParcelableArray(AccountManager.KEY_ACCOUNTS, accounts); + + onResult(response, result); + return; + } + new GetAccountsByTypeAndFeatureSession(userAccounts, response, type, features, userId, opPackageName, + false /* include managed not visible */) + .bind(); + } + + @Override + public boolean addAccountExplicitly(Account account, String password, Bundle extras, int userId) { + return addAccountExplicitlyWithVisibility(account, password, extras, null, userId); + } + + @Override + public void removeAccountAsUser(IAccountManagerResponse response, Account account, boolean expectActivityLaunch, int userId) { + Preconditions.checkArgument(account != null, "Account cannot be null"); + Preconditions.checkArgument(response != null, "Response cannot be null"); + // Only allow the system process to modify accounts of other users + /* + * Only the system, authenticator or profile owner should be allowed to remove accounts for + * that authenticator. This will let users remove accounts (via Settings in the system) but + * not arbitrary applications (like competing authenticators). + */ + BUserAccounts accounts = getUserAccounts(userId); + new RemoveAccountSession(accounts, response, account, expectActivityLaunch) + .bind(); + } + + @Override + public boolean removeAccountExplicitly(Account account, int userId) { + final int callingUid = Binder.getCallingUid(); + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "removeAccountExplicitly: " + account + ", caller's uid " + callingUid + ", pid " + Binder.getCallingPid()); + } + + if (account == null) { + /* + * Null accounts should result in returning false, as per + * AccountManage.addAccountExplicitly(...) java doc. + */ + Log.e(TAG, "account is null"); + return false; + } + BUserAccounts accounts = getUserAccounts(userId); + return removeAccountInternal(accounts, account); + } + + @Override + public void copyAccountToUser(IAccountManagerResponse response, Account account, int userFrom, int userTo) { + final BUserAccounts fromAccounts = getUserAccounts(userFrom); + final BUserAccounts toAccounts = getUserAccounts(userTo); + if (fromAccounts == null || toAccounts == null) { + if (response != null) { + Bundle result = new Bundle(); + result.putBoolean(AccountManager.KEY_BOOLEAN_RESULT, false); + try { + response.onResult(result); + } catch (RemoteException e) { + Slog.w(TAG, "Failed to report error back to the client." + e); + } + } + return; + } + + Slog.d(TAG, "Copying account " + account.toString() + " from user " + userFrom + " to user " + userTo); + new Session(fromAccounts, response, account.type, false, false /* stripAuthTokenFromResult */, account.name, + false /* authDetailsRequired */) { + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", getAccountCredentialsForClone" + ", " + account.type; + } + + @Override + public void run() throws RemoteException { + mAuthenticator.getAccountCredentialsForCloning(this, account); + } + + @Override + public void onResult(Bundle result) { + if (result != null && result.getBoolean(AccountManager.KEY_BOOLEAN_RESULT, false)) { + // Create a Session for the target user and pass in the bundle + completeCloningAccount(response, result, account, toAccounts, userFrom); + } + super.onResult(result); + } + } + .bind(); + } + + @Override + public void invalidateAuthToken(String accountType, String authToken, int userId) { + BUserAccounts accounts = getUserAccounts(userId); + synchronized (accounts.lock) { + boolean changed = false; + for (BAccount account : accounts.accounts) { + if (account.account.type.equals(accountType)) { + account.accountUserData.values().remove(authToken); + changed = true; + } + } + + if (changed) { + saveAllAccounts(); + } + } + + synchronized (mTokenCaches) { + Iterator iterator = mTokenCaches.iterator(); + while (iterator.hasNext()) { + TokenCache next = iterator.next(); + if (next.account.type.equals(accountType) && next.userId == userId && next.authToken.equals(authToken)) { + iterator.remove(); + } + } + } + } + + @Override + public String peekAuthToken(Account account, String authTokenType, int userId) { + Objects.requireNonNull(account, "Account cannot be null"); + Objects.requireNonNull(authTokenType, "AuthTokenType cannot be null"); + + BUserAccounts accounts = getUserAccounts(userId); + if (accounts == null) { + return null; + } + + synchronized (accounts.lock) { + return accounts.getAuthToken(account).get(authTokenType); + } + } + + @Override + public void setAuthToken(Account account, String authTokenType, String authToken, int userId) { + Objects.requireNonNull(account, "Account cannot be null"); + Objects.requireNonNull(authTokenType, "AuthTokenType cannot be null"); + + BUserAccounts accounts = getUserAccounts(userId); + if (accounts == null) { + return; + } + + synchronized (accounts.lock) { + accounts.getAuthToken(account).put(authTokenType, authToken); + saveAllAccounts(); + } + } + + @Override + public void setPassword(Account account, String password, int userId) { + Objects.requireNonNull(account, "Account cannot be null"); + BUserAccounts accounts = getUserAccounts(userId); + if (accounts == null) { + return; + } + + synchronized (accounts.lock) { + BAccount bAccount = accounts.getAccount(account); + bAccount.password = password; + bAccount.authTokens.clear(); + saveAllAccounts(); + } + + synchronized (mTokenCaches) { + Iterator iterator = mTokenCaches.iterator(); + while (iterator.hasNext()) { + TokenCache next = iterator.next(); + if (next.account.equals(account) && next.userId == userId) { + iterator.remove(); + } + } + } + } + + @Override + public void clearPassword(Account account, int userId) { + setPassword(account, null, userId); + } + + @Override + public void setUserData(Account account, String key, String value, int userId) { + if (key == null) { + throw new IllegalArgumentException("key is null"); + } + + if (account == null) { + throw new IllegalArgumentException("account is null"); + } + + BUserAccounts accounts = getUserAccounts(userId); + if (accounts == null) { + return; + } + + synchronized (accounts.lock) { + accounts.getAccountUserData(account).put(key, value); + saveAllAccounts(); + } + } + + @Override + public void updateAppPermission(Account account, String authTokenType, int uid, boolean value) { + // System + } + + @Override + public void getAuthToken(IAccountManagerResponse response, Account account, String authTokenType, boolean notifyOnAuthFailure, boolean expectActivityLaunch, Bundle loginOptions, int userId) { + Preconditions.checkArgument(response != null, "response cannot be null"); + try { + if (account == null) { + Slog.w(TAG, "getAuthToken called with null account"); + response.onError(AccountManager.ERROR_CODE_BAD_ARGUMENTS, "account is null"); + return; + } + + if (authTokenType == null) { + Slog.w(TAG, "getAuthToken called with null authTokenType"); + response.onError(AccountManager.ERROR_CODE_BAD_ARGUMENTS, "authTokenType is null"); + return; + } + } catch (RemoteException e) { + Slog.w(TAG, "Failed to report error back to the client." + e); + return; + } + + final BUserAccounts accounts = getUserAccounts(userId); + AuthenticatorInfo authenticatorInfo = mAuthenticatorCache.authenticators.get(account.type); + + final boolean customTokens = authenticatorInfo != null && authenticatorInfo.desc.customTokens; + + // Get the calling package. We will use it for the purpose of caching. + final String callerPkg = loginOptions.getString(AccountManager.KEY_ANDROID_PACKAGE_NAME); + + // Let authenticator know the identity of the caller + loginOptions.putInt(AccountManager.KEY_CALLER_UID, Binder.getCallingUid()); + loginOptions.putInt(AccountManager.KEY_CALLER_PID, Binder.getCallingPid()); + + if (notifyOnAuthFailure) { + loginOptions.putBoolean(AccountManagerCompat.KEY_NOTIFY_ON_FAILURE, true); + } + + // if the caller has permission, do the peek. otherwise go the more expensive + // route of starting a Session + if (!customTokens) { + String authToken = readAuthTokenInternal(accounts, account, authTokenType); + if (authToken != null) { + Bundle result = new Bundle(); + result.putString(AccountManager.KEY_AUTHTOKEN, authToken); + result.putString(AccountManager.KEY_ACCOUNT_NAME, account.name); + result.putString(AccountManager.KEY_ACCOUNT_TYPE, account.type); + + onResult(response, result); + return; + } + } + + if (customTokens) { + /* + * Look up tokens in the new cache only if the loginOptions don't have parameters + * outside of those expected to be injected by the AccountManager, e.g. + * ANDROID_PACKAGE_NAME. + */ + String token = readCachedTokenInternal(accounts, account, authTokenType, callerPkg); + if (token != null) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "getAuthToken: cache hit ofr custom token authenticator."); + } + + Bundle result = new Bundle(); + result.putString(AccountManager.KEY_AUTHTOKEN, token); + result.putString(AccountManager.KEY_ACCOUNT_NAME, account.name); + result.putString(AccountManager.KEY_ACCOUNT_TYPE, account.type); + + onResult(response, result); + return; + } + } + new Session(accounts, response, account.type, expectActivityLaunch, false /* stripAuthTokenFromResult */, + account.name, false /* authDetailsRequired */) { + @Override + protected String toDebugString(long now) { + loginOptions.keySet(); + return super.toDebugString(now) + ", getAuthToken" + ", " + account + ", authTokenType " + authTokenType + ", loginOptions " + loginOptions + + ", notifyOnAuthFailure " + notifyOnAuthFailure; + } + + @Override + public void run() throws RemoteException { + // If the caller doesn't have permission then create and return the + // "grant permission" intent instead of the "getAuthToken" intent. + mAuthenticator.getAuthToken(this, account, authTokenType, loginOptions); + } + + @Override + public void onResult(Bundle result) { + if (result != null) { + String authToken = result.getString(AccountManager.KEY_AUTHTOKEN); + if (authToken != null) { + String name = result.getString(AccountManager.KEY_ACCOUNT_NAME); + String type = result.getString(AccountManager.KEY_ACCOUNT_TYPE); + if (TextUtils.isEmpty(type) || TextUtils.isEmpty(name)) { + onError(AccountManager.ERROR_CODE_INVALID_RESPONSE, "the type and name should not be empty"); + return; + } + + Account resultAccount = new Account(name, type); + if (!customTokens) { + saveAuthTokenToDatabase(mAccounts, resultAccount, authTokenType, authToken); + } + + long expiryMillis = result.getLong(AbstractAccountAuthenticator.KEY_CUSTOM_TOKEN_EXPIRY, 0L); + if (customTokens && expiryMillis > System.currentTimeMillis()) { + saveCachedToken(mAccounts, account, callerPkg, authTokenType, authToken, expiryMillis); + } + } + } + super.onResult(result); + } + } + .bind(); + } + + @Override + public void addAccount(IAccountManagerResponse response, String accountType, String authTokenType, String[] requiredFeatures, boolean expectActivityLaunch, Bundle optionsIn, int userId) { + if (response == null) { + throw new IllegalArgumentException("response is null"); + } + + if (accountType == null) { + throw new IllegalArgumentException("accountType is null"); + } + + final Bundle options = (optionsIn == null) ? new Bundle() : optionsIn; + BUserAccounts accounts = getUserAccounts(userId); + + new Session(accounts, response, accountType, expectActivityLaunch, + true /* stripAuthTokenFromResult */, null /* accountName */, + false /* authDetailsRequired */, true /* updateLastAuthenticationTime */) { + @Override + public void run() throws RemoteException { + mAuthenticator.addAccount(this, mAccountType, authTokenType, requiredFeatures, options); + } + + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", addAccount" + ", accountType " + accountType + ", requiredFeatures " + + Arrays.toString(requiredFeatures); + } + } + .bind(); + } + + @Override + public void addAccountAsUser(IAccountManagerResponse response, String accountType, String authTokenType, String[] requiredFeatures, boolean expectActivityLaunch, Bundle options, int userId) { + // Ignore + } + + @Override + public void updateCredentials(IAccountManagerResponse response, Account account, String authTokenType, boolean expectActivityLaunch, Bundle loginOptions, int userId) { + if (response == null) { + throw new IllegalArgumentException("response is null"); + } + + if (account == null) { + throw new IllegalArgumentException("account is null"); + } + + BUserAccounts accounts = getUserAccounts(userId); + new Session(accounts, response, account.type, expectActivityLaunch, + true /* stripAuthTokenFromResult */, account.name, + false /* authDetailsRequired */, true /* updateLastCredentialTime */) { + @Override + public void run() throws RemoteException { + mAuthenticator.updateCredentials(this, account, authTokenType, loginOptions); + } + @Override + protected String toDebugString(long now) { + if (loginOptions != null) { + loginOptions.keySet(); + } + return super.toDebugString(now) + ", updateCredentials" + ", " + account + ", authTokenType " + authTokenType + + ", loginOptions " + loginOptions; + } + } + .bind(); + } + + @Override + public void editProperties(IAccountManagerResponse response, String accountType, boolean expectActivityLaunch, int userId) { + if (response == null) { + throw new IllegalArgumentException("response is null"); + } + + if (accountType == null) { + throw new IllegalArgumentException("accountType is null"); + } + + BUserAccounts accounts = getUserAccounts(userId); + new Session(accounts, response, accountType, expectActivityLaunch, + true /* stripAuthTokenFromResult */, null /* accountName */, + false /* authDetailsRequired */) { + @Override + public void run() throws RemoteException { + mAuthenticator.editProperties(this, mAccountType); + } + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", editProperties" + ", accountType " + accountType; + } + } + .bind(); + } + + @Override + public void confirmCredentialsAsUser(IAccountManagerResponse response, Account account, Bundle options, boolean expectActivityLaunch, int userId) { + // Ignore + } + + @Override + public boolean accountAuthenticated(Account account, int userId) { + Objects.requireNonNull(account, "account cannot be null"); + BUserAccounts userAccounts = getUserAccounts(userId); + + if (userAccounts == null) { + return false; + } + return updateLastAuthenticatedTime(userAccounts, account); + } + + @Override + public void getAuthTokenLabel(IAccountManagerResponse response, String accountType, String authTokenType, int userId) { + Preconditions.checkArgument(accountType != null, "accountType cannot be null"); + Preconditions.checkArgument(authTokenType != null, "authTokenType cannot be null"); + + BUserAccounts accounts = getUserAccounts(userId); + new Session(accounts, response, accountType, false /* expectActivityLaunch */, + false /* stripAuthTokenFromResult */, null /* accountName */, + false /* authDetailsRequired */) { + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", getAuthTokenLabel" + ", " + accountType + ", authTokenType " + authTokenType; + } + + @Override + public void run() throws RemoteException { + mAuthenticator.getAuthTokenLabel(this, authTokenType); + } + + @Override + public void onResult(Bundle result) { + if (result != null) { + String label = result.getString(AccountManager.KEY_AUTH_TOKEN_LABEL); + + Bundle bundle = new Bundle(); + bundle.putString(AccountManager.KEY_AUTH_TOKEN_LABEL, label); + super.onResult(bundle); + } + super.onResult(null); + } + } + .bind(); + } + + @Override + public HashMap getPackagesAndVisibilityForAccount(Account account, int userId) { + return new HashMap<>(); + } + + protected void saveCachedToken(BUserAccounts accounts, Account account, String callerPkg, String tokenType, String token, long expiryMillis) { + if (account == null || tokenType == null || callerPkg == null) { + return; + } + + TokenCache cache = new TokenCache(accounts.userId, account, callerPkg, tokenType, token, expiryMillis); + synchronized (mTokenCaches) { + mTokenCaches.add(cache); + } + } + + protected void saveAuthTokenToDatabase(BUserAccounts accounts, Account account, String authTokenType, String authToken) { + if (accounts == null) { + return; + } + + synchronized (accounts.lock) { + accounts.getAuthToken(account).put(authTokenType, authToken); + saveAllAccounts(); + } + } + + protected String readCachedTokenInternal(BUserAccounts accounts, Account account, String tokenType, String callingPackage) { + long nowTime = System.currentTimeMillis(); + synchronized (mTokenCaches) { + Iterator iterator = mTokenCaches.iterator(); + while (iterator.hasNext()) { + TokenCache next = iterator.next(); + + if (next.userId == accounts.userId && next.account.equals(account) && next.authTokenType.equals(tokenType) && next.packageName.equals(callingPackage)) { + if (next.expiryEpochMillis > nowTime) { + return next.authToken; + } + iterator.remove(); + } + } + return null; + } + } + + protected String readAuthTokenInternal(BUserAccounts accounts, Account account, String authTokenType) { + if (accounts == null) { + return null; + } + // If not cached yet - do slow path and sync with db if necessary + synchronized (accounts.lock) { + Map authToken = accounts.getAuthToken(account); + return authToken.get(authTokenType); + } + } + + private void completeCloningAccount(IAccountManagerResponse response, final Bundle accountCredentials, final Account account, + final BUserAccounts targetUser, final int parentUserId) { + new Session(targetUser, response, account.type, false, + false /* stripAuthTokenFromResult */, account.name, + false /* authDetailsRequired */) { + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", getAccountCredentialsForClone" + ", " + account.type; + } + + @Override + public void run() throws RemoteException { + // Confirm that the owner's account still exists before this step. + for (Account acc : getAccounts(parentUserId, mContext.getPackageName())) { + if (acc.equals(account)) { + mAuthenticator.addAccountFromCredentials(this, account, accountCredentials); + break; + } + } + } + + @Override + public void onResult(Bundle result) { + // TODO: Anything to do if if succeded? + // TODO: If it failed: Show error notification? Should we remove the shadow account to avoid retries? + // TODO: What we do with the visibility? + super.onResult(result); + } + + @Override + public void onError(int errorCode, String errorMessage) { + super.onError(errorCode, errorMessage); + // TODO: Show error notification to user + // TODO: Should we remove the shadow account so that it doesn't keep trying? + } + } + .bind(); + } + + public Account[] getAccounts(int userId, String opPackageName) { + BUserAccounts userAccounts = getUserAccounts(userId); + return userAccounts.accounts.toArray(new Account[]{}); + } + + @Override + public boolean addAccountExplicitlyWithVisibility(Account account, String password, Bundle extras, Map packageToVisibility, int userId) { + /* + * Child users are not allowed to add accounts. Only the accounts that are shared by the + * parent profile can be added to child profile. + * + * TODO: Only allow accounts that were shared to be added by a limited user. + */ + // Fails if the account already exists. + BUserAccounts accounts = getUserAccounts(userId); + return addAccountInternal(accounts, account, password, extras, (Map) packageToVisibility); + } + + @Override + public boolean setAccountVisibility(Account account, String packageName, int newVisibility, int userId) { + Objects.requireNonNull(account, "account cannot be null"); + Objects.requireNonNull(packageName, "packageName cannot be null"); + + BUserAccounts userAccounts = getUserAccounts(userId); + if (userAccounts == null) { + return false; + } + return setAccountVisibility(account, packageName, newVisibility, userAccounts); + } + + @Override + public int getAccountVisibility(Account account, String packageName, int userId) { + Objects.requireNonNull(account, "account cannot be null"); + Objects.requireNonNull(packageName, "packageName cannot be null"); + + BUserAccounts accounts = getUserAccounts(userId); + if (AccountManager.PACKAGE_NAME_KEY_LEGACY_VISIBLE.equals(packageName)) { + int visibility = getAccountVisibilityFromCache(account, packageName, accounts); + + if (AccountManager.VISIBILITY_UNDEFINED != visibility) { + return visibility; + } else { + return AccountManager.VISIBILITY_USER_MANAGED_VISIBLE; + } + } + + if (AccountManager.PACKAGE_NAME_KEY_LEGACY_NOT_VISIBLE.equals(packageName)) { + int visibility = getAccountVisibilityFromCache(account, packageName, accounts); + if (AccountManager.VISIBILITY_UNDEFINED != visibility) { + return visibility; + } else { + return AccountManager.VISIBILITY_USER_MANAGED_NOT_VISIBLE; + } + } + return resolveAccountVisibility(account, packageName, accounts); + } + + @Override + public Map getAccountsAndVisibilityForPackage(String packageName, String accountType, int userId) { + Map hashMap = new HashMap<>(); + BUserAccounts userAccounts = getUserAccounts(userId); + + synchronized (userAccounts.lock) { + for (BAccount account : userAccounts.accounts) { + if (account.account.type.equals(accountType)) { + Integer integer = userAccounts.getVisibility(account.account).get(packageName); + if (integer != null) { + hashMap.put(account.account, integer); + } + } + } + } + return hashMap; + } + + @Override + public void registerAccountListener(String[] accountTypes, String opPackageName, int userId) throws RemoteException { } + + @Override + public void unregisterAccountListener(String[] accountTypes, String opPackageName, int userId) { } + + private boolean addAccountInternal(BUserAccounts accounts, Account account, String password, Bundle extras, Map packageToVisibility) { + if (accounts == null) { + accounts = new BUserAccounts(); + } + + synchronized (accounts.lock) { + BAccount bAccount = accounts.getAccount(account); + if (bAccount != null) { + Slog.d(TAG, "skipping since insertExtra failed for key " + account); + return false; + } + + bAccount = accounts.addAccount(account); + bAccount.password = password; + if (extras != null) { + for (String key : extras.keySet()) { + final String value = extras.getString(key); + bAccount.insertExtra(key, value); + } + } + + if (packageToVisibility != null) { + for (Map.Entry entry : packageToVisibility.entrySet()) { + setAccountVisibility(account, entry.getKey() /* package */, entry.getValue() /* visibility */, accounts); + } + } + } + + saveAllAccounts(); + return true; + } + + private boolean setAccountVisibility(Account account, String packageName, int newVisibility, BUserAccounts accounts) { + synchronized (accounts.lock) { + BAccount bAccount = accounts.getAccount(account); + if (bAccount == null) { + return false; + } + + bAccount.visibility.put(packageName, newVisibility); + return true; + } + } + + protected Account[] getAccountsFromCache(BUserAccounts userAccounts, String accountType, String callingPackage, boolean includeManagedNotVisible) { + if (accountType != null) { + Account[] accounts; + synchronized (userAccounts.lock) { + accounts = userAccounts.getAccountsByType(accountType); + } + + if (accounts == null) { + return EMPTY_ACCOUNT_ARRAY; + } + return filterAccounts(userAccounts, Arrays.copyOf(accounts, accounts.length), callingPackage, includeManagedNotVisible); + } else { + int totalLength = 0; + Account[] accountsArray; + + synchronized (mUserAccountsMap) { + for (BUserAccounts bUserAccounts : mUserAccountsMap.values()) { + totalLength += bUserAccounts.toAccounts().length; + } + + if (totalLength == 0) { + return EMPTY_ACCOUNT_ARRAY; + } + + accountsArray = new Account[totalLength]; + totalLength = 0; + for (BUserAccounts bUserAccounts : mUserAccountsMap.values()) { + Account[] accountsOfType = bUserAccounts.toAccounts(); + + System.arraycopy(accountsOfType, 0, accountsArray, totalLength, accountsOfType.length); + totalLength += accountsOfType.length; + } + } + return filterAccounts(userAccounts, accountsArray, callingPackage, includeManagedNotVisible); + } + } + + @NonNull + private Account[] filterAccounts(BUserAccounts accounts, Account[] unfiltered, String callingPackage, boolean includeManagedNotVisible) { + Map firstPass = new LinkedHashMap<>(); + for (Account account : unfiltered) { + int visibility = resolveAccountVisibility(account, callingPackage, accounts); + if ((visibility == AccountManager.VISIBILITY_VISIBLE || visibility == AccountManager.VISIBILITY_USER_MANAGED_VISIBLE) + || (includeManagedNotVisible && (visibility == AccountManager.VISIBILITY_USER_MANAGED_NOT_VISIBLE))) { + firstPass.put(account, visibility); + } + } + return firstPass.keySet().toArray(new Account[]{}); + } + + /** + * Method which handles default values for Account visibility. + * + * @param account The account to check visibility. + * @param packageName Package name to check visibility + * @param accounts UserAccount that currently hosts the account and application + * @return Visibility value, the method never returns AccountManager.VISIBILITY_UNDEFINED + */ + private Integer resolveAccountVisibility(Account account, @NonNull String packageName, BUserAccounts accounts) { + if (accounts == null) { + return AccountManager.VISIBILITY_NOT_VISIBLE; + } + + BAccount bAccount = accounts.getAccount(account); + if (bAccount == null) { + return AccountManager.VISIBILITY_NOT_VISIBLE; + } + + // Return stored value if it was set. + int visibility = getAccountVisibilityFromCache(account, packageName, accounts); + if (AccountManager.VISIBILITY_UNDEFINED != visibility) { + return visibility; + } + return AccountManager.VISIBILITY_NOT_VISIBLE; + } + + /** + * Method returns visibility for given account and package name. + * + * @param account The account to check visibility. + * @param packageName Package name to check visibility. + * @param accounts UserAccount that currently hosts the account and application + * @return Visibility value, AccountManager.VISIBILITY_UNDEFINED if no value was stored. + */ + private int getAccountVisibilityFromCache(Account account, String packageName, BUserAccounts accounts) { + synchronized (accounts.lock) { + Map accountVisibility = getPackagesAndVisibilityForAccountLocked(account, accounts); + Integer visibility = accountVisibility.get(packageName); + return visibility != null ? visibility : AccountManager.VISIBILITY_UNDEFINED; + } + } + + private @NonNull Map getPackagesAndVisibilityForAccountLocked(Account account, BUserAccounts accounts) { + return accounts.getVisibility(account); + } + + private void handleGetAccountsResult(IAccountManagerResponse response, Account[] accounts, String callingPackage, int userId) { + if (needToStartChooseAccountActivity(accounts, callingPackage, userId)) { + return; + } + + if (accounts.length == 1) { + Bundle bundle = new Bundle(); + bundle.putString(AccountManager.KEY_ACCOUNT_NAME, accounts[0].name); + bundle.putString(AccountManager.KEY_ACCOUNT_TYPE, accounts[0].type); + + onResult(response, bundle); + return; + } + onResult(response, new Bundle()); + } + + private boolean needToStartChooseAccountActivity(Account[] accounts, String callingPackage, int userId) { + if (accounts.length < 1) { + return false; + } + + if (accounts.length > 1) { + return true; + } + + Account account = accounts[0]; + BUserAccounts userAccounts = getUserAccounts(userId); + int visibility = resolveAccountVisibility(account, callingPackage, userAccounts); + return visibility == AccountManager.VISIBILITY_USER_MANAGED_NOT_VISIBLE; + } + + private String readUserDataInternal(BUserAccounts accounts, Account account, String key) { + if (accounts == null) { + return null; + } + + synchronized (accounts.lock) { + Map accountUserData = accounts.getAccountUserData(account); + return accountUserData.get(key); + } + } + + public String readPasswordInternal(BUserAccounts accounts, Account account) { + if (accounts == null) { + return null; + } + + synchronized (accounts.lock) { + BAccount bAccount = accounts.getAccount(account); + if (bAccount == null) { + return null; + } + return bAccount.password; + } + } + + public BUserAccounts getUserAccounts(int userId) { + synchronized (mUserAccountsMap) { + BUserAccounts bUserAccounts = mUserAccountsMap.get(userId); + if (bUserAccounts == null) { + bUserAccounts = new BUserAccounts(); + mUserAccountsMap.put(userId, bUserAccounts); + } + return mUserAccountsMap.get(userId); + } + } + + private boolean isAccountPresentForCaller(String accountName, String accountType, int userId) { + BUserAccounts userAccounts = getUserAccounts(userId); + if (userAccounts != null) { + BAccount account = userAccounts.getAccount(new Account(accountName, accountType)); + return account != null; + } + return false; + } + + private boolean removeAccountInternal(BUserAccounts accounts, Account account) { + synchronized (accounts.lock) { + boolean del = accounts.delAccount(account); + if (del) { + saveAllAccounts(); + } + return del; + } + } + + private class RemoveAccountSession extends Session { + final Account mAccount; + + public RemoveAccountSession(BUserAccounts accounts, IAccountManagerResponse response, Account account, boolean expectActivityLaunch) { + super(accounts, response, account.type, expectActivityLaunch, true /* stripAuthTokenFromResult */, account.name, + false /* authDetailsRequired */); + this.mAccount = account; + } + + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", removeAccount" + ", account " + mAccount; + } + + @Override + public void run() throws RemoteException { + mAuthenticator.getAccountRemovalAllowed(this, mAccount); + } + + @Override + public void onResult(Bundle result) { + if (result != null && result.containsKey(AccountManager.KEY_BOOLEAN_RESULT) && !result.containsKey(AccountManager.KEY_INTENT)) { + final boolean removalAllowed = result.getBoolean(AccountManager.KEY_BOOLEAN_RESULT); + if (removalAllowed) { + removeAccountInternal(mAccounts, mAccount); + } + + IAccountManagerResponse response = getResponseAndClose(); + if (response != null) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onResult() on response " + response); + } + + try { + response.onResult(result); + } catch (RemoteException e) { + Slog.e(TAG, "Error calling onResult()", e); + } + } + } + super.onResult(result); + } + } + + private class GetAccountsByTypeAndFeatureSession extends Session { + private final String[] mFeatures; + private volatile Account[] mAccountsOfType = null; + private volatile ArrayList mAccountsWithFeatures = null; + private volatile int mCurrentAccount = 0; + private final String mPackageName; + private final boolean mIncludeManagedNotVisible; + + public GetAccountsByTypeAndFeatureSession(BUserAccounts accounts, IAccountManagerResponse response, String type, String[] features, int userId, + String packageName, boolean includeManagedNotVisible) { + super(accounts, response, type, false /* expectActivityLaunch */, true /* stripAuthTokenFromResult */, + null /* accountName */, false /* authDetailsRequired */); + this.mFeatures = features; + this.mPackageName = packageName; + this.mIncludeManagedNotVisible = includeManagedNotVisible; + } + + @Override + public void run() throws RemoteException { + mAccountsOfType = getAccountsFromCache(mAccounts, mAccountType, mPackageName, mIncludeManagedNotVisible); + // Check whether each account matches the requested features. + mAccountsWithFeatures = new ArrayList<>(mAccountsOfType.length); + mCurrentAccount = 0; + checkAccount(); + } + + public void checkAccount() { + if (mCurrentAccount >= mAccountsOfType.length) { + sendResult(); + return; + } + + final IAccountAuthenticator accountAuthenticator = mAuthenticator; + if (accountAuthenticator == null) { + // It is possible that the authenticator has died, which is indicated by + // mAuthenticator being set to null. If this happens then just abort. + // There is no need to send back a result or error in this case since + // that already happened when mAuthenticator was cleared. + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "checkAccount: aborting session since we are no longer" + " connected to the authenticator, " + toDebugString()); + } + return; + } + + try { + accountAuthenticator.hasFeatures(this, mAccountsOfType[mCurrentAccount], mFeatures); + } catch (RemoteException e) { + onError(AccountManager.ERROR_CODE_REMOTE_EXCEPTION, "remote exception"); + } + } + + @Override + public void onResult(Bundle result) { + mNumResults++; + if (result == null) { + onError(AccountManager.ERROR_CODE_INVALID_RESPONSE, "null bundle"); + return; + } + + if (result.getBoolean(AccountManager.KEY_BOOLEAN_RESULT, false)) { + mAccountsWithFeatures.add(mAccountsOfType[mCurrentAccount]); + } + + mCurrentAccount++; + checkAccount(); + } + + public void sendResult() { + IAccountManagerResponse response = getResponseAndClose(); + if (response != null) { + try { + Account[] accounts = new Account[mAccountsWithFeatures.size()]; + for (int i = 0; i < accounts.length; i++) { + accounts[i] = mAccountsWithFeatures.get(i); + } + + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onResult() on response " + response); + } + + Bundle result = new Bundle(); + result.putParcelableArray(AccountManager.KEY_ACCOUNTS, accounts); + response.onResult(result); + } catch (RemoteException e) { + // If the caller is dead then there is no one to care about remote exceptions. + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "failure while notifying response", e); + } + } + } + } + + @Override + protected String toDebugString(long now) { + return super.toDebugString(now) + ", getAccountsByTypeAndFeatures" + ", " + (mFeatures != null ? TextUtils.join(",", mFeatures) : null); + } + } + + private static final class AuthenticatorInfo { + final AuthenticatorDescription desc; + final ServiceInfo serviceInfo; + + AuthenticatorInfo(AuthenticatorDescription desc, ServiceInfo info) { + this.desc = desc; + this.serviceInfo = info; + } + } + + private static final class AuthenticatorCache { + final Map authenticators = new HashMap<>(); + } + + private static AuthenticatorDescription parseAuthenticatorDescription(Resources resources, String packageName, AttributeSet attributeSet) { + TypedArray array = resources.obtainAttributes(attributeSet, ArrayUtils.toInt(black.com.android.internal.R.styleable.AccountAuthenticator.get())); + try { + String accountType = array.getString(black.com.android.internal.R.styleable.AccountAuthenticator_accountType.get()); + int label = array.getResourceId(black.com.android.internal.R.styleable.AccountAuthenticator_label.get(), 0); + int icon = array.getResourceId(black.com.android.internal.R.styleable.AccountAuthenticator_icon.get(), 0); + int smallIcon = array.getResourceId(black.com.android.internal.R.styleable.AccountAuthenticator_smallIcon.get(), 0); + int accountPreferences = array.getResourceId(black.com.android.internal.R.styleable.AccountAuthenticator_accountPreferences.get(), 0); + boolean customTokens = array.getBoolean(black.com.android.internal.R.styleable.AccountAuthenticator_customTokens.get(), false); + + if (TextUtils.isEmpty(accountType)) { + return null; + } + return new AuthenticatorDescription(accountType, packageName, label, icon, smallIcon, accountPreferences, customTokens); + } finally { + array.recycle(); + } + } + + public void loadAuthenticatorCache(String packageName) { + mAuthenticatorCache.authenticators.clear(); + Intent intent = new Intent(AccountManager.ACTION_AUTHENTICATOR_INTENT); + if (packageName != null) { + intent.setPackage(packageName); + } + + generateServicesMap(mPms.queryIntentServices(intent, PackageManager.GET_META_DATA, BUserHandle.USER_ALL), mAuthenticatorCache.authenticators, + new RegisteredServicesParser()); + } + + private void generateServicesMap(List services, Map map, RegisteredServicesParser accountParser) { + for (ResolveInfo info : services) { + XmlResourceParser parser = accountParser.getParser(mContext, info.serviceInfo, AccountManager.AUTHENTICATOR_META_DATA_NAME); + if (parser != null) { + try { + AttributeSet attributeSet = Xml.asAttributeSet(parser); + if (AccountManager.AUTHENTICATOR_ATTRIBUTES_NAME.equals(parser.getName())) { + AuthenticatorDescription desc = parseAuthenticatorDescription(accountParser.getResources(mContext, info.serviceInfo.applicationInfo), + info.serviceInfo.packageName, attributeSet); + if (desc != null) { + map.put(desc.type, new AuthenticatorInfo(desc, info.serviceInfo)); + } + } + } catch (Exception e) { + e.printStackTrace(); + } + } + } + } + + private abstract class Session extends IAccountAuthenticatorResponse.Stub implements IBinder.DeathRecipient, ServiceConnection { + IAccountManagerResponse mResponse; + final String mAccountType; + final boolean mExpectActivityLaunch; + final long mCreationTime; + final String mAccountName; + // Indicates if we need to add auth details (like last credential time) + final boolean mAuthDetailsRequired; + // If set, we need to update the last authenticated time. This is currently used on + // successful confirming credentials. + final boolean mUpdateLastAuthenticatedTime; + + public int mNumResults = 0; + private int mNumRequestContinued = 0; + private int mNumErrors = 0; + + IAccountAuthenticator mAuthenticator = null; + + private final boolean mStripAuthTokenFromResult; + protected final BUserAccounts mAccounts; + + public Session(BUserAccounts accounts, IAccountManagerResponse response, String accountType, boolean expectActivityLaunch, + boolean stripAuthTokenFromResult, String accountName, boolean authDetailsRequired) { + this(accounts, response, accountType, expectActivityLaunch, stripAuthTokenFromResult, accountName, + authDetailsRequired, false /* updateLastAuthenticatedTime */); + } + + public Session(BUserAccounts accounts, IAccountManagerResponse response, String accountType, boolean expectActivityLaunch, + boolean stripAuthTokenFromResult, String accountName, boolean authDetailsRequired, boolean updateLastAuthenticatedTime) { + super(); + if (accountType == null) { + throw new IllegalArgumentException("accountType is null"); + } + + mAccounts = accounts; + mStripAuthTokenFromResult = stripAuthTokenFromResult; + mResponse = response; + mAccountType = accountType; + mExpectActivityLaunch = expectActivityLaunch; + mCreationTime = SystemClock.elapsedRealtime(); + mAccountName = accountName; + mAuthDetailsRequired = authDetailsRequired; + mUpdateLastAuthenticatedTime = updateLastAuthenticatedTime; + + synchronized (mSessions) { + mSessions.put(toString(), this); + } + + if (response != null) { + try { + response.asBinder().linkToDeath(this, 0 /* flags */); + } catch (RemoteException e) { + mResponse = null; + binderDied(); + } + } + } + + IAccountManagerResponse getResponseAndClose() { + if (mResponse == null) { + // This session has already been closed. + return null; + } + IAccountManagerResponse response = mResponse; + close(); // This clears mResponse so we need to save the response before this call. + return response; + } + + /** + * Checks Intents, supplied via KEY_INTENT, to make sure that they don't violate our + * security policy. + *

+ * In particular we want to make sure that the Authenticator doesn't try to trick users + * into launching arbitrary intents on the device via by tricking to click authenticator + * supplied entries in the system Settings app. + */ + protected boolean checkKeyIntent(int authUid, Intent intent) { + // Explicitly set an empty ClipData to ensure that we don't offer to + // promote any Uris contained inside for granting purposes + if (intent.getClipData() == null) { + intent.setClipData(ClipData.newPlainText(null, null)); + } + intent.setFlags(intent.getFlags() & ~(Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION + | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION | Intent.FLAG_GRANT_PREFIX_URI_PERMISSION)); + long bid = Binder.clearCallingIdentity(); + try { + ResolveInfo resolveInfo = mPms.resolveActivity(intent, 0, null, mAccounts.userId); + return resolveInfo != null; + } finally { + Binder.restoreCallingIdentity(bid); + } + } + + private void close() { + synchronized (mSessions) { + if (mSessions.remove(toString()) == null) { + // The session was already closed, so bail out now. + return; + } + } + if (mResponse != null) { + // Stop listening for response deaths. + mResponse.asBinder().unlinkToDeath(this, 0 /* flags */); + + // Clear this so that we don't accidentally send any further results. + mResponse = null; + } + cancelTimeout(); + unbind(); + } + + @Override + public void binderDied() { + mResponse = null; + close(); + } + + protected String toDebugString() { + return toDebugString(SystemClock.elapsedRealtime()); + } + + protected String toDebugString(long now) { + return "Session: expectLaunch " + mExpectActivityLaunch + ", connected " + (mAuthenticator != null) + + ", stats (" + mNumResults + "/" + mNumRequestContinued + "/" + mNumErrors + ")" + ", lifetime " + ((now - mCreationTime) / 1000.0); + } + + void bind() { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "initiating bind to authenticator type " + mAccountType); + } + + if (!bindToAuthenticator(mAccountType)) { + Log.d(TAG, "bind attempt failed for " + toDebugString()); + onError(AccountManager.ERROR_CODE_REMOTE_EXCEPTION, "bind failure"); + } + } + + private void unbind() { + if (mAuthenticator != null) { + mAuthenticator = null; + mContext.unbindService(this); + } + } + + public void cancelTimeout() { + mHandler.removeMessages(MESSAGE_TIMED_OUT, this); + } + + @Override + public void onServiceConnected(ComponentName name, IBinder service) { + mAuthenticator = IAccountAuthenticator.Stub.asInterface(service); + try { + run(); + } catch (RemoteException e) { + onError(AccountManager.ERROR_CODE_REMOTE_EXCEPTION, "remote exception"); + } + } + + @Override + public void onServiceDisconnected(ComponentName name) { + mAuthenticator = null; + IAccountManagerResponse response = getResponseAndClose(); + + if (response != null) { + try { + response.onError(AccountManager.ERROR_CODE_REMOTE_EXCEPTION, "disconnected"); + } catch (RemoteException e) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "Session.onServiceDisconnected: " + "caught RemoteException while responding", e); + } + } + } + } + + public abstract void run() throws RemoteException; + + @Override + public void onResult(Bundle result) { + mNumResults++; + Intent intent = null; + + if (result != null) { + boolean isSuccessfulConfirmCreds = result.getBoolean(AccountManager.KEY_BOOLEAN_RESULT, false); + boolean isSuccessfulUpdateCredsOrAddAccount = result.containsKey(AccountManager.KEY_ACCOUNT_NAME) + && result.containsKey(AccountManager.KEY_ACCOUNT_TYPE); + // We should only update lastAuthenticated time, if + // mUpdateLastAuthenticatedTime is true and the confirmRequest + // or updateRequest was successful. + boolean needUpdate = mUpdateLastAuthenticatedTime && (isSuccessfulConfirmCreds || isSuccessfulUpdateCredsOrAddAccount); + if (needUpdate || mAuthDetailsRequired) { + boolean accountPresent = isAccountPresentForCaller(mAccountName, mAccountType, mAccounts.userId); + if (needUpdate && accountPresent) { + updateLastAuthenticatedTime(mAccounts, new Account(mAccountName, mAccountType)); + } + + if (mAuthDetailsRequired) { + long lastAuthenticatedTime = -1; + if (accountPresent) { + lastAuthenticatedTime = mAccounts.findAccountLastAuthenticatedTime(new Account(mAccountName, mAccountType)); + } + + result.putLong(AccountManager.KEY_LAST_AUTHENTICATED_TIME, lastAuthenticatedTime); + } + } + } + + if (result != null && (intent = result.getParcelable(AccountManager.KEY_INTENT)) != null) { + if (!checkKeyIntent(Binder.getCallingUid(), intent)) { + onError(AccountManager.ERROR_CODE_INVALID_RESPONSE, "invalid intent in bundle returned"); + return; + } + } + + IAccountManagerResponse response; + if (mExpectActivityLaunch && result != null && result.containsKey(AccountManager.KEY_INTENT)) { + response = mResponse; + } else { + response = getResponseAndClose(); + } + + if (response != null) { + try { + if (result == null) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onError() on response " + response); + } + + response.onError(AccountManager.ERROR_CODE_INVALID_RESPONSE, "null bundle returned"); + } else { + if (mStripAuthTokenFromResult) { + result.remove(AccountManager.KEY_AUTHTOKEN); + } + + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onResult() on response " + response); + } + + if ((result.getInt(AccountManager.KEY_ERROR_CODE, -1) > 0) && (intent == null)) { + // All AccountManager error codes are greater than 0. + response.onError(result.getInt(AccountManager.KEY_ERROR_CODE), result.getString(AccountManager.KEY_ERROR_MESSAGE)); + } else { + response.onResult(result); + } + } + } catch (RemoteException e) { + // If the caller is dead then there is no one to care about remote exceptions. + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "failure while notifying response", e); + } + } + } + } + + @Override + public void onRequestContinued() { + mNumRequestContinued++; + } + + @Override + public void onError(int errorCode, String errorMessage) { + mNumErrors++; + IAccountManagerResponse response = getResponseAndClose(); + + if (response != null) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onError() on response " + response); + } + + try { + response.onError(errorCode, errorMessage); + } catch (RemoteException e) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "Session.onError: caught RemoteException while responding", e); + } + } + } else { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "Session.onError: already closed"); + } + } + } + + /** + * find the component name for the authenticator and initiate a bind + * if no authenticator or the bind fails then return false, otherwise return true + */ + private boolean bindToAuthenticator(String authenticatorType) { + AuthenticatorInfo authenticatorInfo = mAuthenticatorCache.authenticators.get(authenticatorType); + if (authenticatorInfo == null) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "there is no authenticator for " + authenticatorType + ", bailing out"); + } + return false; + } + + Intent intent = new Intent(); + intent.setAction(AccountManager.ACTION_AUTHENTICATOR_INTENT); + + ComponentName componentName = new ComponentName(authenticatorInfo.serviceInfo.packageName, authenticatorInfo.serviceInfo.name); + intent.setComponent(componentName); + intent.putExtra("_B_|_UserId", mAccounts.userId); + + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "performing bindService to " + componentName); + } + + int flags = Context.BIND_AUTO_CREATE; + if (!mContext.bindService(intent, this, flags)) { + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "bindService to " + componentName + " failed"); + } + return false; + } + return true; + } + } + + private void onResult(IAccountManagerResponse response, Bundle result) { + if (result == null) { + Log.e(TAG, "the result is unexpectedly null", new Exception()); + } + + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, getClass().getSimpleName() + " calling onResult() on response " + response); + } + + try { + response.onResult(result); + } catch (RemoteException e) { + // If the caller is dead then there is no one to care about remote exceptions. + if (Log.isLoggable(TAG, Log.VERBOSE)) { + Log.v(TAG, "failure while notifying response", e); + } + } + } + + private boolean updateLastAuthenticatedTime(BUserAccounts userAccounts, Account account) { + userAccounts.updateLastAuthenticatedTime(account); + return true; + } + + private String getCallingPackageName() { + int callingPid = Binder.getCallingPid(); + ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); + + if (processByPid == null) { + throw new IllegalArgumentException("ProcessRecord is null, PID: " + callingPid); + } + return processByPid.getPackageName(); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/accounts/BUserAccounts.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BUserAccounts.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/accounts/BUserAccounts.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BUserAccounts.java index efaf3cd..f6a76e9 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/accounts/BUserAccounts.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/BUserAccounts.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.accounts; +package com.vcore.core.system.accounts; import android.accounts.Account; import android.os.Parcel; @@ -9,9 +9,6 @@ import java.util.List; import java.util.Map; -/** - * Created by BlackBox on 2022/3/3. - */ public class BUserAccounts implements Parcelable { public final Object lock = new Object(); @@ -35,8 +32,9 @@ public BAccount addAccount(Account account) { public BAccount getAccount(Account account) { for (BAccount bAccount : accounts) { - if (bAccount.isMatch(account)) + if (bAccount.isMatch(account)) { return bAccount; + } } return null; } @@ -46,25 +44,27 @@ public boolean delAccount(Account account) { return accounts.remove(bAccount); } - public Map getVisibility(Account account) { BAccount bAccount = getAccount(account); - if (bAccount == null) + if (bAccount == null) { return new HashMap<>(); + } return bAccount.visibility; } public Map getAccountUserData(Account account) { BAccount bAccount = getAccount(account); - if (bAccount == null) + if (bAccount == null) { return new HashMap<>(); + } return bAccount.accountUserData; } public Map getAuthToken(Account account) { BAccount bAccount = getAccount(account); - if (bAccount == null) + if (bAccount == null) { return new HashMap<>(); + } return bAccount.authTokens; } @@ -93,7 +93,6 @@ public long findAccountLastAuthenticatedTime(Account account) { return -1; } - @Override public int describeContents() { return 0; @@ -105,28 +104,10 @@ public void writeToParcel(Parcel dest, int flags) { dest.writeTypedList(this.accounts); } - public void readFromParcel(Parcel source) { - this.userId = source.readInt(); - this.accounts = source.createTypedArrayList(BAccount.CREATOR); - } - - public BUserAccounts() { - } + public BUserAccounts() { } protected BUserAccounts(Parcel in) { this.userId = in.readInt(); this.accounts = in.createTypedArrayList(BAccount.CREATOR); } - - public static final Creator CREATOR = new Creator() { - @Override - public BUserAccounts createFromParcel(Parcel source) { - return new BUserAccounts(source); - } - - @Override - public BUserAccounts[] newArray(int size) { - return new BUserAccounts[size]; - } - }; } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/RegisteredServicesParser.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/RegisteredServicesParser.java new file mode 100644 index 0000000..6197bc0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/RegisteredServicesParser.java @@ -0,0 +1,35 @@ +package com.vcore.core.system.accounts; + +import android.content.Context; +import android.content.pm.ApplicationInfo; +import android.content.pm.ServiceInfo; +import android.content.res.Resources; +import android.content.res.XmlResourceParser; +import android.os.Bundle; + +import com.vcore.core.system.pm.PackageManagerCompat; + +public class RegisteredServicesParser { + public XmlResourceParser getParser(Context context, ServiceInfo serviceInfo, String name) { + Bundle meta = serviceInfo.metaData; + if (meta != null) { + int xmlId = meta.getInt(name); + if (xmlId != 0) { + try { + Resources resources = getResources(context, serviceInfo.applicationInfo); + if (resources == null) { + return null; + } + return resources.getXml(xmlId); + } catch (Exception e) { + e.printStackTrace(); + } + } + } + return null; + } + + public Resources getResources(Context context, ApplicationInfo appInfo) { + return PackageManagerCompat.getResources(context, appInfo); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/TokenCache.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/TokenCache.java new file mode 100644 index 0000000..6a2d538 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/accounts/TokenCache.java @@ -0,0 +1,42 @@ +package com.vcore.core.system.accounts; + +import android.accounts.Account; + +import java.util.Objects; + +public class TokenCache { + public final int userId; + public final Account account; + public final long expiryEpochMillis; + public final String authToken; + public final String authTokenType; + public final String packageName; + + public TokenCache(int userId, Account account, String callerPkg, String tokenType, String token, long expiryMillis) { + this.userId = userId; + this.account = account; + this.expiryEpochMillis = expiryMillis; + this.authToken = token; + this.authTokenType = tokenType; + this.packageName = callerPkg; + } + + @Override + public boolean equals(Object o) { + if (o == this) { + return true; + } + + if (!(o instanceof TokenCache)) { + return false; + } + TokenCache that = (TokenCache) o; + return userId == that.userId && expiryEpochMillis == that.expiryEpochMillis && Objects.equals(account, that.account) && + Objects.equals(authToken, that.authToken) && Objects.equals(authTokenType, that.authTokenType) && Objects.equals(packageName, that.packageName); + } + + @Override + public int hashCode() { + return Objects.hash(userId, account, expiryEpochMillis, authToken, authTokenType, packageName); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/ActiveServices.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActiveServices.java similarity index 76% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/ActiveServices.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActiveServices.java index 3d41fa3..dd5ef0f 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/ActiveServices.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActiveServices.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.am; +package com.vcore.core.system.am; import android.annotation.SuppressLint; import android.app.ActivityManager; @@ -18,98 +18,89 @@ import java.util.UUID; import java.util.concurrent.atomic.AtomicInteger; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.IEmpty; -import top.niunaijun.blackbox.core.system.BProcessManagerService; -import top.niunaijun.blackbox.core.system.ProcessRecord; -import top.niunaijun.blackbox.core.system.pm.BPackageManagerService; -import top.niunaijun.blackbox.entity.UnbindRecord; -import top.niunaijun.blackbox.entity.am.RunningServiceInfo; -import top.niunaijun.blackbox.proxy.ProxyManifest; -import top.niunaijun.blackbox.proxy.record.ProxyServiceRecord; - -/** - * Created by Milk on 4/7/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.BlackBoxCore; +import com.vcore.core.IEmpty; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.entity.UnbindRecord; +import com.vcore.entity.am.RunningServiceInfo; +import com.vcore.proxy.ProxyManifest; +import com.vcore.proxy.record.ProxyServiceRecord; + @SuppressLint("NewApi") public class ActiveServices { public static final String TAG = "ActiveServices"; - private final Map mRunningServiceRecords = new HashMap<>(); private final Map mRunningTokens = new HashMap<>(); private final Map mConnectedServices = new HashMap<>(); - public void startService(Intent intent, String resolvedType, boolean requireForeground, int userId) { + public void startService(Intent intent, String resolvedType, int userId) { ResolveInfo resolveInfo = resolveService(intent, resolvedType, userId); - if (resolveInfo == null) + if (resolveInfo == null) { return; -// throw new RuntimeException("resolveService service exception"); + } + ServiceInfo serviceInfo = resolveInfo.serviceInfo; ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(serviceInfo.packageName, serviceInfo.processName, userId, -1, Binder.getCallingPid()); if (processRecord == null) { throw new RuntimeException("Unable to create " + serviceInfo.name); } + RunningServiceRecord runningServiceRecord = getOrCreateRunningServiceRecord(intent); runningServiceRecord.mServiceInfo = serviceInfo; - runningServiceRecord.getAndIncrementStartId(); + final Intent stubServiceIntent = createStubServiceIntent(intent, serviceInfo, processRecord, runningServiceRecord); - new Thread(new Runnable() { - @Override - public void run() { - try { - BlackBoxCore.getContext().startService(stubServiceIntent); - } catch (Throwable e) { - e.printStackTrace(); - } + new Thread(() -> { + try { + BlackBoxCore.getContext().startService(stubServiceIntent); + } catch (Throwable e) { + e.printStackTrace(); } }).start(); } public int stopService(Intent intent, String resolvedType, int userId) { -// ResolveInfo resolveInfo = resolveService(intent, resolvedType, userId); synchronized (mRunningServiceRecords) { RunningServiceRecord runningServiceRecord = findRunningServiceRecord(intent); if (runningServiceRecord == null) { return 0; } + if (runningServiceRecord.mBindCount.get() > 0) { Log.d(TAG, "There are also connections"); return 0; } + runningServiceRecord.mStartId.set(0); ResolveInfo resolveInfo = resolveService(intent, resolvedType, userId); - if (resolveInfo == null) + if (resolveInfo == null) { return 0; + } + ServiceInfo serviceInfo = resolveInfo.serviceInfo; ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(serviceInfo.packageName, serviceInfo.processName, userId, -1, Binder.getCallingPid()); if (processRecord == null) { return 0; } + try { processRecord.bActivityThread.stopService(intent); - } catch (RemoteException ignored) { - } + } catch (RemoteException ignored) { } } return 0; } public Intent bindService(Intent intent, final IBinder binder, String resolvedType, int userId) { ResolveInfo resolveInfo = resolveService(intent, resolvedType, userId); - if (resolveInfo == null) + if (resolveInfo == null) { return intent; - ServiceInfo serviceInfo = resolveInfo.serviceInfo; - ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked( - serviceInfo.packageName, - serviceInfo.processName, - userId, - -1, Binder.getCallingPid()); + } + ServiceInfo serviceInfo = resolveInfo.serviceInfo; + ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(serviceInfo.packageName, serviceInfo.processName, + userId, -1, Binder.getCallingPid()); if (processRecord == null) { throw new RuntimeException("Unable to create " + serviceInfo.name); } @@ -137,7 +128,7 @@ public void binderDied() { } catch (RemoteException e) { e.printStackTrace(); } - connectedService.mIBinder = binder; + connectedService.mIntent = intent; mConnectedServices.put(binder, connectedService); } @@ -145,55 +136,57 @@ public void binderDied() { if (!isBound) { runningServiceRecord.incrementBindCountAndGet(); } - runningServiceRecord.mConnectedServiceRecord = connectedService; } } return createStubServiceIntent(intent, serviceInfo, processRecord, runningServiceRecord); } - public void unbindService(IBinder binder, int userId) { + public void unbindService(IBinder binder) { ConnectedServiceRecord connectedService = mConnectedServices.get(binder); if (connectedService == null) { return; } + RunningServiceRecord runningServiceRecord = getOrCreateRunningServiceRecord(connectedService.mIntent); - runningServiceRecord.mConnectedServiceRecord = null; runningServiceRecord.mBindCount.decrementAndGet(); mConnectedServices.remove(binder); } - public void stopServiceToken(ComponentName className, IBinder token, int userId) { + public void stopServiceToken(IBinder token, int userId) { RunningServiceRecord runningServiceByToken = findRunningServiceByToken(token); if (runningServiceByToken != null) { stopService(runningServiceByToken.mIntent, null, userId); } } - public void onStartCommand(Intent proxyIntent, int userId) { - } - - public void onServiceDestroy(Intent proxyIntent, int userId) { - if (proxyIntent == null) + public void onServiceDestroy(Intent proxyIntent) { + if (proxyIntent == null) { return; + } + ProxyServiceRecord proxyServiceRecord = ProxyServiceRecord.create(proxyIntent); if (proxyServiceRecord.mServiceIntent != null) { proxyIntent = proxyServiceRecord.mServiceIntent; } + RunningServiceRecord remove = mRunningServiceRecords.remove(new Intent.FilterComparison(proxyIntent)); if (remove != null) { mRunningTokens.remove(remove); } } - public UnbindRecord onServiceUnbind(Intent proxyIntent, int userId) throws RemoteException { - if (proxyIntent == null) + public UnbindRecord onServiceUnbind(Intent proxyIntent) { + if (proxyIntent == null) { return null; + } + ProxyServiceRecord proxyServiceRecord = ProxyServiceRecord.create(proxyIntent); ComponentName component = proxyServiceRecord.mServiceIntent.getComponent(); - RunningServiceRecord runningServiceRecord = findRunningServiceRecord(proxyServiceRecord.mServiceIntent); - if (runningServiceRecord == null) + if (runningServiceRecord == null) { return null; + } + UnbindRecord record = new UnbindRecord(); record.setComponentName(component); record.setBindCount(runningServiceRecord.mBindCount.get()); @@ -203,7 +196,7 @@ public UnbindRecord onServiceUnbind(Intent proxyIntent, int userId) throws Remot private Intent createStubServiceIntent(Intent targetIntent, ServiceInfo serviceInfo, ProcessRecord processRecord, RunningServiceRecord runningServiceRecord) { Intent stub = new Intent(); - ComponentName stubComp = new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyService(processRecord.bpid)); + ComponentName stubComp = new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyService(processRecord.bPID)); stub.setComponent(stubComp); stub.setAction(UUID.randomUUID().toString()); ProxyServiceRecord.saveStub(stub, targetIntent, serviceInfo, runningServiceRecord, processRecord.userId, runningServiceRecord.mStartId.get()); @@ -230,8 +223,7 @@ private RunningServiceRecord findRunningServiceByToken(IBinder token) { } public RunningServiceInfo getRunningServiceInfo(String callerPackage, int userId) { - ActivityManager manager = (ActivityManager) - BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); + ActivityManager manager = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); List runningServices = manager.getRunningServices(Integer.MAX_VALUE); Map serviceInfoMap = new HashMap<>(); for (ActivityManager.RunningServiceInfo runningService : runningServices) { @@ -242,8 +234,10 @@ public RunningServiceInfo getRunningServiceInfo(String callerPackage, int userId for (RunningServiceRecord value : mRunningServiceRecords.values()) { ServiceInfo serviceInfo = value.mServiceInfo; ProcessRecord processRecord = BProcessManagerService.get().findProcessRecord(callerPackage, serviceInfo.processName, userId); - if (processRecord == null) + if (processRecord == null) { continue; + } + ActivityManager.RunningServiceInfo runningServiceInfo = serviceInfoMap.get(processRecord.pid); if (runningServiceInfo != null) { runningServiceInfo.process = processRecord.processName; @@ -256,12 +250,16 @@ public RunningServiceInfo getRunningServiceInfo(String callerPackage, int userId public IBinder peekService(Intent intent, String resolvedType, int userId) { ResolveInfo resolveInfo = resolveService(intent, resolvedType, userId); - if (resolveInfo == null) + if (resolveInfo == null) { return null; - ProcessRecord processRecord = - BProcessManagerService.get().findProcessRecord(resolveInfo.serviceInfo.packageName, resolveInfo.serviceInfo.processName, userId); - if (processRecord == null) + } + + ProcessRecord processRecord = BProcessManagerService.get().findProcessRecord(resolveInfo.serviceInfo.packageName, resolveInfo.serviceInfo.processName, + userId); + if (processRecord == null) { return null; + } + try { return processRecord.bActivityThread.peekService(intent); } catch (RemoteException e) { @@ -275,30 +273,22 @@ private ResolveInfo resolveService(Intent intent, String resolvedType, int userI } public static class RunningServiceRecord extends IEmpty.Stub { - // onStartCommand startId private final AtomicInteger mStartId = new AtomicInteger(1); private final AtomicInteger mBindCount = new AtomicInteger(0); - // 正在连接的服务 - private ConnectedServiceRecord mConnectedServiceRecord; private ServiceInfo mServiceInfo; private Intent mIntent; - public int getAndIncrementStartId() { - return mStartId.getAndIncrement(); - } - - public int decrementBindCountAndGet() { - return mBindCount.decrementAndGet(); + public void getAndIncrementStartId() { + mStartId.getAndIncrement(); } - public int incrementBindCountAndGet() { - return mBindCount.incrementAndGet(); + public void incrementBindCountAndGet() { + mBindCount.incrementAndGet(); } } public static class ConnectedServiceRecord { - private IBinder mIBinder; private Intent mIntent; } } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityRecord.kt b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityRecord.kt new file mode 100644 index 0000000..cc6ae15 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityRecord.kt @@ -0,0 +1,46 @@ +package com.vcore.core.system.am + +import android.content.ComponentName +import android.content.Intent +import android.content.pm.ActivityInfo +import android.os.Binder +import android.os.IBinder +import com.vcore.core.system.ProcessRecord +import java.util.UUID + +class ActivityRecord : Binder() { + @JvmField + var task: TaskRecord? = null + @JvmField + var token: IBinder? = null + @JvmField + var resultTo: IBinder? = null + @JvmField + var info: ActivityInfo? = null + @JvmField + var component: ComponentName? = null + @JvmField + var intent: Intent? = null + @JvmField + var userId = 0 + @JvmField + var finished = false + @JvmField + var processRecord: ProcessRecord? = null + @JvmField + var mBToken: String? = null + + companion object { + @JvmStatic + fun create(intent: Intent?, info: ActivityInfo, resultTo: IBinder?, userId: Int): ActivityRecord { + val record = ActivityRecord() + record.intent = intent + record.info = info + record.component = ComponentName(info.packageName, info.name) + record.resultTo = resultTo + record.userId = userId + record.mBToken = UUID.randomUUID().toString() + return record + } + } +} \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityStack.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityStack.java new file mode 100644 index 0000000..87a49c8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/ActivityStack.java @@ -0,0 +1,520 @@ +package com.vcore.core.system.am; + +import static android.content.pm.PackageManager.GET_ACTIVITIES; + +import android.app.ActivityManager; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ResolveInfo; +import android.content.res.Resources; +import android.content.res.TypedArray; +import android.os.Binder; +import android.os.Bundle; +import android.os.Handler; +import android.os.IBinder; +import android.os.IInterface; +import android.os.Looper; +import android.os.Message; +import android.os.RemoteException; + +import java.util.HashMap; +import java.util.LinkedHashMap; +import java.util.List; +import java.util.Map; +import java.util.Objects; +import java.util.UUID; + +import black.android.app.ActivityManagerNative; +import black.android.app.IActivityManager; + +import com.vcore.BlackBoxCore; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.PackageManagerCompat; +import com.vcore.proxy.ProxyActivity; +import com.vcore.proxy.ProxyManifest; +import com.vcore.proxy.record.ProxyActivityRecord; +import com.vcore.utils.ArrayUtils; +import com.vcore.utils.ComponentUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.ActivityManagerCompat; + +public class ActivityStack { + public static final String TAG = "ActivityStack"; + + private final ActivityManager mAms; + private final Map mTasks = new LinkedHashMap<>(); + private final Map mLaunchingActivities = new HashMap<>(); + + public static final int LAUNCH_TIME_OUT = 0; + + private final Handler mHandler = new Handler(Looper.getMainLooper()) { + @Override + public void handleMessage(Message msg) { + if (msg.what == LAUNCH_TIME_OUT) { + String token = (String) msg.obj; + if (token != null) { + mLaunchingActivities.remove(token); + } + } + } + }; + + public ActivityStack() { + this.mAms = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); + } + + public boolean containsFlag(Intent intent, int flag) { + return (intent.getFlags() & flag) != 0; + } + + public int startActivitiesLocked(int userId, Intent[] intents, String[] resolvedTypes, IBinder resultTo, Bundle options) { + if (intents == null) { + throw new NullPointerException("intents is null"); + } + + if (resolvedTypes == null) { + throw new NullPointerException("resolvedTypes is null"); + } + + if (intents.length != resolvedTypes.length) { + throw new IllegalArgumentException("intents are length different than resolvedTypes"); + } + + for (int i = 0; i < intents.length; i++) { + startActivityLocked(userId, intents[i], resolvedTypes[i], resultTo, null, -1, 0, options); + } + return 0; + } + + public int startActivityLocked(int userId, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options) { + synchronized (mTasks) { + synchronizeTasks(); + } + + ResolveInfo resolveInfo = BPackageManagerService.get().resolveActivity(intent, GET_ACTIVITIES, resolvedType, userId); + if (resolveInfo == null || resolveInfo.activityInfo == null) { + return 0; + } + + Slog.d(TAG, "startActivityLocked : " + resolveInfo.activityInfo); + ActivityInfo activityInfo = resolveInfo.activityInfo; + + ActivityRecord sourceRecord = findActivityRecordByToken(userId, resultTo); + if (sourceRecord == null) { + resultTo = null; + } + + TaskRecord sourceTask = null; + if (sourceRecord != null) { + sourceTask = sourceRecord.task; + } + + String taskAffinity = ComponentUtils.getTaskAffinity(activityInfo); + + int launchModeFlags = 0; + boolean singleTop = containsFlag(intent, Intent.FLAG_ACTIVITY_SINGLE_TOP) || activityInfo.launchMode == ActivityInfo.LAUNCH_SINGLE_TOP; + boolean newTask = containsFlag(intent, Intent.FLAG_ACTIVITY_NEW_TASK); + boolean clearTop = containsFlag(intent, Intent.FLAG_ACTIVITY_CLEAR_TOP); + boolean clearTask = containsFlag(intent, Intent.FLAG_ACTIVITY_CLEAR_TASK); + + TaskRecord taskRecord = null; + switch (activityInfo.launchMode) { + case ActivityInfo.LAUNCH_SINGLE_TOP: + case ActivityInfo.LAUNCH_MULTIPLE: + case ActivityInfo.LAUNCH_SINGLE_TASK: + taskRecord = findTaskRecordByTaskAffinityLocked(userId, taskAffinity); + if (taskRecord == null && !newTask) { + taskRecord = sourceTask; + } + break; + case ActivityInfo.LAUNCH_SINGLE_INSTANCE: + taskRecord = findTaskRecordByTaskAffinityLocked(userId, taskAffinity); + break; + } + + // 如果还没有task则新启动一个task + if (taskRecord == null || taskRecord.needNewTask()) { + return startActivityInNewTaskLocked(userId, intent, activityInfo, resultTo, launchModeFlags); + } + // 移至前台 + mAms.moveTaskToFront(taskRecord.id, 0); + + boolean notStartToFront = clearTop || singleTop || clearTask; + boolean startTaskToFront = !notStartToFront && ComponentUtils.intentFilterEquals(taskRecord.rootIntent, intent) + && taskRecord.rootIntent.getFlags() == intent.getFlags(); + if (startTaskToFront) + return 0; + + ActivityRecord topActivityRecord = taskRecord.getTopActivityRecord(); + ActivityRecord targetActivityRecord = findActivityRecordByComponentName(userId, ComponentUtils.toComponentName(activityInfo)); + ActivityRecord newIntentRecord = null; + + if (clearTop) { + if (targetActivityRecord != null) { + // 目标栈上面所有activity出栈 + synchronized (Objects.requireNonNull(targetActivityRecord.task).activities) { + for (int i = targetActivityRecord.task.activities.size() - 1; i >= 0; i--) { + ActivityRecord next = targetActivityRecord.task.activities.get(i); + if (next != targetActivityRecord) { + next.finished = true; + Slog.d(TAG, "makerFinish: " + Objects.requireNonNull(next.component)); + } else { + if (singleTop) { + newIntentRecord = targetActivityRecord; + } else { + // clearTop并且不是singleTop,目标也finish,重建。 + targetActivityRecord.finished = true; + } + break; + } + } + } + } + } + + if (singleTop && !clearTop) { + if (ComponentUtils.intentFilterEquals(topActivityRecord.intent, intent)) { + newIntentRecord = topActivityRecord; + } + } + + if (activityInfo.launchMode == ActivityInfo.LAUNCH_SINGLE_TASK && !clearTop) { + if (ComponentUtils.intentFilterEquals(topActivityRecord.intent, intent)) { + newIntentRecord = topActivityRecord; + } else { + ActivityRecord record = findActivityRecordByComponentName(userId, ComponentUtils.toComponentName(activityInfo)); + if (record != null) { + // 需要调用目标onNewIntent + newIntentRecord = record; + // 目标栈上面所有activity出栈 + synchronized (taskRecord.activities) { + for (int i = taskRecord.activities.size() - 1; i >= 0; i--) { + ActivityRecord next = taskRecord.activities.get(i); + if (next != record) { + next.finished = true; + } else { + break; + } + } + } + } + } + } + + if (activityInfo.launchMode == ActivityInfo.LAUNCH_SINGLE_INSTANCE) { + newIntentRecord = topActivityRecord; + } + + // clearTask finish All + if (clearTask && newTask) { + for (ActivityRecord activity : taskRecord.activities) { + activity.finished = true; + } + } + + finishAllActivity(userId); + + if (newIntentRecord != null) { + // 通知onNewIntent + deliverNewIntentLocked(newIntentRecord, intent); + return 0; + } + + if (resultTo == null) { + ActivityRecord top = taskRecord.getTopActivityRecord(); + if (top != null) { + resultTo = top.token; + } + } else if (sourceTask != null) { + ActivityRecord top = sourceTask.getTopActivityRecord(); + if (top != null) { + resultTo = top.token; + } + } + return startActivityInSourceTask(intent, resolvedType, resultTo, resultWho, requestCode, flags, options, userId, topActivityRecord, activityInfo, + launchModeFlags); + } + + private void deliverNewIntentLocked(ActivityRecord activityRecord, Intent intent) { + try { + Objects.requireNonNull(activityRecord.processRecord).bActivityThread.handleNewIntent(activityRecord.token, intent); + } catch (RemoteException e) { + e.printStackTrace(); + } + } + + private Intent startActivityProcess(int userId, Intent intent, ActivityInfo info, ActivityRecord record) { + ProxyActivityRecord stubRecord = new ProxyActivityRecord(userId, info, intent, record.mBToken); + ProcessRecord targetApp = BProcessManagerService.get().startProcessLocked(info.packageName, info.processName, userId, -1, Binder.getCallingPid()); + if (targetApp == null) { + throw new RuntimeException("Unable to create process, name:" + info.name); + } + return getStartStubActivityIntentInner(intent, targetApp.bPID, stubRecord, info); + } + + private int startActivityInNewTaskLocked(int userId, Intent intent, ActivityInfo activityInfo, IBinder resultTo, int launchMode) { + ActivityRecord record = newActivityRecord(intent, activityInfo, resultTo, userId); + Intent shadow = startActivityProcess(userId, intent, activityInfo, record); + + shadow.addFlags(Intent.FLAG_ACTIVITY_MULTIPLE_TASK); + shadow.addFlags(Intent.FLAG_ACTIVITY_NEW_DOCUMENT); + shadow.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + shadow.addFlags(launchMode); + + BlackBoxCore.getContext().startActivity(shadow); + return 0; + } + + private int startActivityInSourceTask(Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options, + int userId, ActivityRecord sourceRecord, ActivityInfo activityInfo, int launchMode) { + ActivityRecord selfRecord = newActivityRecord(intent, activityInfo, resultTo, userId); + Intent shadow = startActivityProcess(userId, intent, activityInfo, selfRecord); + shadow.setAction(UUID.randomUUID().toString()); + shadow.addFlags(launchMode); + if (resultTo == null) { + shadow.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + } + return realStartActivityLocked(Objects.requireNonNull(sourceRecord.processRecord).appThread, shadow, resolvedType, resultTo, resultWho, requestCode, flags, options); + } + + private int realStartActivityLocked(IInterface appThread, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, + Bundle options) { + try { + flags &= ~ActivityManagerCompat.START_FLAG_DEBUG; + flags &= ~ActivityManagerCompat.START_FLAG_NATIVE_DEBUGGING; + flags &= ~ActivityManagerCompat.START_FLAG_TRACK_ALLOCATION; + + IActivityManager.startActivity.call(ActivityManagerNative.getDefault.call(), appThread, BlackBoxCore.getHostPkg(), intent, resolvedType, resultTo, resultWho, requestCode, flags, null, options); + } catch (Throwable e) { + e.printStackTrace(); + } + return 0; + } + + private Intent getStartStubActivityIntentInner(Intent intent, int vPID, ProxyActivityRecord target, ActivityInfo activityInfo) { + Intent shadow = new Intent(); + TypedArray typedArray = null; + + try { + Resources resources = PackageManagerCompat.getResources(BlackBoxCore.getContext(), activityInfo.applicationInfo); + int id; + if (activityInfo.theme != 0) { + id = activityInfo.theme; + } else { + id = activityInfo.applicationInfo.theme; + } + + assert resources != null; + typedArray = resources.newTheme().obtainStyledAttributes(id, ArrayUtils.toInt(black.com.android.internal.R.styleable.Window.get())); + boolean windowIsTranslucent = typedArray.getBoolean(black.com.android.internal.R.styleable.Window_windowIsTranslucent.get(), false); + if (windowIsTranslucent) { + shadow.setComponent(new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.TransparentProxyActivity(vPID))); + } else { + shadow.setComponent(new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyActivity(vPID))); + } + + Slog.d(TAG, activityInfo + ", windowIsTranslucent: " + windowIsTranslucent); + } catch (Throwable e) { + e.printStackTrace(); + shadow.setComponent(new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyActivity(vPID))); + } finally { + if (typedArray != null) { + typedArray.recycle(); + } + } + ProxyActivityRecord.saveStub(shadow, intent, target.mActivityInfo, target.mActivityToken, target.mUserId); + return shadow; + } + + private void finishAllActivity(int userId) { + for (TaskRecord task : mTasks.values()) { + for (ActivityRecord activity : task.activities) { + if (activity.userId == userId) { + if (activity.finished) { + try { + assert activity.processRecord != null; + activity.processRecord.bActivityThread.finishActivity(activity.token); + } catch (RemoteException ignored) { } + } + } + } + } + } + + ActivityRecord newActivityRecord(Intent intent, ActivityInfo info, IBinder resultTo, int userId) { + ActivityRecord targetRecord = ActivityRecord.create(intent, info, resultTo, userId); + synchronized (mLaunchingActivities) { + mLaunchingActivities.put(targetRecord.mBToken, targetRecord); + Message obtain = Message.obtain(mHandler, LAUNCH_TIME_OUT, targetRecord.mBToken); + mHandler.sendMessageDelayed(obtain, 15000); + } + return targetRecord; + } + + private ActivityRecord findActivityRecordByComponentName(int userId, ComponentName componentName) { + ActivityRecord record = null; + for (TaskRecord next : mTasks.values()) { + if (userId == next.userId) { + for (ActivityRecord activity : next.activities) { + if (Objects.equals(activity.component, componentName)) { + record = activity; + break; + } + } + } + } + return record; + } + + private ActivityRecord findActivityRecordByToken(int userId, IBinder token) { + ActivityRecord record = null; + if (token != null) { + for (TaskRecord next : mTasks.values()) { + if (userId == next.userId) { + for (ActivityRecord activity : next.activities) { + if (activity.token == token) { + record = activity; + break; + } + } + } + } + } + return record; + } + + private TaskRecord findTaskRecordByTaskAffinityLocked(int userId, String taskAffinity) { + synchronized (mTasks) { + for (TaskRecord next : mTasks.values()) { + if (userId == next.userId && next.taskAffinity.equals(taskAffinity)) { + return next; + } + } + return null; + } + } + + public void onActivityCreated(ProcessRecord processRecord, int taskId, IBinder + token, String activityToken) { + ActivityRecord record = mLaunchingActivities.get(activityToken); + if (record == null) { + return; + } + + synchronized (mLaunchingActivities) { + mLaunchingActivities.remove(activityToken); + mHandler.removeMessages(LAUNCH_TIME_OUT, activityToken); + } + + synchronized (mTasks) { + synchronizeTasks(); + TaskRecord taskRecord = mTasks.get(taskId); + if (taskRecord == null) { + taskRecord = new TaskRecord(taskId, record.userId, ComponentUtils.getTaskAffinity(Objects.requireNonNull(record.info))); + taskRecord.rootIntent = record.intent; + mTasks.put(taskId, taskRecord); + } + + record.token = token; + record.processRecord = processRecord; + record.task = taskRecord; + taskRecord.addTopActivity(record); + Slog.d(TAG, "onActivityCreated : " + Objects.requireNonNull(record.component)); + } + } + + // FIXME: Multiple activities belonged to same app. + public void onActivityResumed(int userId, IBinder token) { + synchronized (mTasks) { + synchronizeTasks(); + ActivityRecord activityRecord = findActivityRecordByToken(userId, token); + if (activityRecord == null) { + return; + } + + Slog.d(TAG, "onActivityResumed : " + Objects.requireNonNull(activityRecord.component)); + synchronized (Objects.requireNonNull(activityRecord.task).activities) { + activityRecord.task.removeActivity(activityRecord); + activityRecord.task.addTopActivity(activityRecord); + } + } + } + + public void onActivityDestroyed(int userId, IBinder token) { + synchronized (mTasks) { + synchronizeTasks(); + ActivityRecord activityRecord = findActivityRecordByToken(userId, token); + if (activityRecord == null) { + return; + } + + activityRecord.finished = true; + Slog.d(TAG, "onActivityDestroyed : " + Objects.requireNonNull(activityRecord.component)); + synchronized (Objects.requireNonNull(activityRecord.task).activities) { + activityRecord.task.removeActivity(activityRecord); + } + } + } + + public void onFinishActivity(int userId, IBinder token) { + synchronized (mTasks) { + synchronizeTasks(); + ActivityRecord activityRecord = findActivityRecordByToken(userId, token); + if (activityRecord == null) { + return; + } + + activityRecord.finished = true; + Slog.d(TAG, "onFinishActivity : " + Objects.requireNonNull(activityRecord.component)); + } + } + + public String getCallingPackage(IBinder token, int userId) { + synchronized (mTasks) { + synchronizeTasks(); + ActivityRecord activityRecordByToken = findActivityRecordByToken(userId, token); + if (activityRecordByToken != null) { + ActivityRecord resultTo = findActivityRecordByToken(userId, activityRecordByToken.resultTo); + if (resultTo != null) { + return Objects.requireNonNull(resultTo.info).packageName; + } + } + return BlackBoxCore.getHostPkg(); + } + } + + public ComponentName getCallingActivity(IBinder token, int userId) { + synchronized (mTasks) { + synchronizeTasks(); + ActivityRecord activityRecordByToken = findActivityRecordByToken(userId, token); + if (activityRecordByToken != null) { + ActivityRecord resultTo = findActivityRecordByToken(userId, activityRecordByToken.resultTo); + if (resultTo != null) { + return resultTo.component; + } + } + return new ComponentName(BlackBoxCore.getHostPkg(), ProxyActivity.P0.class.getName()); + } + } + + private void synchronizeTasks() { + List recentTasks = mAms.getRecentTasks(100, 0); + Map newTacks = new LinkedHashMap<>(); + + for (int i = recentTasks.size() - 1; i >= 0; i--) { + ActivityManager.RecentTaskInfo next = recentTasks.get(i); + TaskRecord taskRecord = mTasks.get(next.id); + if (taskRecord == null) { + continue; + } + newTacks.put(next.id, taskRecord); + } + + mTasks.clear(); + mTasks.putAll(newTacks); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/BActivityManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BActivityManagerService.java similarity index 80% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/BActivityManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BActivityManagerService.java index 748509b..f1e8047 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/BActivityManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BActivityManagerService.java @@ -1,4 +1,6 @@ -package top.niunaijun.blackbox.core.system.am; +package com.vcore.core.system.am; + +import static android.content.pm.PackageManager.GET_META_DATA; import android.app.ActivityManager; import android.content.ComponentName; @@ -15,34 +17,23 @@ import java.util.List; import java.util.Map; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.system.BProcessManagerService; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.ProcessRecord; -import top.niunaijun.blackbox.core.system.pm.BPackageManagerService; -import top.niunaijun.blackbox.entity.AppConfig; -import top.niunaijun.blackbox.entity.UnbindRecord; -import top.niunaijun.blackbox.entity.am.PendingResultData; -import top.niunaijun.blackbox.entity.am.ReceiverData; -import top.niunaijun.blackbox.entity.am.RunningAppProcessInfo; -import top.niunaijun.blackbox.entity.am.RunningServiceInfo; -import top.niunaijun.blackbox.utils.Slog; - -import static android.content.pm.PackageManager.GET_META_DATA; +import com.vcore.BlackBoxCore; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.entity.AppConfig; +import com.vcore.entity.UnbindRecord; +import com.vcore.entity.am.PendingResultData; +import com.vcore.entity.am.ReceiverData; +import com.vcore.entity.am.RunningAppProcessInfo; +import com.vcore.entity.am.RunningServiceInfo; +import com.vcore.utils.Slog; -/** - * Created by Milk on 3/31/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BActivityManagerService extends IBActivityManagerService.Stub implements ISystemService { public static final String TAG = "BActivityManagerService"; private static final BActivityManagerService sService = new BActivityManagerService(); private final Map mUserSpace = new HashMap<>(); - private final BPackageManagerService mPms = BPackageManagerService.get(); private final BroadcastManager mBroadcastManager; public static BActivityManagerService get() { @@ -50,29 +41,28 @@ public static BActivityManagerService get() { } public BActivityManagerService() { - mBroadcastManager = BroadcastManager.startSystem(this, mPms); + BPackageManagerService mPms = BPackageManagerService.get(); + this.mBroadcastManager = BroadcastManager.startSystem(mPms); } @Override public ComponentName startService(Intent intent, String resolvedType, boolean requireForeground, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { - userSpace.mActiveServices.startService(intent, resolvedType, requireForeground, userId); + userSpace.mActiveServices.startService(intent, resolvedType, userId); } return null; } @Override - public IBinder acquireContentProviderClient(ProviderInfo providerInfo) throws RemoteException { + public IBinder acquireContentProviderClient(ProviderInfo providerInfo) { int callingPid = Binder.getCallingPid(); - ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(providerInfo.packageName, - providerInfo.processName, - BProcessManagerService.get().getUserIdByCallingPid(callingPid), - -1, - Binder.getCallingPid()); + ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(providerInfo.packageName, providerInfo.processName, + BProcessManagerService.get().getUserIdByCallingPid(callingPid), -1, Binder.getCallingPid()); if (processRecord == null) { throw new RuntimeException("Unable to create process " + providerInfo.name); } + try { return processRecord.bActivityThread.acquireContentProviderClient(providerInfo); } catch (Throwable t) { @@ -82,20 +72,21 @@ public IBinder acquireContentProviderClient(ProviderInfo providerInfo) throws Re } @Override - public Intent sendBroadcast(Intent intent, String resolvedType, int userId) throws RemoteException { + public Intent sendBroadcast(Intent intent, String resolvedType, int userId) { List resolves = BPackageManagerService.get().queryBroadcastReceivers(intent, GET_META_DATA, resolvedType, userId); - for (ResolveInfo resolve : resolves) { ProcessRecord processRecord = BProcessManagerService.get().findProcessRecord(resolve.activityInfo.packageName, resolve.activityInfo.processName, userId); if (processRecord == null) { continue; } + try { processRecord.bActivityThread.bindApplication(); } catch (RemoteException e) { e.printStackTrace(); } } + Intent shadow = new Intent(); shadow.setPackage(BlackBoxCore.getHostPkg()); shadow.setComponent(null); @@ -112,16 +103,18 @@ public IBinder peekService(Intent intent, String resolvedType, int userId) throw } @Override - public void onActivityCreated(int taskId, IBinder token, IBinder activityRecord) throws RemoteException { + public void onActivityCreated(int taskId, IBinder token, String activityToken) { int callingPid = Binder.getCallingPid(); ProcessRecord process = BProcessManagerService.get().findProcessByPid(callingPid); if (process == null) { return; } - ActivityRecord record = (ActivityRecord) activityRecord; + + // Crash by BinderProxy cast + // ActivityRecord record = (ActivityRecord) activityRecord; UserSpace userSpace = getOrCreateSpaceLocked(process.userId); synchronized (userSpace.mStack) { - userSpace.mStack.onActivityCreated(process, taskId, token, record); + userSpace.mStack.onActivityCreated(process, taskId, token, activityToken); } } @@ -132,6 +125,7 @@ public void onActivityResumed(IBinder token) throws RemoteException { if (process == null) { return; } + UserSpace userSpace = getOrCreateSpaceLocked(process.userId); synchronized (userSpace.mStack) { userSpace.mStack.onActivityResumed(process.userId, token); @@ -145,6 +139,7 @@ public void onActivityDestroyed(IBinder token) throws RemoteException { if (process == null) { return; } + UserSpace userSpace = getOrCreateSpaceLocked(process.userId); synchronized (userSpace.mStack) { userSpace.mStack.onActivityDestroyed(process.userId, token); @@ -152,12 +147,13 @@ public void onActivityDestroyed(IBinder token) throws RemoteException { } @Override - public void onFinishActivity(IBinder token) throws RemoteException { + public void onFinishActivity(IBinder token) { int callingPid = Binder.getCallingPid(); ProcessRecord process = BProcessManagerService.get().findProcessByPid(callingPid); if (process == null) { return; } + UserSpace userSpace = getOrCreateSpaceLocked(process.userId); synchronized (userSpace.mStack) { userSpace.mStack.onFinishActivity(process.userId, token); @@ -165,16 +161,16 @@ public void onFinishActivity(IBinder token) throws RemoteException { } @Override - public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int userId) throws RemoteException { - ActivityManager manager = (ActivityManager) - BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); + public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int userId) { + ActivityManager manager = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); List runningAppProcesses = manager.getRunningAppProcesses(); Map runningProcessMap = new HashMap<>(); + for (ActivityManager.RunningAppProcessInfo runningProcess : runningAppProcesses) { runningProcessMap.put(runningProcess.pid, runningProcess); } - List packageProcessAsUser = BProcessManagerService.get().getPackageProcessAsUser(callerPackage, userId); + List packageProcessAsUser = BProcessManagerService.get().getPackageProcessAsUser(callerPackage, userId); RunningAppProcessInfo appProcessInfo = new RunningAppProcessInfo(); for (ProcessRecord processRecord : packageProcessAsUser) { ActivityManager.RunningAppProcessInfo runningAppProcessInfo = runningProcessMap.get(processRecord.pid); @@ -187,7 +183,7 @@ public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int us } @Override - public RunningServiceInfo getRunningServices(String callerPackage, int userId) throws RemoteException { + public RunningServiceInfo getRunningServices(String callerPackage, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); return userSpace.mActiveServices.getRunningServiceInfo(callerPackage, userId); } @@ -195,12 +191,12 @@ public RunningServiceInfo getRunningServices(String callerPackage, int userId) t @Override public void scheduleBroadcastReceiver(Intent intent, PendingResultData pendingResultData, int userId) throws RemoteException { List resolves = BPackageManagerService.get().queryBroadcastReceivers(intent, GET_META_DATA, null, userId); - if (resolves.isEmpty()) { pendingResultData.build().finish(); Slog.d(TAG, "scheduleBroadcastReceiver empty"); return; } + mBroadcastManager.sendBroadcast(pendingResultData); for (ResolveInfo resolve : resolves) { ProcessRecord processRecord = BProcessManagerService.get().findProcessRecord(resolve.activityInfo.packageName, resolve.activityInfo.processName, userId); @@ -215,12 +211,12 @@ public void scheduleBroadcastReceiver(Intent intent, PendingResultData pendingRe } @Override - public void finishBroadcast(PendingResultData data) throws RemoteException { + public void finishBroadcast(PendingResultData data) { mBroadcastManager.finishBroadcast(data); } @Override - public String getCallingPackage(IBinder token, int userId) throws RemoteException { + public String getCallingPackage(IBinder token, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mStack) { return userSpace.mStack.getCallingPackage(token, userId); @@ -228,7 +224,7 @@ public String getCallingPackage(IBinder token, int userId) throws RemoteExceptio } @Override - public ComponentName getCallingActivity(IBinder token, int userId) throws RemoteException { + public ComponentName getCallingActivity(IBinder token, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mStack) { return userSpace.mStack.getCallingActivity(token, userId); @@ -247,7 +243,7 @@ public void getIntentSender(IBinder target, String packageName, int uid, int use } @Override - public String getPackageForIntentSender(IBinder target, int userId) throws RemoteException { + public String getPackageForIntentSender(IBinder target, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mIntentSenderRecords) { PendingIntentRecord record = userSpace.mIntentSenderRecords.get(target); @@ -259,7 +255,7 @@ public String getPackageForIntentSender(IBinder target, int userId) throws Remot } @Override - public int getUidForIntentSender(IBinder target, int userId) throws RemoteException { + public int getUidForIntentSender(IBinder target, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mIntentSenderRecords) { PendingIntentRecord record = userSpace.mIntentSenderRecords.get(target); @@ -271,26 +267,18 @@ public int getUidForIntentSender(IBinder target, int userId) throws RemoteExcept } @Override - public void onStartCommand(Intent intent, int userId) throws RemoteException { + public UnbindRecord onServiceUnbind(Intent proxyIntent, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { - userSpace.mActiveServices.onStartCommand(intent, userId); + return userSpace.mActiveServices.onServiceUnbind(proxyIntent); } } @Override - public UnbindRecord onServiceUnbind(Intent proxyIntent, int userId) throws RemoteException { + public void onServiceDestroy(Intent proxyIntent, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { - return userSpace.mActiveServices.onServiceUnbind(proxyIntent, userId); - } - } - - @Override - public void onServiceDestroy(Intent proxyIntent, int userId) throws RemoteException { - UserSpace userSpace = getOrCreateSpaceLocked(userId); - synchronized (userSpace.mActiveServices) { - userSpace.mActiveServices.onServiceDestroy(proxyIntent, userId); + userSpace.mActiveServices.onServiceDestroy(proxyIntent); } } @@ -303,7 +291,7 @@ public int stopService(Intent intent, String resolvedType, int userId) { } @Override - public Intent bindService(Intent service, IBinder binder, String resolvedType, int userId) throws RemoteException { + public Intent bindService(Intent service, IBinder binder, String resolvedType, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { return userSpace.mActiveServices.bindService(service, binder, resolvedType, userId); @@ -311,31 +299,32 @@ public Intent bindService(Intent service, IBinder binder, String resolvedType, i } @Override - public void unbindService(IBinder binder, int userId) throws RemoteException { + public void unbindService(IBinder binder, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { - userSpace.mActiveServices.unbindService(binder, userId); + userSpace.mActiveServices.unbindService(binder); } } @Override - public void stopServiceToken(ComponentName className, IBinder token, int userId) throws RemoteException { + public void stopServiceToken(ComponentName className, IBinder token, int userId) { UserSpace userSpace = getOrCreateSpaceLocked(userId); synchronized (userSpace.mActiveServices) { - userSpace.mActiveServices.stopServiceToken(className, token, userId); + userSpace.mActiveServices.stopServiceToken(token, userId); } } @Override - public AppConfig initProcess(String packageName, String processName, int userId) throws RemoteException { + public AppConfig initProcess(String packageName, String processName, int userId) { ProcessRecord processRecord = BProcessManagerService.get().startProcessLocked(packageName, processName, userId, -1, Binder.getCallingPid()); - if (processRecord == null) + if (processRecord == null) { return null; + } return processRecord.getClientConfig(); } @Override - public void restartProcess(String packageName, String processName, int userId) throws RemoteException { + public void restartProcess(String packageName, String processName, int userId) { BProcessManagerService.get().restartAppProcess(packageName, processName, userId); } @@ -348,7 +337,7 @@ public void startActivity(Intent intent, int userId) { } @Override - public int startActivityAms(int userId, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options) throws RemoteException { + public int startActivityAms(int userId, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options) { UserSpace space = getOrCreateSpaceLocked(userId); synchronized (space.mStack) { return space.mStack.startActivityLocked(userId, intent, resolvedType, resultTo, resultWho, requestCode, flags, options); @@ -356,7 +345,7 @@ public int startActivityAms(int userId, Intent intent, String resolvedType, IBin } @Override - public int startActivities(int userId, Intent[] intent, String[] resolvedType, IBinder resultTo, Bundle options) throws RemoteException { + public int startActivities(int userId, Intent[] intent, String[] resolvedType, IBinder resultTo, Bundle options) { UserSpace space = getOrCreateSpaceLocked(userId); synchronized (space.mStack) { return space.mStack.startActivitiesLocked(userId, intent, resolvedType, resultTo, options); @@ -366,8 +355,10 @@ public int startActivities(int userId, Intent[] intent, String[] resolvedType, I private UserSpace getOrCreateSpaceLocked(int userId) { synchronized (mUserSpace) { UserSpace userSpace = mUserSpace.get(userId); - if (userSpace != null) + if (userSpace != null) { return userSpace; + } + userSpace = new UserSpace(); mUserSpace.put(userId, userSpace); return userSpace; diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BJobManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BJobManagerService.java new file mode 100644 index 0000000..eb89281 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BJobManagerService.java @@ -0,0 +1,85 @@ +package com.vcore.core.system.am; + +import android.app.job.JobInfo; +import android.content.ComponentName; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.content.pm.ResolveInfo; +import android.content.pm.ServiceInfo; +import android.os.Binder; +import android.os.RemoteException; + +import java.util.HashMap; +import java.util.Map; + +import com.vcore.BlackBoxCore; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.entity.JobRecord; +import com.vcore.proxy.ProxyManifest; + + + +public class BJobManagerService extends IBJobManagerService.Stub implements ISystemService { + private static final BJobManagerService sService = new BJobManagerService(); + + private final Map mJobRecords = new HashMap<>(); + + public static BJobManagerService get() { + return sService; + } + + @Override + public JobInfo schedule(JobInfo info, int userId) { + ComponentName componentName = info.getService(); + Intent intent = new Intent(); + intent.setComponent(componentName); + ResolveInfo resolveInfo = BPackageManagerService.get().resolveService(intent, PackageManager.GET_META_DATA, null, userId); + if (resolveInfo == null) { + return info; + } + + ServiceInfo serviceInfo = resolveInfo.serviceInfo; + ProcessRecord processRecord = BProcessManagerService.get().findProcessRecord(serviceInfo.packageName, serviceInfo.processName, userId); + if (processRecord == null) { + processRecord = BProcessManagerService.get().startProcessLocked(serviceInfo.packageName, serviceInfo.processName, userId, + -1, Binder.getCallingPid()); + if (processRecord == null) { + throw new RuntimeException("Unable to create Process " + serviceInfo.processName); + } + } + return scheduleJob(processRecord, info, serviceInfo); + } + + @Override + public JobRecord queryJobRecord(String processName, int jobId, int userId) { + return mJobRecords.get(formatKey(processName, jobId)); + } + + public JobInfo scheduleJob(ProcessRecord processRecord, JobInfo info, ServiceInfo serviceInfo) { + JobRecord jobRecord = new JobRecord(); + jobRecord.mJobInfo = info; + jobRecord.mServiceInfo = serviceInfo; + + mJobRecords.put(formatKey(processRecord.processName, info.getId()), jobRecord); + black.android.app.job.JobInfo.service.set(info, new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyJobService(processRecord.bPID))); + return info; + } + + @Override + public void cancelAll(String processName, int userId) { } + + @Override + public int cancel(String processName, int jobId, int userId) throws RemoteException { + return jobId; + } + + private String formatKey(String processName, int jobId) { + return processName + "_" + jobId; + } + + @Override + public void systemReady() { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BroadcastManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BroadcastManager.java new file mode 100644 index 0000000..9f91a58 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/BroadcastManager.java @@ -0,0 +1,135 @@ +package com.vcore.core.system.am; + +import android.content.BroadcastReceiver; +import android.os.Handler; +import android.os.Looper; +import android.os.Message; + +import java.util.ArrayList; +import java.util.HashMap; +import java.util.List; +import java.util.Map; + +import com.vcore.BlackBoxCore; +import com.vcore.core.system.pm.BPackage; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.core.system.pm.PackageMonitor; +import com.vcore.entity.am.PendingResultData; +import com.vcore.proxy.ProxyBroadcastReceiver; +import com.vcore.utils.Slog; + +public class BroadcastManager implements PackageMonitor { + public static final String TAG = "BroadcastManager"; + public static final int TIMEOUT = 9000; + public static final int MSG_TIME_OUT = 1; + private static volatile BroadcastManager sBroadcastManager; + + private final BPackageManagerService mPms; + private final Map> mReceivers = new HashMap<>(); + private final Map mReceiversData = new HashMap<>(); + + private final Handler mHandler = new Handler(Looper.getMainLooper()) { + @Override + public void handleMessage(Message msg) { + super.handleMessage(msg); + if (msg.what == MSG_TIME_OUT) { + try { + PendingResultData data = (PendingResultData) msg.obj; + data.build().finish(); + Slog.d(TAG, "Timeout Receiver: " + data); + } catch (Throwable ignore) { } + } + } + }; + + public static BroadcastManager startSystem(BPackageManagerService pms) { + if (sBroadcastManager == null) { + synchronized (BroadcastManager.class) { + if (sBroadcastManager == null) { + sBroadcastManager = new BroadcastManager(pms); + } + } + } + return sBroadcastManager; + } + + public BroadcastManager(BPackageManagerService pms) { + this.mPms = pms; + } + + public void startup() { + mPms.addPackageMonitor(this); + List bPackageSettings = mPms.getBPackageSettings(); + for (BPackageSettings bPackageSetting : bPackageSettings) { + BPackage bPackage = bPackageSetting.pkg; + registerPackage(bPackage); + } + } + + private void registerPackage(BPackage bPackage) { + synchronized (mReceivers) { + Slog.d(TAG, "register: " + bPackage.packageName + ", size: " + bPackage.receivers.size()); + for (BPackage.Activity receiver : bPackage.receivers) { + List intents = receiver.intents; + for (BPackage.ActivityIntentInfo intent : intents) { + ProxyBroadcastReceiver proxyBroadcastReceiver = new ProxyBroadcastReceiver(); + BlackBoxCore.getContext().registerReceiver(proxyBroadcastReceiver, intent.intentFilter); + addReceiver(bPackage.packageName, proxyBroadcastReceiver); + } + } + } + } + + private void addReceiver(String packageName, BroadcastReceiver receiver) { + List broadcastReceivers = mReceivers.get(packageName); + if (broadcastReceivers == null) { + broadcastReceivers = new ArrayList<>(); + mReceivers.put(packageName, broadcastReceivers); + } + broadcastReceivers.add(receiver); + } + + public void sendBroadcast(PendingResultData pendingResultData) { + synchronized (mReceiversData) { + mReceiversData.put(pendingResultData.mBToken, pendingResultData); + Message obtain = Message.obtain(mHandler, MSG_TIME_OUT, pendingResultData); + mHandler.sendMessageDelayed(obtain, TIMEOUT); + } + } + + public void finishBroadcast(PendingResultData data) { + synchronized (mReceiversData) { + mHandler.removeMessages(MSG_TIME_OUT, mReceiversData.get(data.mBToken)); + } + } + + @Override + public void onPackageUninstalled(String packageName, boolean removeApp, int userId) { + if (removeApp) { + synchronized (mReceivers) { + List broadcastReceivers = mReceivers.get(packageName); + if (broadcastReceivers != null) { + Slog.d(TAG, "unregisterReceiver Package: " + packageName + ", size: " + broadcastReceivers.size()); + for (BroadcastReceiver broadcastReceiver : broadcastReceivers) { + try { + BlackBoxCore.getContext().unregisterReceiver(broadcastReceiver); + } catch (Throwable ignored) { } + } + } + mReceivers.remove(packageName); + } + } + } + + @Override + public void onPackageInstalled(String packageName, int userId) { + synchronized (mReceivers) { + mReceivers.remove(packageName); + BPackageSettings bPackageSetting = mPms.getBPackageSetting(packageName); + if (bPackageSetting != null) { + registerPackage(bPackageSetting.pkg); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/PendingIntentRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/PendingIntentRecord.java new file mode 100644 index 0000000..8eebdc4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/PendingIntentRecord.java @@ -0,0 +1,27 @@ +package com.vcore.core.system.am; + +import java.util.Objects; + +public class PendingIntentRecord { + public int uid; + public String packageName; + + @Override + public boolean equals(Object o) { + if (o == this) { + return true; + } + + if (!(o instanceof PendingIntentRecord)) { + return false; + } + + PendingIntentRecord that = (PendingIntentRecord) o; + return uid == that.uid && Objects.equals(packageName, that.packageName); + } + + @Override + public int hashCode() { + return Objects.hash(uid, packageName); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/TaskRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/TaskRecord.java similarity index 82% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/TaskRecord.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/TaskRecord.java index c1fa292..f614c06 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/am/TaskRecord.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/TaskRecord.java @@ -1,22 +1,17 @@ -package top.niunaijun.blackbox.core.system.am; +package com.vcore.core.system.am; import android.content.Intent; import java.util.LinkedList; import java.util.List; -/** - * Created by Milk on 4/9/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ + + + public class TaskRecord { - public int id; - public int userId; - public String taskAffinity; + public final int id; + public final int userId; + public final String taskAffinity; public Intent rootIntent; public final List activities = new LinkedList<>(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/UserSpace.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/UserSpace.java new file mode 100644 index 0000000..ad21ef3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/am/UserSpace.java @@ -0,0 +1,14 @@ +package com.vcore.core.system.am; + +import android.os.IBinder; + +import java.util.HashMap; +import java.util.Map; + +public class UserSpace { + // 单实例 + public final ActiveServices mActiveServices = new ActiveServices(); + // 单实例 + public final ActivityStack mStack = new ActivityStack(); + public final Map mIntentSenderRecords = new HashMap<>(); +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/location/BLocationManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/BLocationManagerService.java similarity index 90% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/location/BLocationManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/BLocationManagerService.java index 84dd4a0..1ab5c53 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/location/BLocationManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/BLocationManagerService.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.location; +package com.vcore.core.system.location; import android.os.IBinder; import android.os.IInterface; @@ -17,18 +17,17 @@ import java.util.concurrent.Executor; import java.util.concurrent.Executors; -import black.android.location.BRILocationListener; -import black.android.location.BRILocationListenerStub; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.entity.location.BCell; -import top.niunaijun.blackbox.entity.location.BLocation; -import top.niunaijun.blackbox.entity.location.BLocationConfig; -import top.niunaijun.blackbox.fake.frameworks.BLocationManager; -import top.niunaijun.blackbox.utils.CloseUtils; -import top.niunaijun.blackbox.utils.FileUtils; -import top.niunaijun.blackbox.utils.Slog; +import black.android.location.ILocationListener; +import com.vcore.BlackBoxCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.ISystemService; +import com.vcore.entity.location.BCell; +import com.vcore.entity.location.BLocation; +import com.vcore.entity.location.BLocationConfig; +import com.vcore.fake.frameworks.BLocationManager; +import com.vcore.utils.CloseUtils; +import com.vcore.utils.FileUtils; +import com.vcore.utils.Slog; /** * Fake location @@ -58,6 +57,7 @@ private BLocationConfig getOrCreateConfig(int userId, String pkg) { pkgs = new HashMap<>(); mLocationConfigs.put(userId, pkgs); } + BLocationConfig config = pkgs.get(pkg); if (config == null) { config = new BLocationConfig(); @@ -215,8 +215,11 @@ public void requestLocationUpdates(IBinder listener, String packageName, int use if (listener == null || !listener.pingBinder()) { return; } - if (mLocationListeners.containsKey(listener)) + + if (mLocationListeners.containsKey(listener)) { return; + } + listener.linkToDeath(new DeathRecipient() { @Override public void binderDied() { @@ -241,24 +244,29 @@ private void addTask(IBinder locationListener) { mThreadPool.execute(() -> { BLocation lastLocation = null; long l = System.currentTimeMillis(); + while (locationListener.pingBinder()) { - IInterface iInterface = BRILocationListenerStub.get().asInterface(locationListener); + IInterface iInterface = ILocationListener.Stub.asInterface.call(locationListener); LocationRecord locationRecord = mLocationListeners.get(locationListener); - if (locationRecord == null) + if (locationRecord == null) { continue; + } + BLocation location = getLocation(locationRecord.userId, locationRecord.packageName); - if (location == null) + if (location == null) { continue; + } + if (location.equals(lastLocation) && (System.currentTimeMillis() - l) < 3000) { try { Thread.sleep(1000); - } catch (InterruptedException ignored) { - } + } catch (InterruptedException ignored) { } continue; } + lastLocation = location; l = System.currentTimeMillis(); - BlackBoxCore.get().getHandler().post(() -> BRILocationListener.get(iInterface).onLocationChanged(location.convert2SystemLocation())); + BlackBoxCore.get().getHandler().post(() -> ILocationListener.onLocationChanged.call(iInterface, location.convert2SystemLocation())); } }); } @@ -269,16 +277,18 @@ public void save() { Parcel parcel = Parcel.obtain(); AtomicFile atomicFile = new AtomicFile(BEnvironment.getFakeLocationConf()); FileOutputStream fileOutputStream = null; + try { mGlobalConfig.writeToParcel(parcel, 0); - parcel.writeInt(mLocationConfigs.size()); + for (int i = 0; i < mLocationConfigs.size(); i++) { int tmpUserId = mLocationConfigs.keyAt(i); HashMap configArrayMap = mLocationConfigs.valueAt(i); parcel.writeInt(tmpUserId); parcel.writeMap(configArrayMap); } + parcel.setDataPosition(0); fileOutputStream = atomicFile.startWrite(); FileUtils.writeParcelToOutput(parcel, fileOutputStream); @@ -297,11 +307,13 @@ public void save() { public void loadConfig() { Parcel parcel = Parcel.obtain(); InputStream is = null; + try { File fakeLocationConf = BEnvironment.getFakeLocationConf(); if (!fakeLocationConf.exists()) { return; } + is = new FileInputStream(BEnvironment.getFakeLocationConf()); byte[] bytes = FileUtils.toByteArray(is); parcel.unmarshall(bytes, 0, bytes.length); @@ -313,6 +325,7 @@ public void loadConfig() { synchronized (mLocationConfigs) { mLocationConfigs.clear(); + int size = parcel.readInt(); for (int i = 0; i < size; i++) { int userId = parcel.readInt(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/LocationRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/LocationRecord.java new file mode 100644 index 0000000..eda6b2c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/location/LocationRecord.java @@ -0,0 +1,11 @@ +package com.vcore.core.system.location; + +public class LocationRecord { + public final String packageName; + public final int userId; + + public LocationRecord(String packageName, int userId) { + this.packageName = packageName; + this.userId = userId; + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/BNotificationManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/BNotificationManagerService.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/BNotificationManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/BNotificationManagerService.java index cd114c8..06dc512 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/BNotificationManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/BNotificationManagerService.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.notification; +package com.vcore.core.system.notification; import android.annotation.SuppressLint; import android.annotation.TargetApi; @@ -9,48 +9,33 @@ import android.content.Context; import android.os.Binder; import android.os.Build; -import android.os.RemoteException; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; -import black.android.app.BRNotificationChannel; -import black.android.app.BRNotificationChannelGroup; -import black.android.app.BRNotificationO; -import black.android.app.NotificationChannelContext; -import black.android.app.NotificationChannelGroupContext; -import black.android.app.NotificationOContext; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.system.BProcessManagerService; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.ProcessRecord; -import top.niunaijun.blackbox.utils.compat.BuildCompat; - -/** - * Created by BlackBox on 2022/3/15. - */ +import black.android.app.NotificationO; +import com.vcore.BlackBoxCore; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.utils.compat.BuildCompat; + public class BNotificationManagerService extends IBNotificationManagerService.Stub implements ISystemService { private final static BNotificationManagerService sService = new BNotificationManagerService(); public static final String CHANNEL_BLACK = "@black-"; public static final String GROUP_BLACK = "@black-group-"; - - private NotificationChannelManager mNotificationChannelManager; private final Map mNotificationRecords = new HashMap<>(); - private final NotificationManager mRealNotificationManager = - (NotificationManager) BlackBoxCore.getContext().getSystemService(Context.NOTIFICATION_SERVICE); + private final NotificationManager mRealNotificationManager = (NotificationManager) BlackBoxCore.getContext().getSystemService(Context.NOTIFICATION_SERVICE); public static BNotificationManagerService get() { return sService; } @Override - public void systemReady() { - mNotificationChannelManager = NotificationChannelManager.get(); - } - + public void systemReady() { } private NotificationRecord getNotificationRecord(String packageName, int userId) { String key = packageName + "-" + userId; @@ -73,11 +58,13 @@ private void removeNotificationRecord(String packageName, int userId) { @Override @TargetApi(Build.VERSION_CODES.O) - public NotificationChannel getNotificationChannel(String channelId, int userId) throws RemoteException { + public NotificationChannel getNotificationChannel(String channelId, int userId) { int callingPid = getCallingPid(); ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); - if (processByPid == null) + if (processByPid == null) { return null; + } + NotificationRecord notificationRecord = getNotificationRecord(processByPid.getPackageName(), userId); synchronized (notificationRecord.mNotificationChannels) { return notificationRecord.mNotificationChannels.get(channelId); @@ -85,7 +72,7 @@ public NotificationChannel getNotificationChannel(String channelId, int userId) } @Override - public List getNotificationChannels(String packageName, int userId) throws RemoteException { + public List getNotificationChannels(String packageName, int userId) { NotificationRecord notificationRecord = getNotificationRecord(packageName, userId); synchronized (notificationRecord.mNotificationChannels) { return new ArrayList<>(notificationRecord.mNotificationChannels.values()); @@ -93,7 +80,7 @@ public List getNotificationChannels(String packageName, int } @Override - public List getNotificationChannelGroups(String packageName, int userId) throws RemoteException { + public List getNotificationChannelGroups(String packageName, int userId) { NotificationRecord notificationRecord = getNotificationRecord(packageName, userId); synchronized (notificationRecord.mNotificationChannelGroups) { return new ArrayList<>(notificationRecord.mNotificationChannelGroups.values()); @@ -105,8 +92,10 @@ public List getNotificationChannelGroups(String packag public void createNotificationChannel(NotificationChannel notificationChannel, int userId) { int callingPid = getCallingPid(); ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); - if (processByPid == null) + if (processByPid == null) { return; + } + handleNotificationChannel(notificationChannel, userId); mRealNotificationManager.createNotificationChannel(notificationChannel); @@ -122,8 +111,10 @@ public void createNotificationChannel(NotificationChannel notificationChannel, i public void deleteNotificationChannel(String channelId, int userId) { int callingPid = getCallingPid(); ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); - if (processByPid == null) + if (processByPid == null) { return; + } + NotificationRecord notificationRecord = getNotificationRecord(processByPid.getPackageName(), userId); synchronized (notificationRecord.mNotificationChannels) { NotificationChannel remove = notificationRecord.mNotificationChannels.remove(channelId); @@ -139,8 +130,10 @@ public void deleteNotificationChannel(String channelId, int userId) { public void createNotificationChannelGroup(NotificationChannelGroup notificationChannelGroup, int userId) { int callingPid = getCallingPid(); ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); - if (processByPid == null) + if (processByPid == null) { return; + } + handleNotificationGroup(notificationChannelGroup, userId); mRealNotificationManager.createNotificationChannelGroup(notificationChannelGroup); @@ -156,8 +149,10 @@ public void createNotificationChannelGroup(NotificationChannelGroup notification public void deleteNotificationChannelGroup(String groupId, int userId) { int callingPid = getCallingPid(); ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(callingPid); - if (processByPid == null) + if (processByPid == null) { return; + } + NotificationRecord notificationRecord = getNotificationRecord(processByPid.getPackageName(), userId); synchronized (notificationRecord.mNotificationChannelGroups) { NotificationChannelGroup remove = notificationRecord.mNotificationChannelGroups.remove(groupId); @@ -171,23 +166,23 @@ public void deleteNotificationChannelGroup(String groupId, int userId) { @Override public void enqueueNotificationWithTag(int id, String tag, Notification notification, int userId) { ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(Binder.getCallingPid()); - if (processByPid == null) + if (processByPid == null) { return; - int notificationId = getNotificationId(userId, id, processByPid.getPackageName()); + } + int notificationId = getNotificationId(userId, id, processByPid.getPackageName()); if (BuildCompat.isOreo()) { - NotificationOContext notificationOContext = BRNotificationO.get(notification); - // channel - if (notificationOContext._check_mChannelId() != null) { - String blackChannelId = getBlackChannelId(notificationOContext.mChannelId(), userId); - notificationOContext._set_mChannelId(blackChannelId); + if (NotificationO.mChannelId != null) { + String blackChannelId = getBlackChannelId(NotificationO.mChannelId.get(), userId); + NotificationO.mChannelId.set(blackChannelId); } - // group - if (notificationOContext._check_mGroupKey() != null) { - String blackGroupId = getBlackGroupId(notificationOContext.mGroupKey(), userId); - notificationOContext._set_mGroupKey(blackGroupId); + + if (NotificationO.mGroupKey != null) { + String blackGroupId = getBlackGroupId(NotificationO.mGroupKey.get(), userId); + NotificationO.mGroupKey.set(blackGroupId); } } + NotificationRecord notificationRecord = getNotificationRecord(processByPid.getPackageName(), userId); synchronized (notificationRecord.mIds) { notificationRecord.mIds.add(notificationId); @@ -196,10 +191,12 @@ public void enqueueNotificationWithTag(int id, String tag, Notification notifica } @Override - public void cancelNotificationWithTag(int id, String tag, int userId) throws RemoteException { + public void cancelNotificationWithTag(int id, String tag, int userId) { ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(Binder.getCallingPid()); - if (processByPid == null) + if (processByPid == null) { return; + } + int notificationId = getNotificationId(userId, id, processByPid.getPackageName()); mRealNotificationManager.cancel(notificationId); @@ -211,28 +208,25 @@ public void cancelNotificationWithTag(int id, String tag, int userId) throws Rem @TargetApi(Build.VERSION_CODES.O) private void handleNotificationChannel(NotificationChannel notificationChannel, int userId) { - NotificationChannelContext channelContext = BRNotificationChannel.get(notificationChannel); - String channelId = channelContext.mId(); + String channelId = black.android.app.NotificationChannel.mId.get(notificationChannel); String blackChannelId = getBlackChannelId(channelId, userId); - channelContext._set_mId(blackChannelId); + black.android.app.NotificationChannel.mId.set(notificationChannel, blackChannelId); notificationChannel.setGroup(getBlackGroupId(notificationChannel.getGroup(), userId)); } private void resetNotificationChannel(NotificationChannel notificationChannel) { - NotificationChannelContext channelContext = BRNotificationChannel.get(notificationChannel); - String channelId = channelContext.mId(); + String channelId = black.android.app.NotificationChannel.mId.get(notificationChannel); String realChannelId = getRealChannelId(channelId); - channelContext._set_mId(realChannelId); + black.android.app.NotificationChannel.mId.set(notificationChannel, realChannelId); } private void handleNotificationGroup(NotificationChannelGroup notificationChannelGroup, int userId) { - NotificationChannelGroupContext groupContext = BRNotificationChannelGroup.get(notificationChannelGroup); - String groupId = groupContext.mId(); + String groupId = black.android.app.NotificationChannelGroup.mId.get(notificationChannelGroup); String blackGroupId = getBlackGroupId(groupId, userId); - groupContext._set_mId(blackGroupId); + black.android.app.NotificationChannelGroup.mId.set(notificationChannelGroup, blackGroupId); - List notificationChannels = groupContext.mChannels(); + List notificationChannels = black.android.app.NotificationChannelGroup.mChannels.get(notificationChannelGroup); if (notificationChannels != null) { for (NotificationChannel notificationChannel : notificationChannels) { createNotificationChannel(notificationChannel, userId); @@ -241,12 +235,11 @@ private void handleNotificationGroup(NotificationChannelGroup notificationChanne } private void resetNotificationGroup(NotificationChannelGroup notificationChannelGroup) { - NotificationChannelGroupContext groupContext = BRNotificationChannelGroup.get(notificationChannelGroup); - String groupId = groupContext.mId(); + String groupId = black.android.app.NotificationChannelGroup.mId.get(notificationChannelGroup); String realGroupId = getRealGroupId(groupId); - groupContext._set_mId(realGroupId); + black.android.app.NotificationChannelGroup.mId.set(notificationChannelGroup, realGroupId); - List notificationChannels = groupContext.mChannels(); + List notificationChannels = black.android.app.NotificationChannelGroup.mChannels.get(notificationChannelGroup); if (notificationChannels != null) { for (NotificationChannel notificationChannel : notificationChannels) { resetNotificationChannel(notificationChannel); @@ -262,11 +255,13 @@ public void deletePackageNotification(String packageName, int userId) { String blackGroupId = getBlackGroupId(value.getId(), userId); mRealNotificationManager.deleteNotificationChannelGroup(blackGroupId); } + for (NotificationChannel value : notificationRecord.mNotificationChannels.values()) { String blackChannelId = getBlackChannelId(value.getId(), userId); mRealNotificationManager.deleteNotificationChannel(blackChannelId); } } + for (Integer id : notificationRecord.mIds) { mRealNotificationManager.cancel(id); } @@ -288,14 +283,16 @@ private String getRealChannelId(String channelId) { } private String getBlackGroupId(String groupId, int userId) { - if (groupId == null || groupId.contains(GROUP_BLACK)) + if (groupId == null || groupId.contains(GROUP_BLACK)) { return groupId; + } return groupId + GROUP_BLACK + userId; } private String getRealGroupId(String groupId) { - if (groupId == null || !groupId.contains(GROUP_BLACK)) + if (groupId == null || !groupId.contains(GROUP_BLACK)) { return groupId; + } return groupId.split(GROUP_BLACK)[0]; } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/NotificationRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/NotificationRecord.java similarity index 82% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/NotificationRecord.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/NotificationRecord.java index 5ffe69c..0203168 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/notification/NotificationRecord.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/notification/NotificationRecord.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.notification; +package com.vcore.core.system.notification; import android.app.NotificationChannel; import android.app.NotificationChannelGroup; @@ -8,9 +8,6 @@ import java.util.Map; import java.util.Set; -/** - * Created by BlackBox on 2022/3/18. - */ public class NotificationRecord { public final Map mNotificationChannels = new HashMap<>(); public final Map mNotificationChannelGroups = new HashMap<>(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/os/BStorageManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/os/BStorageManagerService.java new file mode 100644 index 0000000..07246c1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/os/BStorageManagerService.java @@ -0,0 +1,59 @@ +package com.vcore.core.system.os; + +import android.net.Uri; +import android.os.Process; +import android.os.storage.StorageVolume; + +import java.io.File; + +import black.android.os.storage.StorageManager; +import com.vcore.BlackBoxCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.fake.provider.FileProvider; +import com.vcore.proxy.ProxyManifest; +import com.vcore.utils.compat.BuildCompat; + +public class BStorageManagerService extends IBStorageManagerService.Stub implements ISystemService { + private static final BStorageManagerService sService = new BStorageManagerService(); + + public static BStorageManagerService get() { + return sService; + } + + public BStorageManagerService() { } + + @Override + public StorageVolume[] getVolumeList(int uid, String packageName, int flags, int userId) { + if (StorageManager.getVolumeList == null) { + return null; + } + + try { + StorageVolume[] storageVolumes = StorageManager.getVolumeList.call(BUserHandle.getUserId(Process.myUid()), 0); + if (storageVolumes == null) { + return null; + } + + for (StorageVolume storageVolume : storageVolumes) { + black.android.os.storage.StorageVolume.mPath.set(storageVolume, BEnvironment.getExternalUserDir(userId)); + if (BuildCompat.isPie()) { + black.android.os.storage.StorageVolume.mInternalPath.set(storageVolume, BEnvironment.getExternalUserDir(userId)); + } + } + return storageVolumes; + } catch (Exception e) { + e.printStackTrace(); + } + return null; + } + + @Override + public Uri getUriForFile(String file) { + return FileProvider.getUriForFile(BlackBoxCore.getContext(), ProxyManifest.getProxyFileProvider(), new File(file)); + } + + @Override + public void systemReady() { } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackage.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackage.java similarity index 91% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackage.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackage.java index 114358a..1ecd04d 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackage.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackage.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import android.content.ComponentName; import android.content.IntentFilter; @@ -19,45 +19,35 @@ import java.util.ArrayList; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.utils.compat.BuildCompat; - -/** - * Created by Milk on 4/21/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.compat.BuildCompat; + public class BPackage implements Parcelable { - public ArrayList activities = new ArrayList(0); - public ArrayList receivers = new ArrayList(0); - public ArrayList providers = new ArrayList(0); - public ArrayList services = new ArrayList(0); - public ArrayList instrumentation = new ArrayList(0); - public ArrayList permissions = new ArrayList(0); - public ArrayList permissionGroups = new ArrayList(0); - public ArrayList requestedPermissions = new ArrayList(); - public Signature[] mSignatures; + public final ArrayList activities; + public final ArrayList receivers; + public final ArrayList providers; + public final ArrayList services; + public final ArrayList instrumentation; + public final ArrayList permissions; + public final ArrayList permissionGroups; + public ArrayList requestedPermissions = new ArrayList<>(); + public final Signature[] mSignatures; public SigningDetails mSigningDetails; - public Bundle mAppMetaData; + public final Bundle mAppMetaData; public BPackageSettings mExtras; - public String packageName; - public int mPreferredOrder; - public String mSharedUserId; - public ArrayList usesLibraries; - public ArrayList usesOptionalLibraries; - public int mVersionCode; + public final String packageName; + public final int mPreferredOrder; + public final String mSharedUserId; + public final ArrayList usesLibraries; + public final ArrayList usesOptionalLibraries; + public final int mVersionCode; public ApplicationInfo applicationInfo; - public String mVersionName; + public final String mVersionName; public String baseCodePath; - public int mSharedUserLabel; - // Applications hardware preferences - public ArrayList configPreferences = null; - // Applications requested features - public ArrayList reqFeatures = null; + public final int mSharedUserLabel; + public final ArrayList configPreferences; + public final ArrayList reqFeatures; public InstallOption installOption; @@ -68,6 +58,7 @@ public BPackage(PackageParser.Package aPackage) { for (ActivityIntentInfo intent : selfActivity.intents) { intent.activity = selfActivity; } + selfActivity.owner = this; this.activities.add(selfActivity); } @@ -78,6 +69,7 @@ public BPackage(PackageParser.Package aPackage) { for (ActivityIntentInfo intent : selfReceiver.intents) { intent.activity = selfReceiver; } + selfReceiver.owner = this; this.receivers.add(selfReceiver); } @@ -88,6 +80,7 @@ public BPackage(PackageParser.Package aPackage) { for (ProviderIntentInfo intent : selfProvider.intents) { intent.provider = selfProvider; } + selfProvider.owner = this; this.providers.add(selfProvider); } @@ -98,6 +91,7 @@ public BPackage(PackageParser.Package aPackage) { for (ServiceIntentInfo intent : selfService.intents) { intent.service = selfService; } + selfService.owner = this; this.services.add(selfService); } @@ -130,6 +124,7 @@ public BPackage(PackageParser.Package aPackage) { } else { this.mSignatures = aPackage.mSignatures; } + this.mAppMetaData = aPackage.mAppMetaData; // this.mExtras = new BPackageSettings((PackageSetting) aPackage.mExtras); this.packageName = aPackage.packageName; @@ -154,6 +149,7 @@ protected BPackage(Parcel in) { for (ActivityIntentInfo intent : activity.intents) { intent.activity = activity; } + activity.owner = this; this.activities.add(activity); } @@ -165,6 +161,7 @@ protected BPackage(Parcel in) { for (ActivityIntentInfo intent : activity.intents) { intent.activity = activity; } + activity.owner = this; this.receivers.add(activity); } @@ -176,6 +173,7 @@ protected BPackage(Parcel in) { for (ProviderIntentInfo intent : provider.intents) { intent.provider = provider; } + provider.owner = this; this.providers.add(provider); } @@ -187,6 +185,7 @@ protected BPackage(Parcel in) { for (ServiceIntentInfo intent : service.intents) { intent.service = service; } + service.owner = this; this.services.add(service); } @@ -219,9 +218,10 @@ protected BPackage(Parcel in) { if (BuildCompat.isPie()) { this.mSigningDetails = in.readParcelable(SigningDetails.class.getClassLoader()); } + this.mSignatures = in.createTypedArray(Signature.CREATOR); this.mAppMetaData = in.readBundle(Bundle.class.getClassLoader()); -// this.mExtras = in.readParcelable(BPackageSettings.class.getClassLoader()); + // this.mExtras = in.readParcelable(BPackageSettings.class.getClassLoader()); this.packageName = in.readString(); this.mPreferredOrder = in.readInt(); this.mSharedUserId = in.readString(); @@ -238,14 +238,16 @@ protected BPackage(Parcel in) { } public final static class Activity extends Component { - public ActivityInfo info; + public final ActivityInfo info; public Activity(PackageParser.Activity activity) { super(activity); this.info = activity.info; + if (activity.intents != null) { int size = activity.intents.size(); this.intents = new ArrayList<>(size); + for (PackageParser.ActivityIntentInfo intent : activity.intents) { this.intents.add(new ActivityIntentInfo(intent)); } @@ -257,6 +259,7 @@ public Activity(Parcel parcel) { this.info = parcel.readParcelable(ActivityInfo.class.getClassLoader()); int N = parcel.readInt(); this.intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); this.intents.add(new ActivityIntentInfo(intentInfo)); @@ -265,14 +268,16 @@ public Activity(Parcel parcel) { } public static final class Service extends Component { - public ServiceInfo info; + public final ServiceInfo info; public Service(PackageParser.Service service) { super(service); info = service.info; + if (service.intents != null) { int size = service.intents.size(); intents = new ArrayList<>(size); + for (PackageParser.ServiceIntentInfo intent : service.intents) { intents.add(new ServiceIntentInfo(intent)); } @@ -284,6 +289,7 @@ public Service(Parcel parcel) { info = parcel.readParcelable(ServiceInfo.class.getClassLoader()); int N = parcel.readInt(); intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); intents.add(new ServiceIntentInfo(intentInfo)); @@ -292,14 +298,16 @@ public Service(Parcel parcel) { } public static final class Provider extends Component { - public ProviderInfo info; + public final ProviderInfo info; public Provider(PackageParser.Provider provider) { super(provider); info = provider.info; + if (provider.intents != null) { int size = provider.intents.size(); intents = new ArrayList<>(size); + for (PackageParser.ProviderIntentInfo intent : provider.intents) { intents.add(new ProviderIntentInfo(intent)); } @@ -311,6 +319,7 @@ public Provider(Parcel parcel) { info = parcel.readParcelable(ProviderInfo.class.getClassLoader()); int N = parcel.readInt(); intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); intents.add(new ProviderIntentInfo(intentInfo)); @@ -319,14 +328,16 @@ public Provider(Parcel parcel) { } public static final class Instrumentation extends Component { - public InstrumentationInfo info; + public final InstrumentationInfo info; public Instrumentation(PackageParser.Instrumentation instrumentation) { super(instrumentation); info = instrumentation.info; + if (instrumentation.intents != null) { int size = instrumentation.intents.size(); this.intents = new ArrayList<>(size); + for (PackageParser.IntentInfo intent : instrumentation.intents) { this.intents.add(new IntentInfo(intent)); } @@ -338,6 +349,7 @@ public Instrumentation(Parcel parcel) { this.info = parcel.readParcelable(InstrumentationInfo.class.getClassLoader()); int N = parcel.readInt(); this.intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); this.intents.add(intentInfo); @@ -346,14 +358,16 @@ public Instrumentation(Parcel parcel) { } public static final class Permission extends Component { - public PermissionInfo info; + public final PermissionInfo info; public Permission(PackageParser.Permission permission) { super(permission); this.info = permission.info; + if (permission.intents != null) { int size = permission.intents.size(); this.intents = new ArrayList<>(size); + for (PackageParser.IntentInfo intent : permission.intents) { this.intents.add(new IntentInfo(intent)); } @@ -365,6 +379,7 @@ public Permission(Parcel parcel) { this.info = parcel.readParcelable(Permission.class.getClassLoader()); int N = parcel.readInt(); this.intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); this.intents.add(intentInfo); @@ -373,14 +388,16 @@ public Permission(Parcel parcel) { } public static final class PermissionGroup extends Component { - public PermissionGroupInfo info; + public final PermissionGroupInfo info; public PermissionGroup(PackageParser.PermissionGroup group) { super(group); this.info = group.info; + if (group.intents != null) { int size = group.intents.size(); this.intents = new ArrayList<>(size); + for (PackageParser.IntentInfo intent : group.intents) { this.intents.add(new IntentInfo(intent)); } @@ -392,6 +409,7 @@ public PermissionGroup(Parcel parcel) { this.info = parcel.readParcelable(PermissionGroup.class.getClassLoader()); int N = parcel.readInt(); this.intents = new ArrayList<>(N); + while (N-- > 0) { IntentInfo intentInfo = parcel.readParcelable(BPackage.class.getClassLoader()); this.intents.add(intentInfo); @@ -436,9 +454,7 @@ public ProviderIntentInfo(IntentInfo intentInfo) { } public static final class SigningDetails implements Parcelable { - public Signature[] signatures; - - public static final PackageParser.SigningDetails UNKNOWN = null; + public final Signature[] signatures; @Override public int describeContents() { @@ -458,7 +474,7 @@ public SigningDetails(PackageParser.SigningDetails signingDetails) { } } - protected SigningDetails(Parcel in) { + private SigningDetails(Parcel in) { this.signatures = in.createTypedArray(Signature.CREATOR); } @@ -476,13 +492,13 @@ public SigningDetails[] newArray(int size) { } public static class IntentInfo implements Parcelable { - public IntentFilter intentFilter; - public boolean hasDefault; - public int labelRes; - public String nonLocalizedLabel; - public int icon; - public int logo; - public int banner; + public final IntentFilter intentFilter; + public final boolean hasDefault; + public final int labelRes; + public final String nonLocalizedLabel; + public final int icon; + public final int logo; + public final int banner; public IntentInfo(PackageParser.IntentInfo intentInfo) { this.intentFilter = intentInfo; @@ -498,7 +514,7 @@ public IntentInfo(IntentInfo intentInfo) { this.intentFilter = intentInfo.intentFilter; this.hasDefault = intentInfo.hasDefault; this.labelRes = intentInfo.labelRes; - this.nonLocalizedLabel = intentInfo.nonLocalizedLabel == null ? null : intentInfo.nonLocalizedLabel.toString(); + this.nonLocalizedLabel = intentInfo.nonLocalizedLabel == null ? null : intentInfo.nonLocalizedLabel; this.icon = intentInfo.icon; this.logo = intentInfo.logo; this.banner = intentInfo.banner; @@ -546,8 +562,8 @@ public IntentInfo[] newArray(int size) { public static class Component { public BPackage owner; public ArrayList intents; - public String className; - public Bundle metaData; + public final String className; + public final Bundle metaData; public ComponentName componentName; public Component(Parcel parcel) { @@ -565,8 +581,7 @@ public ComponentName getComponentName() { return componentName; } if (className != null) { - componentName = new ComponentName(owner.packageName, - className); + componentName = new ComponentName(owner.packageName, className); } return componentName; } @@ -581,11 +596,12 @@ public int describeContents() { public void writeToParcel(Parcel dest, int flags) { int size = this.activities.size(); dest.writeInt(size); + for (Activity activity : this.activities) { dest.writeString(activity.className); dest.writeBundle(activity.metaData); - dest.writeParcelable(activity.info, flags); + if (activity.intents != null) { int N = activity.intents.size(); dest.writeInt(N); @@ -599,11 +615,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.receivers.size(); dest.writeInt(size); + for (Activity receiver : this.receivers) { dest.writeString(receiver.className); dest.writeBundle(receiver.metaData); - dest.writeParcelable(receiver.info, flags); + if (receiver.intents != null) { int N = receiver.intents.size(); dest.writeInt(N); @@ -617,11 +634,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.providers.size(); dest.writeInt(size); + for (Provider provider : this.providers) { dest.writeString(provider.className); dest.writeBundle(provider.metaData); - dest.writeParcelable(provider.info, flags); + if (provider.intents != null) { int N = provider.intents.size(); dest.writeInt(N); @@ -635,11 +653,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.services.size(); dest.writeInt(size); + for (Service service : this.services) { dest.writeString(service.className); dest.writeBundle(service.metaData); - dest.writeParcelable(service.info, flags); + if (service.intents != null) { int N = service.intents.size(); dest.writeInt(N); @@ -653,11 +672,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.instrumentation.size(); dest.writeInt(size); + for (Instrumentation instrumentation : this.instrumentation) { dest.writeString(instrumentation.className); dest.writeBundle(instrumentation.metaData); - dest.writeParcelable(instrumentation.info, flags); + if (instrumentation.intents != null) { int N = instrumentation.intents.size(); dest.writeInt(N); @@ -671,11 +691,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.permissions.size(); dest.writeInt(size); + for (Permission permission : this.permissions) { dest.writeString(permission.className); dest.writeBundle(permission.metaData); - dest.writeParcelable(permission.info, flags); + if (permission.intents != null) { int N = permission.intents.size(); dest.writeInt(N); @@ -689,11 +710,12 @@ public void writeToParcel(Parcel dest, int flags) { size = this.permissionGroups.size(); dest.writeInt(size); + for (PermissionGroup permissionGroup : this.permissionGroups) { dest.writeString(permissionGroup.className); dest.writeBundle(permissionGroup.metaData); - dest.writeParcelable(permissionGroup.info, flags); + if (permissionGroup.intents != null) { int N = permissionGroup.intents.size(); dest.writeInt(N); @@ -709,9 +731,10 @@ public void writeToParcel(Parcel dest, int flags) { if (BuildCompat.isPie()) { dest.writeParcelable(this.mSigningDetails, flags); } + dest.writeTypedArray(this.mSignatures, flags); dest.writeBundle(this.mAppMetaData); -// dest.writeParcelable(this.mExtras, flags); + // dest.writeParcelable(this.mExtras, flags); dest.writeString(this.packageName); dest.writeInt(this.mPreferredOrder); dest.writeString(this.mSharedUserId); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageInstallerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageInstallerService.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageInstallerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageInstallerService.java index 0f3fd5e..b60be96 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageInstallerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageInstallerService.java @@ -1,26 +1,20 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import java.util.ArrayList; import java.util.List; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.pm.installer.CopyExecutor; -import top.niunaijun.blackbox.core.system.pm.installer.CreatePackageExecutor; -import top.niunaijun.blackbox.core.system.pm.installer.CreateUserExecutor; -import top.niunaijun.blackbox.core.system.pm.installer.Executor; -import top.niunaijun.blackbox.core.system.pm.installer.RemoveAppExecutor; -import top.niunaijun.blackbox.core.system.pm.installer.RemoveUserExecutor; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.utils.Slog; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.pm.installer.CopyExecutor; +import com.vcore.core.system.pm.installer.CreatePackageExecutor; +import com.vcore.core.system.pm.installer.CreateUserExecutor; +import com.vcore.core.system.pm.installer.Executor; +import com.vcore.core.system.pm.installer.RemoveAppExecutor; +import com.vcore.core.system.pm.installer.RemoveUserExecutor; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.Slog; + + -/** - * Created by Milk on 4/21/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BPackageInstallerService extends IBPackageInstallerService.Stub implements ISystemService { private static final BPackageInstallerService sService = new BPackageInstallerService(); @@ -104,7 +98,5 @@ public int updatePackage(BPackageSettings ps) { } @Override - public void systemReady() { - - } + public void systemReady() { } } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageManagerService.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageManagerService.java index 0cb9ec6..713bd98 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageManagerService.java @@ -1,4 +1,6 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; + +import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; import android.content.BroadcastReceiver; import android.content.ComponentName; @@ -14,7 +16,7 @@ import android.content.pm.ResolveInfo; import android.content.pm.ServiceInfo; import android.net.Uri; -import android.os.Binder; +import android.os.Build; import android.os.RemoteException; import android.text.TextUtils; @@ -28,38 +30,29 @@ import java.util.Objects; import java.util.UUID; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.GmsCore; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.BProcessManagerService; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.ProcessRecord; -import top.niunaijun.blackbox.core.system.user.BUserHandle; -import top.niunaijun.blackbox.core.system.user.BUserInfo; -import top.niunaijun.blackbox.core.system.user.BUserManagerService; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.entity.pm.InstallResult; -import top.niunaijun.blackbox.entity.pm.InstalledPackage; -import top.niunaijun.blackbox.utils.AbiUtils; -import top.niunaijun.blackbox.utils.FileUtils; -import top.niunaijun.blackbox.utils.Slog; -import top.niunaijun.blackbox.utils.compat.PackageParserCompat; -import top.niunaijun.blackbox.utils.compat.XposedParserCompat; +import com.vcore.BlackBoxCore; +import com.vcore.core.GmsCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.ProcessRecord; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.core.system.user.BUserInfo; +import com.vcore.core.system.user.BUserManagerService; +import com.vcore.entity.pm.InstallOption; +import com.vcore.entity.pm.InstallResult; +import com.vcore.entity.pm.InstalledPackage; +import com.vcore.utils.AbiUtils; +import com.vcore.utils.FileUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.PackageParserCompat; +import com.vcore.utils.compat.XposedParserCompat; -import static android.content.pm.PackageManager.MATCH_DIRECT_BOOT_UNAWARE; -/** - * Created by Milk on 4/1/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BPackageManagerService extends IBPackageManagerService.Stub implements ISystemService { public static final String TAG = "BPackageManagerService"; - public static BPackageManagerService sService = new BPackageManagerService(); + public static final BPackageManagerService sService = new BPackageManagerService(); private final Settings mSettings = new Settings(); private final ComponentResolver mComponentResolver; private static final BUserManagerService sUserManager = BUserManagerService.get(); @@ -78,25 +71,27 @@ public BPackageManagerService() { filter.addAction("android.intent.action.PACKAGE_ADDED"); filter.addAction("android.intent.action.PACKAGE_REMOVED"); filter.addDataScheme("package"); - BlackBoxCore.getContext() - .registerReceiver(mPackageChangedHandler, filter); - } - private final BroadcastReceiver mPackageChangedHandler = new BroadcastReceiver() { - @Override - public void onReceive(Context context, Intent intent) { - String action = intent.getAction(); - if (!TextUtils.isEmpty(action)) { - if ("android.intent.action.PACKAGE_ADDED".equals(action) || "android.intent.action.PACKAGE_REMOVED".equals(action)) { - mSettings.scanPackage(); + BroadcastReceiver mPackageChangedHandler = new BroadcastReceiver() { + @Override + public void onReceive(Context context, Intent intent) { + String action = intent.getAction(); + if (!TextUtils.isEmpty(action)) { + if ("android.intent.action.PACKAGE_ADDED".equals(action) || "android.intent.action.PACKAGE_REMOVED".equals(action)) { + mSettings.scanPackage(); + } } } - } - }; + }; + BlackBoxCore.getContext().registerReceiver(mPackageChangedHandler, filter); + } @Override public ApplicationInfo getApplicationInfo(String packageName, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + if (Objects.equals(packageName, BlackBoxCore.getHostPkg())) { try { return BlackBoxCore.getPackageManager().getApplicationInfo(packageName, flags); @@ -105,10 +100,10 @@ public ApplicationInfo getApplicationInfo(String packageName, int flags, int use } return null; } - flags = updateFlags(flags, userId); - // reader + + flags = updateFlags(flags); synchronized (mPackages) { - // Normalize package name to handle renamed packages and static libs + // Normalize package name to handle renamed packages and static libs. BPackageSettings ps = mPackages.get(packageName); if (ps != null) { BPackage p = ps.pkg; @@ -120,9 +115,11 @@ public ApplicationInfo getApplicationInfo(String packageName, int flags, int use @Override public ResolveInfo resolveService(Intent intent, int flags, String resolvedType, int userId) { - if (!sUserManager.exists(userId)) return null; - List query = queryIntentServicesInternal( - intent, resolvedType, flags, userId); + if (!sUserManager.exists(userId)) { + return null; + } + + List query = queryIntentServicesInternal(intent, resolvedType, flags, userId); if (query != null) { if (query.size() >= 1) { // If there is more than one service with the same priority, @@ -141,6 +138,7 @@ private List queryIntentServicesInternal(Intent intent, String reso comp = intent.getComponent(); } } + if (comp != null) { final List list = new ArrayList<>(1); final ServiceInfo si = getServiceInfo(comp, flags, userId); @@ -156,15 +154,13 @@ private List queryIntentServicesInternal(Intent intent, String reso return list; } - // reader synchronized (mPackages) { String pkgName = intent.getPackage(); if (pkgName != null) { BPackageSettings bPackageSettings = mPackages.get(pkgName); if (bPackageSettings != null) { final BPackage pkg = bPackageSettings.pkg; - return mComponentResolver.queryServices(intent, resolvedType, flags, pkg.services, - userId); + return mComponentResolver.queryServices(intent, resolvedType, flags, pkg.services, userId); } } else { return mComponentResolver.queryServices(intent, resolvedType, flags, userId); @@ -175,26 +171,34 @@ private List queryIntentServicesInternal(Intent intent, String reso @Override public ResolveInfo resolveActivity(Intent intent, int flags, String resolvedType, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + List resolves = queryIntentActivities(intent, resolvedType, flags, userId); - return chooseBestActivity(intent, resolvedType, flags, resolves); + return chooseBestActivity(resolves); } @Override public ProviderInfo resolveContentProvider(String authority, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + return mComponentResolver.queryProvider(authority, flags, userId); } @Override public ResolveInfo resolveIntent(Intent intent, String resolvedType, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + List resolves = queryIntentActivities(intent, resolvedType, flags, userId); - return chooseBestActivity(intent, resolvedType, flags, resolves); + return chooseBestActivity(resolves); } - private ResolveInfo chooseBestActivity(Intent intent, String resolvedType, - int flags, List query) { + private ResolveInfo chooseBestActivity(List query) { if (query != null) { final int N = query.size(); if (N == 1) { @@ -206,9 +210,7 @@ private ResolveInfo chooseBestActivity(Intent intent, String resolvedType, ResolveInfo r1 = query.get(1); // If the first activity has a higher priority, or a different // default, then it is always desirable to pick it. - if (r0.priority != r1.priority - || r0.preferredOrder != r1.preferredOrder - || r0.isDefault != r1.isDefault) { + if (r0.priority != r1.priority || r0.preferredOrder != r1.preferredOrder || r0.isDefault != r1.isDefault) { return query.get(0); } } @@ -216,8 +218,7 @@ private ResolveInfo chooseBestActivity(Intent intent, String resolvedType, return null; } - private List queryIntentActivities(Intent intent, - String resolvedType, int flags, int userId) { + private List queryIntentActivities(Intent intent, String resolvedType, int flags, int userId) { ComponentName comp = intent.getComponent(); if (comp == null) { if (intent.getSelector() != null) { @@ -241,37 +242,48 @@ private List queryIntentActivities(Intent intent, } } - // reader synchronized (mPackages) { return mComponentResolver.queryActivities(intent, resolvedType, flags, userId); } } @Override - public List queryIntentServices( - Intent intent, int flags, int userId) { + public List queryIntentServices(Intent intent, int flags, int userId) { final String resolvedType = intent.resolveTypeIfNeeded(BlackBoxCore.getContext().getContentResolver()); return this.queryIntentServicesInternal(intent, resolvedType, flags, userId); } - private ActivityInfo getActivity(ComponentName component, int flags, - int userId) { - flags = updateFlags(flags, userId); + private ActivityInfo getActivity(ComponentName component, int flags, int userId) { + flags = updateFlags(flags); synchronized (mPackages) { BPackage.Activity a = mComponentResolver.getActivity(component); if (a != null) { BPackageSettings ps = mSettings.mPackages.get(component.getPackageName()); - if (ps == null) return null; + if (ps == null) { + return null; + } return PackageManagerCompat.generateActivityInfo(a, flags, ps.readUserState(userId), userId); } } return null; } + @Override + public int getUidByPid(int pid) { + ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(pid); + if (processByPid != null) { + return processByPid.bUID; + } + return -1; + } + @Override public PackageInfo getPackageInfo(String packageName, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + if (Objects.equals(packageName, BlackBoxCore.getHostPkg())) { try { return BlackBoxCore.getPackageManager().getPackageInfo(packageName, flags); @@ -281,13 +293,14 @@ public PackageInfo getPackageInfo(String packageName, int flags, int userId) { return null; } - flags = updateFlags(flags, userId); - BPackageSettings ps = null; - // reader + flags = updateFlags(flags); + BPackageSettings ps; + synchronized (mPackages) { - // Normalize package name to handle renamed packages and static libs + // Normalize package name to handle renamed packages and static libs. ps = mPackages.get(packageName); } + if (ps != null) { return PackageManagerCompat.generatePackageInfo(ps, flags, ps.readUserState(userId), userId); } @@ -296,14 +309,19 @@ public PackageInfo getPackageInfo(String packageName, int flags, int userId) { @Override public ServiceInfo getServiceInfo(ComponentName component, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + synchronized (mPackages) { BPackage.Service s = mComponentResolver.getService(component); + if (s != null) { BPackageSettings ps = mPackages.get(component.getPackageName()); - if (ps == null) return null; - return PackageManagerCompat.generateServiceInfo( - s, flags, ps.readUserState(userId), userId); + if (ps == null) { + return null; + } + return PackageManagerCompat.generateServiceInfo(s, flags, ps.readUserState(userId), userId); } } return null; @@ -311,14 +329,19 @@ public ServiceInfo getServiceInfo(ComponentName component, int flags, int userId @Override public ActivityInfo getReceiverInfo(ComponentName component, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + synchronized (mPackages) { BPackage.Activity a = mComponentResolver.getReceiver(component); + if (a != null) { BPackageSettings ps = mPackages.get(component.getPackageName()); - if (ps == null) return null; - return PackageManagerCompat.generateActivityInfo( - a, flags, ps.readUserState(userId), userId); + if (ps == null) { + return null; + } + return PackageManagerCompat.generateActivityInfo(a, flags, ps.readUserState(userId), userId); } } return null; @@ -326,15 +349,19 @@ public ActivityInfo getReceiverInfo(ComponentName component, int flags, int user @Override public ActivityInfo getActivityInfo(ComponentName component, int flags, int userId) { - if (!sUserManager.exists(userId)) return null; + if (!sUserManager.exists(userId)) { + return null; + } + synchronized (mPackages) { BPackage.Activity a = mComponentResolver.getActivity(component); if (a != null) { BPackageSettings ps = mPackages.get(component.getPackageName()); - if (ps == null) return null; - return PackageManagerCompat.generateActivityInfo( - a, flags, ps.readUserState(userId), userId); + if (ps == null) { + return null; + } + return PackageManagerCompat.generateActivityInfo(a, flags, ps.readUserState(userId), userId); } } return null; @@ -345,11 +372,13 @@ public ProviderInfo getProviderInfo(ComponentName component, int flags, int user if (!sUserManager.exists(userId)) return null; synchronized (mPackages) { BPackage.Provider p = mComponentResolver.getProvider(component); + if (p != null) { BPackageSettings ps = mPackages.get(component.getPackageName()); - if (ps == null) return null; - return PackageManagerCompat.generateProviderInfo( - p, flags, ps.readUserState(userId), userId); + if (ps == null) { + return null; + } + return PackageManagerCompat.generateProviderInfo(p, flags, ps.readUserState(userId), userId); } } return null; @@ -357,28 +386,20 @@ public ProviderInfo getProviderInfo(ComponentName component, int flags, int user @Override public List getInstalledApplications(int flags, int userId) { - return getInstalledApplicationsListInternal(flags, userId, Binder.getCallingUid()); + return getInstalledApplicationsListInternal(flags, userId); } @Override public List getInstalledPackages(int flags, int userId) { - final int callingUid = Binder.getCallingUid(); -// if (getInstantAppPackageName(callingUid) != null) { -// return ParceledListSlice.emptyList(); -// } - if (!sUserManager.exists(userId)) return Collections.emptyList(); + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } - // writer synchronized (mPackages) { ArrayList list; list = new ArrayList<>(mPackages.size()); + for (BPackageSettings ps : mPackages.values()) { -// if (filterSharedLibPackageLPr(ps, callingUid, userId, flags)) { -// continue; -// } -// if (filterAppAccessLPr(ps, callingUid, userId)) { -// continue; -// } PackageInfo pi = getPackageInfo(ps.pkg.packageName, flags, userId); if (pi != null) { list.add(pi); @@ -388,26 +409,22 @@ public List getInstalledPackages(int flags, int userId) { } } - private List getInstalledApplicationsListInternal(int flags, int userId, - int callingUid) { - if (!sUserManager.exists(userId)) return Collections.emptyList(); + private List getInstalledApplicationsListInternal(int flags, int userId) { + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } - // writer synchronized (mPackages) { ArrayList list; list = new ArrayList<>(mPackages.size()); Collection packageSettings = mPackages.values(); + for (BPackageSettings ps : packageSettings) { -// if (filterSharedLibPackageLPr(ps, Binder.getCallingUid(), userId, flags)) { -// continue; -// } -// if (filterAppAccessLPr(ps, callingUid, userId)) { -// continue; -// } - if (GmsCore.isGoogleAppOrService(ps.pkg.packageName)) + if (GmsCore.isGoogleAppOrService(ps.pkg.packageName)) { continue; - ApplicationInfo ai = PackageManagerCompat.generateApplicationInfo(ps.pkg, flags, - ps.readUserState(userId), userId); + } + + ApplicationInfo ai = PackageManagerCompat.generateApplicationInfo(ps.pkg, flags, ps.readUserState(userId), userId); if (ai != null) { list.add(ai); } @@ -417,8 +434,11 @@ private List getInstalledApplicationsListInternal(int flags, in } @Override - public List queryIntentActivities(Intent intent, int flags, String resolvedType, int userId) throws RemoteException { - if (!sUserManager.exists(userId)) return Collections.emptyList(); + public List queryIntentActivities(Intent intent, int flags, String resolvedType, int userId) { + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } + final String pkgName = intent.getPackage(); ComponentName comp = intent.getComponent(); if (comp == null) { @@ -443,18 +463,17 @@ public List queryIntentActivities(Intent intent, int flags, String return list; } - // reader List result; synchronized (mPackages) { if (pkgName != null) { BPackageSettings bPackageSettings = mPackages.get(pkgName); result = null; + if (bPackageSettings != null) { final BPackage pkg = bPackageSettings.pkg; - - result = mComponentResolver.queryActivities( - intent, resolvedType, flags, pkg.activities, userId); + result = mComponentResolver.queryActivities(intent, resolvedType, flags, pkg.activities, userId); } + if (result == null || result.size() == 0) { // the caller wants to resolve for a particular package; however, there // were no installed results, so, try to find an ephemeral result @@ -469,8 +488,10 @@ public List queryIntentActivities(Intent intent, int flags, String } @Override - public List queryBroadcastReceivers(Intent intent, int flags, String resolvedType, int userId) throws RemoteException { - if (!sUserManager.exists(userId)) return Collections.emptyList(); + public List queryBroadcastReceivers(Intent intent, int flags, String resolvedType, int userId) { + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } ComponentName comp = intent.getComponent(); if (comp == null) { @@ -479,6 +500,7 @@ public List queryBroadcastReceivers(Intent intent, int flags, Strin comp = intent.getComponent(); } } + if (comp != null) { final List list = new ArrayList<>(1); final ActivityInfo ai = getReceiverInfo(comp, flags, userId); @@ -494,14 +516,12 @@ public List queryBroadcastReceivers(Intent intent, int flags, Strin return list; } - // reader synchronized (mPackages) { String pkgName = intent.getPackage(); BPackageSettings bPackageSettings = mPackages.get(pkgName); if (bPackageSettings != null) { final BPackage pkg = bPackageSettings.pkg; - return mComponentResolver.queryReceivers( - intent, resolvedType, flags, pkg.receivers, userId); + return mComponentResolver.queryReceivers(intent, resolvedType, flags, pkg.receivers, userId); } else { return mComponentResolver.queryReceivers(intent, resolvedType, flags, userId); } @@ -510,12 +530,15 @@ public List queryBroadcastReceivers(Intent intent, int flags, Strin @Override public List queryContentProviders(String processName, int uid, int flags, int userId) throws RemoteException { - if (!sUserManager.exists(userId)) return Collections.emptyList(); + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } List providers = new ArrayList<>(); - if (TextUtils.isEmpty(processName)) + if (TextUtils.isEmpty(processName)) { return providers; - providers.addAll(mComponentResolver.queryProviders(processName, null, flags, userId)); + } + providers.addAll(mComponentResolver.queryProviders(processName, flags, userId)); return providers; } @@ -531,21 +554,20 @@ public void uninstallPackageAsUser(String packageName, int userId) throws Remote synchronized (mInstallLock) { synchronized (mPackages) { BPackageSettings ps = mPackages.get(packageName); - if (ps == null) + if (ps == null) { return; + } + if (ps.installOption.isFlag(InstallOption.FLAG_XPOSED) && userId != BUserHandle.USER_XPOSED) { return; } + if (!isInstalled(packageName, userId)) { return; } + boolean removeApp = ps.getUserState().size() <= 1; BProcessManagerService.get().killPackageAsUser(packageName, userId); - int i = BPackageInstallerService.get().uninstallPackageAsUser(ps, removeApp, userId); - if (i < 0) { - // todo - } - if (removeApp) { mSettings.removePackage(packageName); mComponentResolver.removeAllComponents(ps.pkg); @@ -563,8 +585,10 @@ public void uninstallPackage(String packageName) { synchronized (mInstallLock) { synchronized (mPackages) { BPackageSettings ps = mPackages.get(packageName); - if (ps == null) + if (ps == null) { return; + } + BProcessManagerService.get().killAllByPackageName(packageName); if (ps.installOption.isFlag(InstallOption.FLAG_XPOSED)) { for (BUserInfo user : BUserManagerService.get().getAllUsers()) { @@ -583,6 +607,7 @@ public void uninstallPackage(String packageName) { onPackageUninstalled(packageName, true, userId); } } + mSettings.removePackage(packageName); mComponentResolver.removeAllComponents(ps.pkg); } @@ -595,10 +620,6 @@ public void clearPackage(String packageName, int userId) { return; } BProcessManagerService.get().killPackageAsUser(packageName, userId); - BPackageSettings ps = mPackages.get(packageName); - if (ps == null) - return; - int i = BPackageInstallerService.get().clearPackage(ps, userId); } @Override @@ -617,18 +638,25 @@ public void deleteUser(int userId) throws RemoteException { @Override public boolean isInstalled(String packageName, int userId) { - if (!sUserManager.exists(userId)) return false; + if (!sUserManager.exists(userId)) { + return false; + } + synchronized (mPackages) { BPackageSettings ps = mPackages.get(packageName); - if (ps == null) + if (ps == null) { return false; + } return ps.getInstalled(userId); } } @Override public List getInstalledPackagesAsUser(int userId) { - if (!sUserManager.exists(userId)) return Collections.emptyList(); + if (!sUserManager.exists(userId)) { + return Collections.emptyList(); + } + synchronized (mPackages) { List installedPackages = new ArrayList<>(); for (BPackageSettings ps : mPackages.values()) { @@ -644,8 +672,11 @@ public List getInstalledPackagesAsUser(int userId) { } @Override - public String[] getPackagesForUid(int uid, int userId) throws RemoteException { - if (!sUserManager.exists(userId)) return new String[]{}; + public String[] getPackagesForUid(int uid, int userId) { + if (!sUserManager.exists(userId)) { + return new String[]{}; + } + synchronized (mPackages) { List packages = new ArrayList<>(); for (BPackageSettings ps : mPackages.values()) { @@ -654,6 +685,7 @@ public String[] getPackagesForUid(int uid, int userId) throws RemoteException { packages.add(packageName); } } + if (packages.isEmpty()) { ProcessRecord processByPid = BProcessManagerService.get().findProcessByPid(getCallingPid()); if (processByPid != null) { @@ -668,10 +700,12 @@ private InstallResult installPackageAsUserLocked(String file, InstallOption opti long l = System.currentTimeMillis(); InstallResult result = new InstallResult(); File apkFile = null; + try { if (!sUserManager.exists(userId)) { sUserManager.createUser(userId); } + if (option.isFlag(InstallOption.FLAG_URI_FILE)) { apkFile = new File(BEnvironment.getCacheDir(), UUID.randomUUID().toString() + ".apk"); InputStream inputStream = BlackBoxCore.getContext().getContentResolver().openInputStream(Uri.parse(file)); @@ -684,12 +718,12 @@ private InstallResult installPackageAsUserLocked(String file, InstallOption opti return new InstallResult().installError("Please install the XP module in XP module management"); } if (option.isFlag(InstallOption.FLAG_XPOSED) && !XposedParserCompat.isXPModule(apkFile.getAbsolutePath())) { - return new InstallResult().installError("not a XP module"); + return new InstallResult().installError("Not a XP module"); } PackageInfo packageArchiveInfo = BlackBoxCore.getPackageManager().getPackageArchiveInfo(apkFile.getAbsolutePath(), 0); if (packageArchiveInfo == null) { - return result.installError("getPackageArchiveInfo error.Please check whether APK is normal."); + return result.installError("getPackageArchiveInfo error. Please check whether APK is normal."); } boolean support = AbiUtils.isSupport(apkFile); @@ -698,28 +732,29 @@ private InstallResult installPackageAsUserLocked(String file, InstallOption opti return result.installError(packageArchiveInfo.packageName, msg + "\n" + (BlackBoxCore.is64Bit() ? "The box does not support 32-bit Application" : "The box does not support 64-bit Application")); } + PackageParser.Package aPackage = parserApk(apkFile.getAbsolutePath()); if (aPackage == null) { - return result.installError("parser apk error."); + return result.installError("Parser apk error."); } - result.packageName = aPackage.packageName; + result.packageName = aPackage.packageName; if (option.isFlag(InstallOption.FLAG_SYSTEM)) { aPackage.applicationInfo = BlackBoxCore.getPackageManager().getPackageInfo(aPackage.packageName, 0).applicationInfo; } BPackageSettings bPackageSettings = mSettings.getPackageLPw(aPackage.packageName, aPackage, option); - // stop pkg BProcessManagerService.get().killPackageAsUser(aPackage.packageName, userId); - int i = BPackageInstallerService.get().installPackageAsUser(bPackageSettings, userId); if (i < 0) { - return result.installError("install apk error."); + return result.installError("Install apk error."); } + synchronized (mPackages) { bPackageSettings.setInstalled(true, userId); bPackageSettings.save(); } + mComponentResolver.removeAllComponents(bPackageSettings.pkg); mComponentResolver.addAllComponents(bPackageSettings.pkg); mSettings.scanPackage(aPackage.packageName); @@ -731,14 +766,14 @@ private InstallResult installPackageAsUserLocked(String file, InstallOption opti if (apkFile != null && option.isFlag(InstallOption.FLAG_URI_FILE)) { FileUtils.deleteDir(apkFile); } - Slog.d(TAG, "install finish: " + (System.currentTimeMillis() - l) + "ms"); + Slog.d(TAG, "Install finish: " + (System.currentTimeMillis() - l) + "ms"); } return result; } private PackageParser.Package parserApk(String file) { try { - PackageParser parser = PackageParserCompat.createParser(new File(file)); + PackageParser parser = PackageParserCompat.createParser(); PackageParser.Package aPackage = PackageParserCompat.parsePackage(parser, new File(file), 0); PackageParserCompat.collectCertificates(parser, aPackage, 0); return aPackage; @@ -758,14 +793,9 @@ static String fixProcessName(String defProcessName, String processName) { /** * Update given flags based on encryption status of current user. */ - private int updateFlags(int flags, int userId) { - if ((flags & (PackageManager.MATCH_DIRECT_BOOT_UNAWARE - | PackageManager.MATCH_DIRECT_BOOT_AWARE)) != 0) { - // Caller expressed an explicit opinion about what encryption - // aware/unaware components they want to see, so fall through and - // give them what they want - } else { - // Caller expressed no opinion, so match based on user state + private int updateFlags(int flags) { + // Caller expressed no opinion, so match based on user state + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) { flags |= PackageManager.MATCH_DIRECT_BOOT_AWARE | MATCH_DIRECT_BOOT_UNAWARE; } return flags; @@ -773,23 +803,16 @@ private int updateFlags(int flags, int userId) { public int getAppId(String packageName) { BPackageSettings bPackageSettings = mPackages.get(packageName); - if (bPackageSettings != null) + if (bPackageSettings != null) { return bPackageSettings.appId; + } return -1; } - Settings getSettings() { - return mSettings; - } - public void addPackageMonitor(PackageMonitor monitor) { mPackageMonitors.add(monitor); } - public void removePackageMonitor(PackageMonitor monitor) { - mPackageMonitors.remove(monitor); - } - void onPackageUninstalled(String packageName, boolean isRemove, int userId) { for (PackageMonitor packageMonitor : mPackageMonitors) { packageMonitor.onPackageUninstalled(packageName, isRemove, userId); @@ -820,4 +843,4 @@ public void systemReady() { mComponentResolver.addAllComponents(value.pkg); } } -} \ No newline at end of file +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageSettings.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageSettings.java similarity index 78% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageSettings.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageSettings.java index 6ba1904..ee5e17c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageSettings.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageSettings.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import android.os.Parcel; import android.os.Parcelable; @@ -10,29 +10,19 @@ import java.util.List; import java.util.Map; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.user.BUserHandle; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.utils.CloseUtils; -import top.niunaijun.blackbox.utils.FileUtils; - -/** - * Created by Milk on 4/21/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.CloseUtils; +import com.vcore.utils.FileUtils; + public class BPackageSettings implements Parcelable { public BPackage pkg; public int appId; public InstallOption installOption; public Map userState = new HashMap<>(); - static final BPackageUserState DEFAULT_USER_STATE = new BPackageUserState(); - public BPackageSettings() { - } + public BPackageSettings() { } public List getUserState() { return new ArrayList<>(userState.values()); @@ -50,22 +40,6 @@ public boolean getInstalled(int userId) { return readUserState(userId).installed; } - public boolean getStopped(int userId) { - return readUserState(userId).stopped; - } - - public void setStopped(boolean stop, int userId) { - modifyUserState(userId).stopped = stop; - } - - public boolean getHidden(int userId) { - return readUserState(userId).hidden; - } - - public void setHidden(boolean hidden, int userId) { - modifyUserState(userId).hidden = hidden; - } - public void removeUser(int userId) { userState.remove(userId); } @@ -75,6 +49,7 @@ public BPackageUserState readUserState(int userId) { if (state == null) { state = new BPackageUserState(); } + state = new BPackageUserState(state); // xp模块所有用户可见、如果开启的话 if (installOption.isFlag(InstallOption.FLAG_XPOSED) && @@ -82,6 +57,7 @@ public BPackageUserState readUserState(int userId) { BXposedManagerService.get().isXPEnable()) { state.installed = true; } + if (userId == BUserHandle.USER_ALL) { state.installed = true; } @@ -97,22 +73,22 @@ private BPackageUserState modifyUserState(int userId) { return state; } - public boolean save() { + public void save() { synchronized (this) { Parcel parcel = Parcel.obtain(); AtomicFile atomicFile = new AtomicFile(BEnvironment.getPackageConf(pkg.packageName)); FileOutputStream fileOutputStream = null; + try { writeToParcel(parcel, 0); parcel.setDataPosition(0); fileOutputStream = atomicFile.startWrite(); + FileUtils.writeParcelToOutput(parcel, fileOutputStream); atomicFile.finishWrite(fileOutputStream); - return true; } catch (Throwable e) { e.printStackTrace(); atomicFile.failWrite(fileOutputStream); - return false; } finally { parcel.recycle(); CloseUtils.close(fileOutputStream); @@ -131,6 +107,7 @@ public void writeToParcel(Parcel dest, int flags) { dest.writeInt(this.appId); dest.writeParcelable(this.installOption, flags); dest.writeInt(this.userState.size()); + for (Map.Entry entry : this.userState.entrySet()) { dest.writeValue(entry.getKey()); dest.writeParcelable(entry.getValue(), flags); @@ -142,7 +119,8 @@ protected BPackageSettings(Parcel in) { this.appId = in.readInt(); this.installOption = in.readParcelable(InstallOption.class.getClassLoader()); int userStateSize = in.readInt(); - this.userState = new HashMap(userStateSize); + this.userState = new HashMap<>(userStateSize); + for (int i = 0; i < userStateSize; i++) { Integer key = (Integer) in.readValue(Integer.class.getClassLoader()); BPackageUserState value = in.readParcelable(BPackageUserState.class.getClassLoader()); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageUserState.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageUserState.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageUserState.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageUserState.java index d31339c..167f2bb 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BPackageUserState.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BPackageUserState.java @@ -1,20 +1,12 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import android.os.Parcel; import android.os.Parcelable; -/** - * Created by Milk on 4/27/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BPackageUserState implements Parcelable { public boolean installed; - public boolean stopped; - public boolean hidden; + public final boolean stopped; + public final boolean hidden; public BPackageUserState() { this.installed = false; diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BXposedManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BXposedManagerService.java similarity index 88% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BXposedManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BXposedManagerService.java index 56a9fc5..e3faa00 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/BXposedManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/BXposedManagerService.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; @@ -13,23 +13,15 @@ import java.util.List; import java.util.Map; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.user.BUserHandle; -import top.niunaijun.blackbox.entity.pm.InstalledModule; -import top.niunaijun.blackbox.entity.pm.XposedConfig; -import top.niunaijun.blackbox.utils.CloseUtils; -import top.niunaijun.blackbox.utils.FileUtils; -import top.niunaijun.blackbox.utils.compat.XposedParserCompat; - -/** - * Created by Milk on 5/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.entity.pm.InstalledModule; +import com.vcore.entity.pm.XposedConfig; +import com.vcore.utils.CloseUtils; +import com.vcore.utils.FileUtils; +import com.vcore.utils.compat.XposedParserCompat; + public class BXposedManagerService extends IBXposedManagerService.Stub implements ISystemService, PackageMonitor { private static final BXposedManagerService sService = new BXposedManagerService(); @@ -42,8 +34,7 @@ public static BXposedManagerService get() { return sService; } - public BXposedManagerService() { - } + public BXposedManagerService() { } @Override public void systemReady() { @@ -91,13 +82,16 @@ public List getInstalledModules() { List installedApplications = mPms.getInstalledApplications(PackageManager.GET_META_DATA, BUserHandle.USER_XPOSED); synchronized (mCacheModule) { for (ApplicationInfo installedApplication : installedApplications) { - if (mCacheModule.containsKey(installedApplication.packageName)) + if (mCacheModule.containsKey(installedApplication.packageName)) { continue; + } + InstalledModule installedModule = XposedParserCompat.parseModule(installedApplication); if (installedModule != null) { mCacheModule.put(installedApplication.packageName, installedModule); } } + ArrayList installedModules = new ArrayList<>(mCacheModule.values()); for (InstalledModule installedModule : installedModules) { installedModule.enable = isModuleEnable(installedModule.packageName); @@ -113,6 +107,7 @@ private void loadModuleStateLr() { saveModuleStateLw(); return; } + Parcel parcel = null; try { parcel = FileUtils.readToParcel(xpModuleConf); @@ -130,10 +125,12 @@ private void saveModuleStateLw() { Parcel parcel = Parcel.obtain(); AtomicFile atomicFile = new AtomicFile(BEnvironment.getXPModuleConf()); FileOutputStream fileOutputStream = null; + try { mXposedConfig.writeToParcel(parcel, 0); parcel.setDataPosition(0); fileOutputStream = atomicFile.startWrite(); + FileUtils.writeParcelToOutput(parcel, fileOutputStream); atomicFile.finishWrite(fileOutputStream); } catch (Exception ignored) { @@ -149,9 +146,11 @@ public void onPackageUninstalled(String packageName, boolean removeApp, int user if (userId != BUserHandle.USER_XPOSED && userId != BUserHandle.USER_ALL) { return; } + synchronized (mCacheModule) { mCacheModule.remove(packageName); } + synchronized (mLock) { mXposedConfig.moduleState.remove(packageName); saveModuleStateLw(); @@ -163,9 +162,11 @@ public void onPackageInstalled(String packageName, int userId) { if (userId != BUserHandle.USER_XPOSED && userId != BUserHandle.USER_ALL) { return; } + synchronized (mCacheModule) { mCacheModule.remove(packageName); } + synchronized (mLock) { mXposedConfig.moduleState.put(packageName, false); saveModuleStateLw(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/ComponentResolver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/ComponentResolver.java new file mode 100644 index 0000000..fa38a53 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/ComponentResolver.java @@ -0,0 +1,555 @@ +package com.vcore.core.system.pm; + +import android.content.ComponentName; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.PackageManager; +import android.content.pm.ProviderInfo; +import android.content.pm.ResolveInfo; +import android.content.pm.ServiceInfo; +import android.util.ArrayMap; + +import java.util.ArrayList; +import java.util.List; + +import com.vcore.utils.Slog; + +public class ComponentResolver { + public static final String TAG = "ComponentResolver"; + + private final Object mLock = new Object(); + + /** + * All available activities, for your resolving pleasure. + */ + private final ActivityIntentResolver mActivities = new ActivityIntentResolver(); + + /** + * All available providers, for your resolving pleasure. + */ + private final ProviderIntentResolver mProviders = new ProviderIntentResolver(); + + /** + * All available receivers, for your resolving pleasure. + */ + private final ActivityIntentResolver mReceivers = new ActivityIntentResolver(); + + /** + * All available services, for your resolving pleasure. + */ + private final ServiceIntentResolver mServices = new ServiceIntentResolver(); + /** + * Mapping from provider authority [first directory in content URI codePath) to provider. + */ + private final ArrayMap mProvidersByAuthority = new ArrayMap<>(); + + public ComponentResolver() { } + + void addAllComponents(BPackage pkg) { + final ArrayList newIntents = new ArrayList<>(); + synchronized (mLock) { + addActivitiesLocked(pkg, newIntents); + addServicesLocked(pkg); + addProvidersLocked(pkg); + addReceiversLocked(pkg); + } + } + + void removeAllComponents(BPackage pkg) { + synchronized (mLock) { + removeAllComponentsLocked(pkg); + } + } + + private void removeAllComponentsLocked(BPackage pkg) { + int componentSize; + int i; + + componentSize = pkg.activities.size(); + for (i = 0; i < componentSize; i++) { + BPackage.Activity a = pkg.activities.get(i); + mActivities.removeActivity(a); + } + + componentSize = pkg.providers.size(); + for (i = 0; i < componentSize; i++) { + BPackage.Provider p = pkg.providers.get(i); + mProviders.removeProvider(p); + if (p.info.authority == null) { + // Another content provider with this authority existed when this app was + // installed, so this authority is null. Ignore it as we don't have to + // unregister the provider. + continue; + } + + String[] names = p.info.authority.split(";"); + for (String name : names) { + if (mProvidersByAuthority.get(name) == p) { + mProvidersByAuthority.remove(name); + } + } + mProvidersByAuthority.remove(p.info.authority); + } + + componentSize = pkg.receivers.size(); + for (i = 0; i < componentSize; i++) { + BPackage.Activity a = pkg.receivers.get(i); + mReceivers.removeActivity(a); + } + + componentSize = pkg.services.size(); + for (i = 0; i < componentSize; i++) { + BPackage.Service s = pkg.services.get(i); + mServices.removeService(s); + } + } + + private void addActivitiesLocked(BPackage pkg, List newIntents) { + final int activitiesSize = pkg.activities.size(); + for (int i = 0; i < activitiesSize; i++) { + BPackage.Activity a = pkg.activities.get(i); + a.info.processName = BPackageManagerService.fixProcessName(pkg.applicationInfo.processName, a.info.processName); + mActivities.addActivity(a, "activity", newIntents); + } + } + + private void addProvidersLocked(BPackage pkg) { + final int providersSize = pkg.providers.size(); + for (int i = 0; i < providersSize; i++) { + BPackage.Provider p = pkg.providers.get(i); + p.info.processName = BPackageManagerService.fixProcessName(pkg.applicationInfo.processName, p.info.processName); + mProviders.addProvider(p); + + if (p.info.authority != null) { + String[] names = p.info.authority.split(";"); + p.info.authority = null; + for (String name : names) { + if (!mProvidersByAuthority.containsKey(name)) { + mProvidersByAuthority.put(name, p); + if (p.info.authority == null) { + p.info.authority = name; + } else { + p.info.authority = p.info.authority + ";" + name; + } + } else { + final BPackage.Provider other = mProvidersByAuthority.get(name); + final ComponentName component = (other != null && other.getComponentName() != null) ? other.getComponentName() : null; + final String packageName = component != null ? component.getPackageName() : "?"; + + Slog.w(TAG, "Skipping provider name " + name + " (in package " + pkg.applicationInfo.packageName + ")" + + ": name already used by " + packageName); + } + } + } + } + } + + private void addReceiversLocked(BPackage pkg) { + final int receiversSize = pkg.receivers.size(); + for (int i = 0; i < receiversSize; i++) { + BPackage.Activity a = pkg.receivers.get(i); + a.info.processName = BPackageManagerService.fixProcessName(pkg.applicationInfo.processName, a.info.processName); + mReceivers.addActivity(a, "receiver", null); + } + } + + private void addServicesLocked(BPackage pkg) { + final int servicesSize = pkg.services.size(); + for (int i = 0; i < servicesSize; i++) { + BPackage.Service s = pkg.services.get(i); + s.info.processName = BPackageManagerService.fixProcessName(pkg.applicationInfo.processName, s.info.processName); + mServices.addService(s); + } + } + + /** + * Returns the given activity + */ + BPackage.Activity getActivity(ComponentName component) { + synchronized (mLock) { + return mActivities.mActivities.get(component); + } + } + + /** + * Returns the given provider + */ + BPackage.Provider getProvider(ComponentName component) { + synchronized (mLock) { + return mProviders.mProviders.get(component); + } + } + + /** + * Returns the given receiver + */ + BPackage.Activity getReceiver(ComponentName component) { + synchronized (mLock) { + return mReceivers.mActivities.get(component); + } + } + + /** + * Returns the given service + */ + BPackage.Service getService(ComponentName component) { + synchronized (mLock) { + return mServices.mServices.get(component); + } + } + + List queryActivities(Intent intent, String resolvedType, int flags, int userId) { + synchronized (mLock) { + return mActivities.queryIntent(intent, resolvedType, flags, userId); + } + } + + List queryActivities(Intent intent, String resolvedType, int flags, List activities, int userId) { + synchronized (mLock) { + return mActivities.queryIntentForPackage(intent, resolvedType, flags, activities, userId); + } + } + + List queryProviders(String processName, int flags, int userId) { + List providerList = new ArrayList<>(); + synchronized (mLock) { + for (int i = mProviders.mProviders.size() - 1; i >= 0; --i) { + final BPackage.Provider p = mProviders.mProviders.valueAt(i); + final BPackageSettings ps = p.owner.mExtras; + if (ps == null) { + continue; + } + + if (p.info.authority == null) { + continue; + } + + if (processName != null && (!p.info.processName.equals(processName))) { + continue; + } + // See PM.queryContentProviders()'s javadoc for why we have the metaData parameter. + final ProviderInfo info = PackageManagerCompat.generateProviderInfo(p, flags, ps.readUserState(userId), userId); + if (info == null) { + continue; + } + providerList.add(info); + } + } + return providerList; + } + + ProviderInfo queryProvider(String authority, int flags, int userId) { + synchronized (mLock) { + final BPackage.Provider p = mProvidersByAuthority.get(authority); + if (p == null) { + return null; + } + + BPackageSettings ps = p.owner.mExtras; + return PackageManagerCompat.generateProviderInfo(p, flags, ps.readUserState(userId), userId); + } + } + + List queryReceivers(Intent intent, String resolvedType, int flags, int userId) { + synchronized (mLock) { + return mReceivers.queryIntent(intent, resolvedType, flags, userId); + } + } + + List queryReceivers(Intent intent, String resolvedType, int flags, List receivers, int userId) { + synchronized (mLock) { + return mReceivers.queryIntentForPackage(intent, resolvedType, flags, receivers, userId); + } + } + + List queryServices(Intent intent, String resolvedType, int flags, int userId) { + synchronized (mLock) { + return mServices.queryIntent(intent, resolvedType, flags, userId); + } + } + + List queryServices(Intent intent, String resolvedType, int flags, List services, int userId) { + synchronized (mLock) { + return mServices.queryIntentForPackage(intent, resolvedType, flags, services, userId); + } + } + + private static final class ServiceIntentResolver extends IntentResolver { + + @Override + public List queryIntent(Intent intent, String resolvedType, boolean defaultOnly, int userId) { + mFlags = defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0; + return super.queryIntent(intent, resolvedType, defaultOnly, userId); + } + + List queryIntent(Intent intent, String resolvedType, int flags, int userId) { + mFlags = flags; + return super.queryIntent(intent, resolvedType, (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, userId); + } + + List queryIntentForPackage(Intent intent, String resolvedType, int flags, List packageServices, int userId) { + if (packageServices == null) { + return null; + } + + mFlags = flags; + final boolean defaultOnly = (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0; + final int servicesSize = packageServices.size(); + + ArrayList listCut = new ArrayList<>(servicesSize); + ArrayList intentFilters; + + for (int i = 0; i < servicesSize; ++i) { + intentFilters = packageServices.get(i).intents; + if (intentFilters != null && intentFilters.size() > 0) { + BPackage.ServiceIntentInfo[] array = new BPackage.ServiceIntentInfo[intentFilters.size()]; + intentFilters.toArray(array); + listCut.add(array); + } + } + return super.queryIntentFromList(intent, resolvedType, defaultOnly, listCut, userId); + } + + void addService(BPackage.Service s) { + mServices.put(s.getComponentName(), s); + final int intentsSize = s.intents.size(); + int j; + + for (j = 0; j < intentsSize; j++) { + BPackage.ServiceIntentInfo intent = s.intents.get(j); + addFilter(intent); + } + } + + void removeService(BPackage.Service s) { + mServices.remove(s.getComponentName()); + final int intentsSize = s.intents.size(); + int j; + + for (j = 0; j < intentsSize; j++) { + BPackage.ServiceIntentInfo intent = s.intents.get(j); + removeFilter(intent); + } + } + + @Override + protected boolean isPackageForFilter(String packageName, BPackage.ServiceIntentInfo info) { + return packageName.equals(info.service.owner.packageName); + } + + @Override + protected BPackage.ServiceIntentInfo[] newArray(int size) { + return new BPackage.ServiceIntentInfo[size]; + } + + @Override + protected ResolveInfo newResult(BPackage.ServiceIntentInfo filter, int match, int userId) { + final BPackage.Service service = filter.service; + BPackageSettings ps = service.owner.mExtras; + if (ps == null) { + return null; + } + + ServiceInfo si = PackageManagerCompat.generateServiceInfo(service, mFlags, ps.readUserState(userId), userId); + final ResolveInfo res = new ResolveInfo(); + res.serviceInfo = si; + if ((mFlags & PackageManager.GET_RESOLVED_FILTER) != 0) { + res.filter = filter.intentFilter; + } + + res.priority = filter.intentFilter.getPriority(); + res.preferredOrder = service.owner.mPreferredOrder; + res.match = match; + res.isDefault = filter.hasDefault; + res.labelRes = filter.labelRes; + res.nonLocalizedLabel = filter.nonLocalizedLabel; + res.icon = filter.icon; + return res; + } + + // Keys are String (activity class name), values are Activity. + private final ArrayMap mServices = new ArrayMap<>(); + private int mFlags; + } + + + private static final class ActivityIntentResolver extends IntentResolver { + + @Override + public List queryIntent(Intent intent, String resolvedType, boolean defaultOnly, int userId) { + mFlags = (defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0); + return super.queryIntent(intent, resolvedType, defaultOnly, userId); + } + + List queryIntent(Intent intent, String resolvedType, int flags, int userId) { + mFlags = flags; + return super.queryIntent(intent, resolvedType, (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0, userId); + } + + List queryIntentForPackage(Intent intent, String resolvedType, int flags, List packageActivities, int userId) { + if (packageActivities == null) { + return null; + } + + mFlags = flags; + final boolean defaultOnly = (flags & PackageManager.MATCH_DEFAULT_ONLY) != 0; + final int activitiesSize = packageActivities.size(); + + ArrayList listCut = new ArrayList<>(activitiesSize); + ArrayList intentFilters; + + for (int i = 0; i < activitiesSize; ++i) { + intentFilters = packageActivities.get(i).intents; + if (intentFilters != null && intentFilters.size() > 0) { + BPackage.ActivityIntentInfo[] array = new BPackage.ActivityIntentInfo[intentFilters.size()]; + intentFilters.toArray(array); + listCut.add(array); + } + } + return super.queryIntentFromList(intent, resolvedType, defaultOnly, listCut, userId); + } + + private void addActivity(BPackage.Activity a, String type, List newIntents) { + mActivities.put(a.getComponentName(), a); + final int intentsSize = a.intents.size(); + + for (int j = 0; j < intentsSize; j++) { + BPackage.ActivityIntentInfo intent = a.intents.get(j); + if (newIntents != null && "activity".equals(type)) { + newIntents.add(intent); + } + addFilter(intent); + } + } + + private void removeActivity(BPackage.Activity a) { + mActivities.remove(a.getComponentName()); + final int intentsSize = a.intents.size(); + + for (int j = 0; j < intentsSize; j++) { + BPackage.ActivityIntentInfo intent = a.intents.get(j); + removeFilter(intent); + } + } + + @Override + protected boolean isPackageForFilter(String packageName, BPackage.ActivityIntentInfo info) { + return packageName.equals(info.activity.owner.packageName); + } + + @Override + protected BPackage.ActivityIntentInfo[] newArray(int size) { + return new BPackage.ActivityIntentInfo[size]; + } + + @Override + protected ResolveInfo newResult(BPackage.ActivityIntentInfo info, int match, int userId) { + final BPackage.Activity activity = info.activity; + BPackageSettings ps = activity.owner.mExtras; + if (ps == null) { + return null; + } + + ActivityInfo ai = PackageManagerCompat.generateActivityInfo(activity, mFlags, ps.readUserState(userId), userId); + final ResolveInfo res = new ResolveInfo(); + res.activityInfo = ai; + if ((mFlags & PackageManager.GET_RESOLVED_FILTER) != 0) { + res.filter = info.intentFilter; + } + + res.priority = info.intentFilter.getPriority(); + res.preferredOrder = activity.owner.mPreferredOrder; + res.match = match; + res.isDefault = info.hasDefault; + res.labelRes = info.labelRes; + res.nonLocalizedLabel = info.nonLocalizedLabel; + res.icon = info.icon; + return res; + } + + // Keys are String (activity class name), values are Activity. + private final ArrayMap mActivities = new ArrayMap<>(); + private int mFlags; + } + + private static final class ProviderIntentResolver + extends IntentResolver { + @Override + public List queryIntent(Intent intent, String resolvedType, boolean defaultOnly, int userId) { + mFlags = defaultOnly ? PackageManager.MATCH_DEFAULT_ONLY : 0; + return super.queryIntent(intent, resolvedType, defaultOnly, userId); + } + + void addProvider(BPackage.Provider p) { + mProviders.put(p.getComponentName(), p); + final int intentsSize = p.intents.size(); + int j; + + for (j = 0; j < intentsSize; j++) { + BPackage.ProviderIntentInfo intent = p.intents.get(j); + addFilter(intent); + } + } + + void removeProvider(BPackage.Provider p) { + mProviders.remove(p.getComponentName()); + final int intentsSize = p.intents.size(); + int j; + + for (j = 0; j < intentsSize; j++) { + BPackage.ProviderIntentInfo intent = p.intents.get(j); + removeFilter(intent); + } + } + + @Override + protected boolean allowFilterResult(BPackage.ProviderIntentInfo filter, List dest) { + ProviderInfo filterPi = filter.provider.info; + for (int i = dest.size() - 1; i >= 0; i--) { + ProviderInfo destPi = dest.get(i).providerInfo; + if (destPi.name.equals(filterPi.name) && destPi.packageName.equals(filterPi.packageName)) { + return false; + } + } + return true; + } + + @Override + protected BPackage.ProviderIntentInfo[] newArray(int size) { + return new BPackage.ProviderIntentInfo[size]; + } + + @Override + protected boolean isPackageForFilter(String packageName, BPackage.ProviderIntentInfo info) { + return packageName.equals(info.provider.owner.packageName); + } + + @Override + protected ResolveInfo newResult(BPackage.ProviderIntentInfo filter, int match, int userId) { + final BPackage.Provider provider = filter.provider; + BPackageSettings ps = provider.owner.mExtras; + if (ps == null) { + return null; + } + + ProviderInfo pi = PackageManagerCompat.generateProviderInfo(provider, mFlags, ps.readUserState(userId), userId); + final ResolveInfo res = new ResolveInfo(); + res.providerInfo = pi; + if ((mFlags & PackageManager.GET_RESOLVED_FILTER) != 0) { + res.filter = filter.intentFilter; + } + + res.priority = filter.intentFilter.getPriority(); + res.preferredOrder = provider.owner.mPreferredOrder; + res.match = match; + res.isDefault = filter.hasDefault; + res.labelRes = filter.labelRes; + res.nonLocalizedLabel = filter.nonLocalizedLabel; + res.icon = filter.icon; + return res; + } + + private final ArrayMap mProviders = new ArrayMap<>(); + private int mFlags; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/FastImmutableArraySet.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/FastImmutableArraySet.java new file mode 100644 index 0000000..a5376ec --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/FastImmutableArraySet.java @@ -0,0 +1,65 @@ +package com.vcore.core.system.pm; + +import androidx.annotation.NonNull; + +import java.util.AbstractSet; +import java.util.Iterator; + +/** + * A fast immutable set wrapper for an array that is optimized for non-concurrent iteration. + * The same iterator instance is reused each time to avoid creating lots of garbage. + * Iterating over an array in this fashion is 2.5x faster than iterating over a {@link HashSet} + * so it is worth copying the contents of the set to an array when iterating over it + * hundreds of times. + * @hide + */ +public final class FastImmutableArraySet extends AbstractSet { + FastIterator mIterator; + final T[] mContents; + + public FastImmutableArraySet(T[] contents) { + this.mContents = contents; + } + + @NonNull + @Override + public Iterator iterator() { + FastIterator it = mIterator; + if (it == null) { + it = new FastIterator<>(mContents); + mIterator = it; + } else { + it.mIndex = 0; + } + return it; + } + + @Override + public int size() { + return mContents.length; + } + + private static final class FastIterator implements Iterator { + private final T[] mContents; + int mIndex; + + public FastIterator(T[] contents) { + this.mContents = contents; + } + + @Override + public boolean hasNext() { + return mIndex != mContents.length; + } + + @Override + public T next() { + return mContents[mIndex++]; + } + + @Override + public void remove() { + throw new UnsupportedOperationException(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/IntentResolver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/IntentResolver.java new file mode 100644 index 0000000..dd0f7db --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/IntentResolver.java @@ -0,0 +1,483 @@ +package com.vcore.core.system.pm; + +import android.content.Intent; +import android.content.IntentFilter; +import android.net.Uri; +import android.util.ArrayMap; +import android.util.Log; +import android.util.LogPrinter; + +import java.util.ArrayList; +import java.util.Arrays; +import java.util.Iterator; +import java.util.List; +import java.util.Set; + +import com.vcore.utils.Slog; + +/** + * {@hide} + */ +public abstract class IntentResolver { + final private static String TAG = "IntentResolver"; + final private static boolean DEBUG = false; + final private static boolean localLOGV = DEBUG; + + public void addFilter(F f) { + if (localLOGV) { + Slog.v(TAG, "Adding filter: " + f); + f.intentFilter.dump(new LogPrinter(Log.VERBOSE, TAG), " "); + Slog.v(TAG, " Building Lookup Maps:"); + } + + int numS = register_intent_filter(f, f.intentFilter.schemesIterator(), mSchemeToFilter, " Scheme: "); + int numT = register_mime_types(f); + if (numS == 0 && numT == 0) { + register_intent_filter(f, f.intentFilter.actionsIterator(), mActionToFilter, " Action: "); + } + + if (numT != 0) { + register_intent_filter(f, f.intentFilter.actionsIterator(), + mTypedActionToFilter, " TypedAction: "); + } + } + + public void removeFilter(F f) { + removeFilterInternal(f); + } + + void removeFilterInternal(F f) { + if (localLOGV) { + Slog.v(TAG, "Removing filter: " + f); + f.intentFilter.dump(new LogPrinter(Log.VERBOSE, TAG), " "); + Slog.v(TAG, " Cleaning Lookup Maps:"); + } + + int numS = unregister_intent_filter(f, f.intentFilter.schemesIterator(), mSchemeToFilter, " Scheme: "); + int numT = unregister_mime_types(f); + if (numS == 0 && numT == 0) { + unregister_intent_filter(f, f.intentFilter.actionsIterator(), mActionToFilter, " Action: "); + } + + if (numT != 0) { + unregister_intent_filter(f, f.intentFilter.actionsIterator(), mTypedActionToFilter, " TypedAction: "); + } + } + + public List queryIntentFromList(Intent intent, String resolvedType, boolean defaultOnly, ArrayList listCut, int userId) { + ArrayList resultList = new ArrayList<>(); + final boolean debug = localLOGV || ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); + + FastImmutableArraySet categories = getFastIntentCategories(intent); + final String scheme = intent.getScheme(); + int N = listCut.size(); + + for (int i = 0; i < N; ++i) { + buildResolveList(intent, categories, debug, defaultOnly, resolvedType, scheme, listCut.get(i), resultList, userId); + } + return resultList; + } + + public List queryIntent(Intent intent, String resolvedType, boolean defaultOnly, int userId) { + String scheme = intent.getScheme(); + ArrayList finalList = new ArrayList<>(); + + final boolean debug = localLOGV || ((intent.getFlags() & Intent.FLAG_DEBUG_LOG_RESOLUTION) != 0); + if (debug) { + Slog.v(TAG, "Resolving type=" + resolvedType + " scheme=" + scheme + " defaultOnly=" + defaultOnly + " userId=" + userId + " of " + intent); + } + + F[] firstTypeCut = null; + F[] secondTypeCut = null; + F[] thirdTypeCut = null; + F[] schemeCut = null; + + // If the intent includes a MIME type, then we want to collect all of + // the filters that match that MIME type. + if (resolvedType != null) { + int slashPos = resolvedType.indexOf('/'); + if (slashPos > 0) { + final String baseType = resolvedType.substring(0, slashPos); + if (!baseType.equals("*")) { + if (resolvedType.length() != slashPos + 2 || resolvedType.charAt(slashPos+1) != '*') { + // Not a wild card, so we can just look for all filters that + // completely match or wildcards whose base type matches. + firstTypeCut = mTypeToFilter.get(resolvedType); + } else { + // We can match anything with our base type. + firstTypeCut = mBaseTypeToFilter.get(baseType); + } + + if (debug) { + Slog.v(TAG, "First type cut: " + Arrays.toString(firstTypeCut)); + } + + secondTypeCut = mWildTypeToFilter.get(baseType); + if (debug) { + Slog.v(TAG, "Second type cut: " + Arrays.toString(secondTypeCut)); + } + // Any */* types always apply, but we only need to do this + // if the intent type was not already */*. + thirdTypeCut = mWildTypeToFilter.get("*"); + if (debug) { + Slog.v(TAG, "Third type cut: " + Arrays.toString(thirdTypeCut)); + } + } else if (intent.getAction() != null) { + // The intent specified any type ({@literal *}/*). This + // can be a whole heck of a lot of things, so as a first + // cut let's use the action instead. + firstTypeCut = mTypedActionToFilter.get(intent.getAction()); + if (debug) { + Slog.v(TAG, "Typed Action list: " + Arrays.toString(firstTypeCut)); + } + } + } + } + + // If the intent includes a data URI, then we want to collect all of + // the filters that match its scheme (we will further refine matches + // on the authority and path by directly matching each resulting filter). + if (scheme != null) { + schemeCut = mSchemeToFilter.get(scheme); + if (debug) { + Slog.v(TAG, "Scheme list: " + Arrays.toString(schemeCut)); + } + } + + // If the intent does not specify any data -- either a MIME type or + // a URI -- then we will only be looking for matches against empty + // data. + if (resolvedType == null && scheme == null && intent.getAction() != null) { + firstTypeCut = mActionToFilter.get(intent.getAction()); + if (debug) { + Slog.v(TAG, "Action list: " + Arrays.toString(firstTypeCut)); + } + } + + FastImmutableArraySet categories = getFastIntentCategories(intent); + if (firstTypeCut != null) { + buildResolveList(intent, categories, debug, defaultOnly, resolvedType, scheme, firstTypeCut, finalList, userId); + } + + if (secondTypeCut != null) { + buildResolveList(intent, categories, debug, defaultOnly, resolvedType, scheme, secondTypeCut, finalList, userId); + } + + if (thirdTypeCut != null) { + buildResolveList(intent, categories, debug, defaultOnly, resolvedType, scheme, thirdTypeCut, finalList, userId); + } + + if (schemeCut != null) { + buildResolveList(intent, categories, debug, defaultOnly, resolvedType, scheme, schemeCut, finalList, userId); + } + + if (debug) { + Slog.v(TAG, "Final result list:"); + for (int i=0; i dest) { + return true; + } + + /** + * Returns whether this filter is owned by this package. This must be + * implemented to provide correct filtering of Intents that have + * specified a package name they are to be delivered to. + */ + protected abstract boolean isPackageForFilter(String packageName, F filter); + + protected abstract F[] newArray(int size); + + @SuppressWarnings("unchecked") + protected R newResult(F filter, int match, int userId) { + return (R)filter; + } + + private void addFilter(ArrayMap map, String name, F filter) { + F[] array = map.get(name); + if (array == null) { + array = newArray(2); + map.put(name, array); + array[0] = filter; + } else { + final int N = array.length; + int i = N; + while (i > 0 && array[i-1] == null) { + i--; + } + + if (i < N) { + array[i] = filter; + } else { + F[] newArray = newArray((N*3)/2); + System.arraycopy(array, 0, newArray, 0, N); + newArray[N] = filter; + map.put(name, newArray); + } + } + } + + private int register_mime_types(F filter) { + final Iterator i = filter.intentFilter.typesIterator(); + if (i == null) { + return 0; + } + + int num = 0; + while (i.hasNext()) { + String name = i.next(); + num++; + + if (localLOGV) { + Slog.v(TAG, " Type: " + name); + } + + String baseName = name; + final int slashPos = name.indexOf('/'); + if (slashPos > 0) { + baseName = name.substring(0, slashPos).intern(); + } else { + name = name + "/*"; + } + + addFilter(mTypeToFilter, name, filter); + if (slashPos > 0) { + addFilter(mBaseTypeToFilter, baseName, filter); + } else { + addFilter(mWildTypeToFilter, baseName, filter); + } + } + return num; + } + + private int unregister_mime_types(F filter) { + final Iterator i = filter.intentFilter.typesIterator(); + if (i == null) { + return 0; + } + + int num = 0; + while (i.hasNext()) { + String name = i.next(); + num++; + + if (localLOGV) { + Slog.v(TAG, " Type: " + name); + } + + String baseName = name; + final int slashPos = name.indexOf('/'); + if (slashPos > 0) { + baseName = name.substring(0, slashPos).intern(); + } else { + name = name + "/*"; + } + + remove_all_objects(mTypeToFilter, name, filter); + if (slashPos > 0) { + remove_all_objects(mBaseTypeToFilter, baseName, filter); + } else { + remove_all_objects(mWildTypeToFilter, baseName, filter); + } + } + return num; + } + + private int register_intent_filter(F filter, Iterator i, ArrayMap dest, String prefix) { + if (i == null) { + return 0; + } + + int num = 0; + while (i.hasNext()) { + String name = i.next(); + num++; + + if (localLOGV) { + Slog.v(TAG, prefix + name); + } + addFilter(dest, name, filter); + } + return num; + } + + private int unregister_intent_filter(F filter, Iterator i, ArrayMap dest, String prefix) { + if (i == null) { + return 0; + } + + int num = 0; + while (i.hasNext()) { + String name = i.next(); + num++; + + if (localLOGV) { + Slog.v(TAG, prefix + name); + } + remove_all_objects(dest, name, filter); + } + return num; + } + + private void remove_all_objects(ArrayMap map, String name, Object object) { + F[] array = map.get(name); + if (array != null) { + int LAST = array.length-1; + while (LAST >= 0 && array[LAST] == null) { + LAST--; + } + + for (int idx=LAST; idx>=0; idx--) { + if (array[idx] == object) { + final int remain = LAST - idx; + if (remain > 0) { + System.arraycopy(array, idx+1, array, idx, remain); + } + + array[LAST] = null; + LAST--; + } + } + + if (LAST < 0) { + map.remove(name); + } else if (LAST < (array.length/2)) { + F[] newArray = newArray(LAST+2); + System.arraycopy(array, 0, newArray, 0, LAST+1); + map.put(name, newArray); + } + } + } + + private static FastImmutableArraySet getFastIntentCategories(Intent intent) { + final Set categories = intent.getCategories(); + if (categories == null) { + return null; + } + return new FastImmutableArraySet<>(categories.toArray(new String[0])); + } + + private void buildResolveList(Intent intent, FastImmutableArraySet categories, boolean debug, boolean defaultOnly, String resolvedType, String scheme, + F[] src, List dest, int userId) { + final String action = intent.getAction(); + final Uri data = intent.getData(); + final String packageName = intent.getPackage(); + + final int N = src != null ? src.length : 0; + boolean hasNonDefaults = false; + int i; + F filter; + + for (i = 0; i < N && (filter = src[i]) != null; i++) { + int match; + if (debug) { + Slog.v(TAG, "Matching against filter " + filter); + } + + // Is delivery being limited to filters owned by a particular package? + if (packageName != null && !isPackageForFilter(packageName, filter)) { + if (debug) { + Slog.v(TAG, " Filter is not from package " + packageName + "; skipping"); + } + continue; + } + + // Do we already have this one? + if (!allowFilterResult(filter, dest)) { + if (debug) { + Slog.v(TAG, " Filter's target already added"); + } + continue; + } + + match = filter.intentFilter.match(action, resolvedType, scheme, data, categories, TAG); + if (match >= 0) { + if (debug) { + Slog.v(TAG, " Filter matched! match=0x" + Integer.toHexString(match) + " hasDefault=" + + filter.intentFilter.hasCategory(Intent.CATEGORY_DEFAULT)); + } + + if (!defaultOnly || filter.intentFilter.hasCategory(Intent.CATEGORY_DEFAULT)) { + final R oneResult = newResult(filter, match, userId); + if (debug) { + Slog.v(TAG, " Created result: " + oneResult); + } + + if (oneResult != null) { + dest.add(oneResult); + } + } else { + hasNonDefaults = true; + } + } else { + if (debug) { + String reason; + switch (match) { + case IntentFilter.NO_MATCH_ACTION: reason = "action"; break; + case IntentFilter.NO_MATCH_CATEGORY: reason = "category"; break; + case IntentFilter.NO_MATCH_DATA: reason = "data"; break; + case IntentFilter.NO_MATCH_TYPE: reason = "type"; break; + default: reason = "unknown reason"; break; + } + Slog.v(TAG, " Filter did not match: " + reason); + } + } + } + + if (debug && hasNonDefaults) { + if (dest.size() == 0) { + Slog.v(TAG, "resolveIntent failed: found match, but none with CATEGORY_DEFAULT"); + } else if (dest.size() > 1) { + Slog.v(TAG, "resolveIntent: multiple matches, only some with CATEGORY_DEFAULT"); + } + } + } + + /** + * All of the MIME types that have been registered, such as "image/jpeg", + * "image/*", or "{@literal *}/*". + */ + private final ArrayMap mTypeToFilter = new ArrayMap<>(); + + /** + * The base names of all of all fully qualified MIME types that have been + * registered, such as "image" or "*". Wild card MIME types such as + * "image/*" will not be here. + */ + private final ArrayMap mBaseTypeToFilter = new ArrayMap<>(); + + /** + * The base names of all of the MIME types with a sub-type wildcard that + * have been registered. For example, a filter with "image/*" will be + * included here as "image" but one with "image/jpeg" will not be + * included here. This also includes the "*" for the "{@literal *}/*" + * MIME type. + */ + private final ArrayMap mWildTypeToFilter = new ArrayMap<>(); + + /** + * All of the URI schemes (such as http) that have been registered. + */ + private final ArrayMap mSchemeToFilter = new ArrayMap<>(); + + /** + * All of the actions that have been registered, but only those that did + * not specify data. + */ + private final ArrayMap mActionToFilter = new ArrayMap<>(); + + /** + * All of the actions that have been registered and specified a MIME type. + */ + private final ArrayMap mTypedActionToFilter = new ArrayMap<>(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageManagerCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageManagerCompat.java new file mode 100644 index 0000000..7e8c444 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageManagerCompat.java @@ -0,0 +1,385 @@ +package com.vcore.core.system.pm; + +import android.annotation.SuppressLint; +import android.content.Context; +import android.content.pm.ActivityInfo; +import android.content.pm.ApplicationInfo; +import android.content.pm.ConfigurationInfo; +import android.content.pm.FeatureInfo; +import android.content.pm.InstrumentationInfo; +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; +import android.content.pm.PermissionInfo; +import android.content.pm.ProviderInfo; +import android.content.pm.ServiceInfo; +import android.content.res.AssetManager; +import android.content.res.Resources; +import android.os.Build; + +import java.util.HashSet; +import java.util.Set; + +import black.android.content.pm.ApplicationInfoL; +import black.android.content.pm.ApplicationInfoN; +import black.android.content.pm.SigningInfo; +import com.vcore.BlackBoxCore; +import com.vcore.core.env.AppSystemEnv; +import com.vcore.core.env.BEnvironment; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.ArrayUtils; +import com.vcore.utils.FileUtils; +import com.vcore.utils.compat.BuildCompat; + +@SuppressLint({"SdCardPath", "NewApi"}) +public class PackageManagerCompat { + public static PackageInfo generatePackageInfo(BPackageSettings ps, int flags, BPackageUserState state, int userId) { + if (ps == null) { + return null; + } + + BPackage p = ps.pkg; + if (p != null) { + PackageInfo packageInfo = null; + try { + packageInfo = generatePackageInfo(p, flags, 0, 0, state, userId); + } catch (Throwable ignored) { } + return packageInfo; + } + return null; + } + + public static PackageInfo generatePackageInfo(BPackage p, int flags, long firstInstallTime, long lastUpdateTime, BPackageUserState state, int userId) { + if (checkUseInstalledOrHidden(state, p.applicationInfo)) { + return null; + } + + PackageInfo pi = new PackageInfo(); + pi.packageName = p.packageName; + pi.versionCode = p.mVersionCode; + pi.versionName = p.mVersionName; + pi.sharedUserId = p.mSharedUserId; + pi.sharedUserLabel = p.mSharedUserLabel; + pi.applicationInfo = generateApplicationInfo(p, flags, state, userId); + + pi.firstInstallTime = firstInstallTime; + pi.lastUpdateTime = lastUpdateTime; + if (!p.requestedPermissions.isEmpty()) { + String[] requestedPermissions = new String[p.requestedPermissions.size()]; + p.requestedPermissions.toArray(requestedPermissions); + pi.requestedPermissions = requestedPermissions; + } + + if ((flags & PackageManager.GET_GIDS) != 0) { + pi.gids = new int[]{}; + } + + if ((flags & PackageManager.GET_CONFIGURATIONS) != 0) { + int N = p.configPreferences != null ? p.configPreferences.size() : 0; + if (N > 0) { + pi.configPreferences = new ConfigurationInfo[N]; + p.configPreferences.toArray(pi.configPreferences); + } + + N = p.reqFeatures != null ? p.reqFeatures.size() : 0; + if (N > 0) { + pi.reqFeatures = new FeatureInfo[N]; + p.reqFeatures.toArray(pi.reqFeatures); + } + } + + if ((flags & PackageManager.GET_ACTIVITIES) != 0) { + pi.activities = null; + final int N = p.activities.size(); + + if (N > 0) { + int num = 0; + final ActivityInfo[] res = new ActivityInfo[N]; + for (int i = 0; i < N; i++) { + final BPackage.Activity a = p.activities.get(i); + res[num++] = generateActivityInfo(a, flags, state, userId); + } + + pi.activities = ArrayUtils.trimToSize(res, num); + } + } + + if ((flags & PackageManager.GET_RECEIVERS) != 0) { + pi.receivers = null; + final int N = p.receivers.size(); + + if (N > 0) { + int num = 0; + final ActivityInfo[] res = new ActivityInfo[N]; + for (int i = 0; i < N; i++) { + final BPackage.Activity a = p.receivers.get(i); + res[num++] = generateActivityInfo(a, flags, state, userId); + } + + pi.receivers = ArrayUtils.trimToSize(res, num); + } + } + + if ((flags & PackageManager.GET_SERVICES) != 0) { + pi.services = null; + final int N = p.services.size(); + if (N > 0) { + int num = 0; + final ServiceInfo[] res = new ServiceInfo[N]; + for (int i = 0; i < N; i++) { + final BPackage.Service s = p.services.get(i); + res[num++] = generateServiceInfo(s, flags, state, userId); + } + + pi.services = ArrayUtils.trimToSize(res, num); + } + } + + if ((flags & PackageManager.GET_PROVIDERS) != 0) { + pi.providers = null; + final int N = p.providers.size(); + + if (N > 0) { + int num = 0; + final ProviderInfo[] res = new ProviderInfo[N]; + for (int i = 0; i < N; i++) { + final BPackage.Provider pr = p.providers.get(i); + ProviderInfo providerInfo = generateProviderInfo(pr, flags, state, userId); + if (providerInfo != null) { + res[num++] = providerInfo; + } + } + + pi.providers = ArrayUtils.trimToSize(res, num); + } + } + + if ((flags & PackageManager.GET_INSTRUMENTATION) != 0) { + pi.instrumentation = null; + int N = p.instrumentation.size(); + if (N > 0) { + pi.instrumentation = new InstrumentationInfo[N]; + for (int i = 0; i < N; i++) { + pi.instrumentation[i] = generateInstrumentationInfo(p.instrumentation.get(i), flags); + } + } + } + + if ((flags & PackageManager.GET_PERMISSIONS) != 0) { + pi.permissions = null; + int N = p.permissions.size(); + if (N > 0) { + pi.permissions = new PermissionInfo[N]; + for (int i = 0; i < N; i++) { + pi.permissions[i] = generatePermissionInfo(p.permissions.get(i), flags); + } + } + + pi.requestedPermissions = null; + N = p.requestedPermissions.size(); + if (N > 0) { + pi.requestedPermissions = new String[N]; + pi.requestedPermissionsFlags = new int[N]; + for (int i = 0; i < N; i++) { + final String perm = p.requestedPermissions.get(i); + pi.requestedPermissions[i] = perm; + } + } + } + + PackageInfo base = null; + try { + base = BlackBoxCore.getPackageManager().getPackageInfo(p.packageName, flags); + } catch (PackageManager.NameNotFoundException ignored) { } + if (base != null) { + if (base.splitNames != null) { + pi.splitNames = base.splitNames; + } + } + + if ((flags & PackageManager.GET_SIGNATURES) != 0) { + if (base == null) { + pi.signatures = p.mSignatures; + } else { + pi.signatures = base.signatures; + } + } + + if (BuildCompat.isPie()) { + if ((flags & PackageManager.GET_SIGNING_CERTIFICATES) != 0) { + if (base == null) { + black.android.content.pm.PackageParser.SigningDetails.signatures.set(null, p.mSigningDetails.signatures); + pi.signingInfo = SigningInfo._new.newInstance(); + } else { + pi.signingInfo = base.signingInfo; + } + } + } + return pi; + } + + public static ActivityInfo generateActivityInfo(BPackage.Activity a, int flags, BPackageUserState state, int userId) { + if (checkUseInstalledOrHidden(state, a.info.applicationInfo)) { + return null; + } + // Make shallow copies so we can store the metadata safely + ActivityInfo ai = new ActivityInfo(a.info); + ai.metaData = a.metaData; + ai.processName = BPackageManagerService.fixProcessName(ai.packageName, ai.processName); + ai.applicationInfo = generateApplicationInfo(a.owner, flags, state, userId); + return ai; + } + + public static ServiceInfo generateServiceInfo(BPackage.Service s, int flags, BPackageUserState state, int userId) { + if (checkUseInstalledOrHidden(state, s.info.applicationInfo)) { + return null; + } + // Make shallow copies so we can store the metadata safely + ServiceInfo si = new ServiceInfo(s.info); + si.metaData = s.metaData; + si.processName = BPackageManagerService.fixProcessName(si.packageName, si.processName); + si.applicationInfo = generateApplicationInfo(s.owner, flags, state, userId); + return si; + } + + public static ProviderInfo generateProviderInfo(BPackage.Provider p, int flags, BPackageUserState state, int userId) { + if (checkUseInstalledOrHidden(state, p.info.applicationInfo)) { + return null; + } + // Make shallow copies so we can store the metadata safely + ProviderInfo pi = new ProviderInfo(p.info); + if (pi.authority == null) { + return null; + } + + pi.metaData = p.metaData; + pi.processName = BPackageManagerService.fixProcessName(pi.packageName, pi.processName); + if ((flags & PackageManager.GET_URI_PERMISSION_PATTERNS) == 0) { + pi.uriPermissionPatterns = null; + } + pi.applicationInfo = generateApplicationInfo(p.owner, flags, state, userId); + return pi; + } + + public static PermissionInfo generatePermissionInfo(BPackage.Permission p, int flags) { + if (p == null) { + return null; + } + + if ((flags & PackageManager.GET_META_DATA) == 0) { + return p.info; + } + PermissionInfo pi = new PermissionInfo(p.info); + pi.metaData = p.metaData; + return pi; + } + + public static InstrumentationInfo generateInstrumentationInfo(BPackage.Instrumentation i, int flags) { + if (i == null) { + return null; + } + + if ((flags & PackageManager.GET_META_DATA) == 0) { + return i.info; + } + InstrumentationInfo ii = new InstrumentationInfo(i.info); + ii.metaData = i.metaData; + return ii; + } + + public static ApplicationInfo generateApplicationInfo(BPackage p, int flags, BPackageUserState state, int userId) { + if (checkUseInstalledOrHidden(state, p.applicationInfo)) { + return null; + } + + ApplicationInfo baseApplication; + try { + baseApplication = BlackBoxCore.getPackageManager().getApplicationInfo(BlackBoxCore.getHostPkg(), flags); + } catch (Exception e) { + return null; + } + + String sourceDir = p.baseCodePath; + if (p.applicationInfo == null) { + p.applicationInfo = BlackBoxCore.getPackageManager().getPackageArchiveInfo(sourceDir, 0).applicationInfo; + } + + ApplicationInfo ai = new ApplicationInfo(p.applicationInfo); + if ((flags & PackageManager.GET_META_DATA) != 0) { + ai.metaData = p.mAppMetaData; + } + + ai.dataDir = BEnvironment.getDataDir(ai.packageName, userId).getAbsolutePath(); + if (!p.installOption.isFlag(InstallOption.FLAG_SYSTEM)) { + ai.nativeLibraryDir = BEnvironment.getAppLibDir(ai.packageName).getAbsolutePath(); + } + ai.processName = BPackageManagerService.fixProcessName(p.packageName, ai.packageName); + ai.publicSourceDir = sourceDir; + ai.sourceDir = sourceDir; + ai.uid = p.mExtras.appId; + + if (BuildCompat.isL()) { + ApplicationInfoL.primaryCpuAbi.set(ai, Build.CPU_ABI); + ApplicationInfoL.scanPublicSourceDir.set(ai, ApplicationInfoL.scanPublicSourceDir.get(baseApplication)); + ApplicationInfoL.scanSourceDir.set(ai, ApplicationInfoL.scanSourceDir.get(baseApplication)); + } + + if (Build.VERSION.SDK_INT <= Build.VERSION_CODES.N) { + ai.deviceProtectedDataDir = BEnvironment.getDeDataDir(p.packageName, userId).getAbsolutePath(); + + if (ApplicationInfoN.deviceProtectedDataDir != null) { + ApplicationInfoN.deviceProtectedDataDir.set(ai, ai.deviceProtectedDataDir); + } + + if (ApplicationInfoN.credentialEncryptedDataDir != null) { + ApplicationInfoN.credentialEncryptedDataDir.set(ai, ai.dataDir); + } + + if (ApplicationInfoN.deviceProtectedDataDir != null) { + ApplicationInfoN.deviceProtectedDataDir.set(ai, ai.deviceProtectedDataDir); + } + + if (ApplicationInfoN.credentialProtectedDataDir != null) { + ApplicationInfoN.credentialProtectedDataDir.set(ai, ai.dataDir); + } + } + fixJar(ai); + return ai; + } + + private static boolean checkUseInstalledOrHidden(BPackageUserState state, ApplicationInfo appInfo) { + if (AppSystemEnv.isBlackPackage(appInfo.packageName)) { + return true; + } + // Returns false if the package is hidden system app until installed. + return !state.installed || state.hidden; + } + + private static void fixJar(ApplicationInfo info) { + String APACHE_LEGACY_JAR = "/system/framework/org.apache.http.legacy.boot.jar"; + String APACHE_LEGACY_JAR_Q = "/system/framework/org.apache.http.legacy.jar"; + Set sharedLibraryFileList = new HashSet<>(); + + if (BuildCompat.isQ()) { + if (!FileUtils.isExist(APACHE_LEGACY_JAR_Q)) { + sharedLibraryFileList.add(APACHE_LEGACY_JAR); + } else { + sharedLibraryFileList.add(APACHE_LEGACY_JAR_Q); + } + } else { + sharedLibraryFileList.add(APACHE_LEGACY_JAR); + } + info.sharedLibraryFiles = sharedLibraryFileList.toArray(new String[]{}); + } + + public static Resources getResources(Context context, ApplicationInfo appInfo) { + BPackageSettings ps = BPackageManagerService.get().getBPackageSetting(appInfo.packageName); + if (ps != null) { + AssetManager assets = black.android.content.res.AssetManager._new.newInstance(); + black.android.content.res.AssetManager.addAssetPath.call(assets, ps.pkg.baseCodePath); + + Resources hostRes = context.getResources(); + return new Resources(assets, hostRes.getDisplayMetrics(), hostRes.getConfiguration()); + } + return null; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageMonitor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageMonitor.java new file mode 100644 index 0000000..6077769 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/PackageMonitor.java @@ -0,0 +1,7 @@ +package com.vcore.core.system.pm; + +public interface PackageMonitor { + void onPackageUninstalled(String packageName, boolean isRemove, int userId); + + void onPackageInstalled(String packageName, int userId); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/Settings.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/Settings.java new file mode 100644 index 0000000..c55b279 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/Settings.java @@ -0,0 +1,246 @@ +package com.vcore.core.system.pm; + +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; +import android.content.pm.PackageParser; +import android.os.Parcel; +import android.os.Process; +import android.util.ArrayMap; +import android.util.AtomicFile; + +import java.io.File; +import java.io.FileOutputStream; +import java.util.HashMap; +import java.util.HashSet; +import java.util.Map; +import java.util.Set; + +import com.vcore.BlackBoxCore; +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.BProcessManagerService; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.PackageParserCompat; + +/*public*/ class Settings { + public static final String TAG = "Settings"; + + final ArrayMap mPackages = new ArrayMap<>(); + private final Map mAppIds = new HashMap<>(); + private final Map mSharedUsers = SharedUserSetting.sSharedUsers; + private int mCurrUid = 0; + + public Settings() { + synchronized (mPackages) { + loadUidLP(); + SharedUserSetting.loadSharedUsers(); + } + } + + BPackageSettings getPackageLPw(String name, PackageParser.Package aPackage, InstallOption installOption) { + BPackageSettings pkgSettings; + BPackageSettings origSettings = new BPackageSettings(); + origSettings.pkg = new BPackage(aPackage); + origSettings.pkg.installOption = installOption; + origSettings.installOption = installOption; + origSettings.pkg.mExtras = origSettings; + origSettings.pkg.applicationInfo = PackageManagerCompat.generateApplicationInfo(origSettings.pkg, 0, BPackageUserState.create(), 0); + + synchronized (mPackages) { + pkgSettings = mPackages.get(name); + if (pkgSettings != null) { + origSettings.appId = pkgSettings.appId; + origSettings.userState = pkgSettings.userState; + } else { + boolean b = registerAppIdLPw(origSettings); + if (!b) { + throw new RuntimeException("registerAppIdLPw err."); + } + } + } + return origSettings; + } + + boolean registerAppIdLPw(BPackageSettings p) { + boolean createdNew; + String sharedUserId = p.pkg.mSharedUserId; + SharedUserSetting sharedUserSetting = null; + + if (sharedUserId != null) { + sharedUserSetting = mSharedUsers.get(sharedUserId); + if (sharedUserSetting == null) { + sharedUserSetting = new SharedUserSetting(sharedUserId); + sharedUserSetting.userId = acquireAndRegisterNewAppIdLPw(p); + mSharedUsers.put(sharedUserId, sharedUserSetting); + } + } + + if (sharedUserSetting != null) { + p.appId = sharedUserSetting.userId; + Slog.d(TAG, p.pkg.packageName + " sharedUserId = " + sharedUserId + ", setAppId = " + p.appId); + } + + if (p.appId == 0) { + // Assign new user ID + p.appId = acquireAndRegisterNewAppIdLPw(p); + } + createdNew = p.appId >= 0; + saveUidLP(); + SharedUserSetting.saveSharedUsers(); + return createdNew; + } + + private int acquireAndRegisterNewAppIdLPw(BPackageSettings obj) { + // Let's be stupidly inefficient for now... + Integer integer = mAppIds.get(obj.pkg.packageName); + if (integer != null) { + return integer; + } + + if (mCurrUid >= Process.LAST_APPLICATION_UID) { + return -1; + } + mCurrUid++; + mAppIds.put(obj.pkg.packageName, mCurrUid); + return Process.FIRST_APPLICATION_UID + mCurrUid; + } + + private void saveUidLP() { + Parcel parcel = Parcel.obtain(); + FileOutputStream fileOutputStream = null; + AtomicFile atomicFile = new AtomicFile(BEnvironment.getUidConf()); + + try { + Set pkgName = mPackages.keySet(); + for (String s : new HashSet<>(mAppIds.keySet())) { + if (!pkgName.contains(s)) { + mAppIds.remove(s); + } + } + parcel.writeInt(mCurrUid); + parcel.writeMap(mAppIds); + + fileOutputStream = atomicFile.startWrite(); + FileUtils.writeParcelToOutput(parcel, fileOutputStream); + atomicFile.finishWrite(fileOutputStream); + } catch (Exception e) { + e.printStackTrace(); + atomicFile.failWrite(fileOutputStream); + } finally { + parcel.recycle(); + } + } + + private void loadUidLP() { + Parcel parcel = Parcel.obtain(); + try { + byte[] uidBytes = FileUtils.toByteArray(BEnvironment.getUidConf()); + parcel.unmarshall(uidBytes, 0, uidBytes.length); + parcel.setDataPosition(0); + + mCurrUid = parcel.readInt(); + HashMap hashMap = parcel.readHashMap(HashMap.class.getClassLoader()); + synchronized (mAppIds) { + mAppIds.clear(); + mAppIds.putAll(hashMap); + } + } catch (Exception e) { + // e.printStackTrace(); + } finally { + parcel.recycle(); + } + } + + public void scanPackage() { + synchronized (mPackages) { + File appRootDir = BEnvironment.getAppRootDir(); + FileUtils.mkdirs(appRootDir); + File[] apps = appRootDir.listFiles(); + + if (apps != null) { + for (File app : apps) { + if (!app.isDirectory()) { + continue; + } + scanPackage(app.getName()); + } + } + } + } + + public void scanPackage(String packageName) { + synchronized (mPackages) { + updatePackageLP(BEnvironment.getAppDir(packageName)); + } + } + + private void updatePackageLP(File app) { + String packageName = app.getName(); + Parcel packageSettingsIn = Parcel.obtain(); + File packageConf = BEnvironment.getPackageConf(packageName); + + try { + byte[] bPackageSettingsBytes = FileUtils.toByteArray(packageConf); + + packageSettingsIn.unmarshall(bPackageSettingsBytes, 0, bPackageSettingsBytes.length); + packageSettingsIn.setDataPosition(0); + + BPackageSettings bPackageSettings = new BPackageSettings(packageSettingsIn); + bPackageSettings.pkg.mExtras = bPackageSettings; + if (bPackageSettings.installOption.isFlag(InstallOption.FLAG_SYSTEM)) { + PackageInfo packageInfo = BlackBoxCore.getPackageManager().getPackageInfo(packageName, PackageManager.GET_META_DATA); + String currPackageSourcePath = packageInfo.applicationInfo.sourceDir; + if (!currPackageSourcePath.equals(bPackageSettings.pkg.baseCodePath)) { + BProcessManagerService.get().killAllByPackageName(bPackageSettings.pkg.packageName); + BPackageSettings newPkg = reInstallBySystem(packageInfo, bPackageSettings.installOption); + bPackageSettings.pkg = newPkg.pkg; + } + } else { + bPackageSettings.pkg.applicationInfo = PackageManagerCompat.generateApplicationInfo(bPackageSettings.pkg, 0, BPackageUserState.create(), 0); + } + + bPackageSettings.save(); + mPackages.put(bPackageSettings.pkg.packageName, bPackageSettings); + Slog.d(TAG, "Loaded package: " + packageName); + } catch (Throwable e) { + e.printStackTrace(); + + FileUtils.deleteDir(app); + removePackage(packageName); + BProcessManagerService.get().killAllByPackageName(packageName); + BPackageManagerService.get().onPackageUninstalled(packageName, true, BUserHandle.USER_ALL); + Slog.d(TAG, "Bad package: " + packageName); + } finally { + packageSettingsIn.recycle(); + } + } + + private BPackageSettings reInstallBySystem(PackageInfo systemPackageInfo, InstallOption option) throws Exception { + Slog.d(TAG, "reInstallBySystem: " + systemPackageInfo.packageName); + PackageParser.Package aPackage = parserApk(systemPackageInfo.applicationInfo.sourceDir); + if (aPackage == null) { + throw new RuntimeException("parser apk error."); + } + + aPackage.applicationInfo = BlackBoxCore.getPackageManager().getPackageInfo(aPackage.packageName, 0).applicationInfo; + return getPackageLPw(aPackage.packageName, aPackage, option); + } + + public void removePackage(String packageName) { + mPackages.remove(packageName); + } + + private PackageParser.Package parserApk(String file) { + try { + PackageParser parser = PackageParserCompat.createParser(); + PackageParser.Package aPackage = PackageParserCompat.parsePackage(parser, new File(file), 0); + PackageParserCompat.collectCertificates(parser, aPackage, 0); + return aPackage; + } catch (Throwable t) { + t.printStackTrace(); + } + return null; + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/SharedUserSetting.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/SharedUserSetting.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/SharedUserSetting.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/SharedUserSetting.java index 695fbaf..4e68d5b 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/pm/SharedUserSetting.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/SharedUserSetting.java @@ -1,20 +1,4 @@ -/* - * Copyright (C) 2011 The Android Open Source Project - * - * Licensed under the Apache License, Version 2.0 (the "License"); - * you may not use this file except in compliance with the License. - * You may obtain a copy of the License at - * - * http://www.apache.org/licenses/LICENSE-2.0 - * - * Unless required by applicable law or agreed to in writing, software - * distributed under the License is distributed on an "AS IS" BASIS, - * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - * See the License for the specific language governing permissions and - * limitations under the License. - */ - -package top.niunaijun.blackbox.core.system.pm; +package com.vcore.core.system.pm; import android.os.Parcel; import android.os.Parcelable; @@ -24,8 +8,8 @@ import java.util.HashMap; import java.util.Map; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.utils.FileUtils; +import com.vcore.core.env.BEnvironment; +import com.vcore.utils.FileUtils; /** * Settings data for a particular shared user ID we know about. @@ -40,21 +24,20 @@ public final class SharedUserSetting implements Parcelable { // that all apps within the sharedUser run in the same selinux context. int seInfoTargetSdkVersion; - SharedUserSetting(String _name) { name = _name; } @Override public String toString() { - return "SharedUserSetting{" + Integer.toHexString(System.identityHashCode(this)) + " " - + name + "/" + userId + "}"; + return "SharedUserSetting{" + Integer.toHexString(System.identityHashCode(this)) + " " + name + "/" + userId + "}"; } public static void saveSharedUsers() { Parcel parcel = Parcel.obtain(); FileOutputStream fileOutputStream = null; AtomicFile atomicFile = new AtomicFile(BEnvironment.getSharedUserConf()); + try { parcel.writeMap(sSharedUsers); @@ -71,6 +54,7 @@ public static void saveSharedUsers() { public static void loadSharedUsers() { Parcel parcel = Parcel.obtain(); + try { byte[] sharedUsersBytes = FileUtils.toByteArray(BEnvironment.getSharedUserConf()); parcel.unmarshall(sharedUsersBytes, 0, sharedUsersBytes.length); @@ -82,7 +66,7 @@ public static void loadSharedUsers() { sSharedUsers.putAll(hashMap); } } catch (Exception e) { -// e.printStackTrace(); + // e.printStackTrace(); } finally { parcel.recycle(); } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CopyExecutor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CopyExecutor.java new file mode 100644 index 0000000..93aa169 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CopyExecutor.java @@ -0,0 +1,45 @@ +package com.vcore.core.system.pm.installer; + +import java.io.File; +import java.io.IOException; + +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; +import com.vcore.utils.NativeUtils; + +public class CopyExecutor implements Executor { + + @Override + public int exec(BPackageSettings ps, InstallOption option, int userId) { + try { + if (!option.isFlag(InstallOption.FLAG_SYSTEM)) { + NativeUtils.copyNativeLib(new File(ps.pkg.baseCodePath), BEnvironment.getAppLibDir(ps.pkg.packageName)); + } + } catch (Exception e) { + e.printStackTrace(); + return -1; + } + if (option.isFlag(InstallOption.FLAG_STORAGE)) { + // 外部安装 + File origFile = new File(ps.pkg.baseCodePath); + File newFile = BEnvironment.getBaseApkDir(ps.pkg.packageName); + try { + if (option.isFlag(InstallOption.FLAG_URI_FILE)) { + boolean b = FileUtils.renameTo(origFile, newFile); + if (!b) { + FileUtils.copyFile(origFile, newFile); + } + } else { + FileUtils.copyFile(origFile, newFile); + } + ps.pkg.baseCodePath = newFile.getAbsolutePath(); + } catch (IOException e) { + e.printStackTrace(); + return -1; + } + } + return 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreatePackageExecutor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreatePackageExecutor.java new file mode 100644 index 0000000..b6d0ad5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreatePackageExecutor.java @@ -0,0 +1,17 @@ +package com.vcore.core.system.pm.installer; + +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; + +public class CreatePackageExecutor implements Executor { + + @Override + public int exec(BPackageSettings ps, InstallOption option, int userId) { + FileUtils.deleteDir(BEnvironment.getAppDir(ps.pkg.packageName)); + FileUtils.mkdirs(BEnvironment.getAppDir(ps.pkg.packageName)); + FileUtils.mkdirs(BEnvironment.getAppLibDir(ps.pkg.packageName)); + return 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreateUserExecutor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreateUserExecutor.java new file mode 100644 index 0000000..8f60ca1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/CreateUserExecutor.java @@ -0,0 +1,22 @@ +package com.vcore.core.system.pm.installer; + +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; + +public class CreateUserExecutor implements Executor { + + @Override + public int exec(BPackageSettings ps, InstallOption option, int userId) { + String packageName = ps.pkg.packageName; + FileUtils.deleteDir(BEnvironment.getDataLibDir(packageName, userId)); + + FileUtils.mkdirs(BEnvironment.getDataDir(packageName, userId)); + FileUtils.mkdirs(BEnvironment.getDataCacheDir(packageName, userId)); + FileUtils.mkdirs(BEnvironment.getDataFilesDir(packageName, userId)); + FileUtils.mkdirs(BEnvironment.getDataDatabasesDir(packageName, userId)); + FileUtils.mkdirs(BEnvironment.getDeDataDir(packageName, userId)); + return 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/Executor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/Executor.java new file mode 100644 index 0000000..ddb8826 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/Executor.java @@ -0,0 +1,10 @@ +package com.vcore.core.system.pm.installer; + +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; + +public interface Executor { + String TAG = "InstallExecutor"; + + int exec(BPackageSettings ps, InstallOption option, int userId); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveAppExecutor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveAppExecutor.java new file mode 100644 index 0000000..4e3578c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveAppExecutor.java @@ -0,0 +1,14 @@ +package com.vcore.core.system.pm.installer; + +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; + +public class RemoveAppExecutor implements Executor { + @Override + public int exec(BPackageSettings ps, InstallOption option, int userId) { + FileUtils.deleteDir(BEnvironment.getAppDir(ps.pkg.packageName)); + return 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveUserExecutor.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveUserExecutor.java new file mode 100644 index 0000000..cec4a2d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/pm/installer/RemoveUserExecutor.java @@ -0,0 +1,19 @@ +package com.vcore.core.system.pm.installer; + +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.entity.pm.InstallOption; +import com.vcore.utils.FileUtils; + +public class RemoveUserExecutor implements Executor { + + @Override + public int exec(BPackageSettings ps, InstallOption option, int userId) { + String packageName = ps.pkg.packageName; + + FileUtils.deleteDir(BEnvironment.getDataDir(packageName, userId)); + FileUtils.deleteDir(BEnvironment.getDeDataDir(packageName, userId)); + FileUtils.deleteDir(BEnvironment.getExternalDataDir(packageName, userId)); + return 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserHandle.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserHandle.java new file mode 100644 index 0000000..4936d4a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserHandle.java @@ -0,0 +1,238 @@ +package com.vcore.core.system.user; + +import android.os.Parcel; +import android.os.Parcelable; +import android.os.Process; + +import androidx.annotation.NonNull; + +/** + * Representation of a user on the device. + */ +public final class BUserHandle implements Parcelable { + // NOTE: keep logic in sync with system/core/libcutils/multiuser.c + + /** + * @hide Range of uids allocated for a user. + */ + public static final int PER_USER_RANGE = 100000; + + /** + * @hide A user id to indicate all users on the device + */ + public static final int USER_ALL = -1; + + /** + * @hide A user handle to indicate all users on the device + */ + public static final BUserHandle ALL = new BUserHandle(USER_ALL); + + /** + * @hide A user id to indicate the currently active user + */ + public static final int USER_CURRENT = -2; + + /** + * @hide A user handle to indicate the current user of the device + */ + public static final BUserHandle CURRENT = new BUserHandle(USER_CURRENT); + + public static final int USER_XPOSED = -4; + + /** + * @hide An undefined user id + */ + public static final int USER_NULL = -10000; + + /** + * @hide A user id constant to indicate the "owner" user of the device + * @deprecated Consider using either {@link BUserHandle#USER_SYSTEM} constant or + * check the target user's flag {@link }. + */ + @Deprecated + public static final int USER_OWNER = 0; + + /** + * @hide A user handle to indicate the primary/owner user of the device + * @deprecated Consider using either {@link BUserHandle#SYSTEM} constant or + * check the target user's flag {@link }. + */ + @Deprecated + public static final BUserHandle OWNER = new BUserHandle(USER_OWNER); + + /** + * @hide A user id constant to indicate the "system" user of the device + */ + public static final int USER_SYSTEM = 0; + + /** + * @hide A user handle to indicate the "system" user of the device + */ + public static final BUserHandle SYSTEM = new BUserHandle(USER_SYSTEM); + + /** + * @hide Enable multi-user related side effects. Set this to false if + * there are problems with single user use-cases. + */ + public static final boolean MU_ENABLED = true; + + /** + * @hide + */ + public static final int AID_APP_START = android.os.Process.FIRST_APPLICATION_UID; + + final int mHandle; + + /** + * Whether a UID belongs to a system core component or not. + * + * @hide + */ + public static boolean isCore(int uid) { + if (uid >= 0) { + final int appId = getAppId(uid); + return appId < Process.FIRST_APPLICATION_UID; + } else { + return false; + } + } + + /** + * Returns the user id for a given uid. + * + * @hide + */ + public static int getUserId(int uid) { + if (MU_ENABLED) { + return uid / PER_USER_RANGE; + } else { + return BUserHandle.USER_SYSTEM; + } + } + + /** + * @hide + */ + public static BUserHandle of(int userId) { + return userId == USER_SYSTEM ? SYSTEM : new BUserHandle(userId); + } + + /** + * Returns the uid that is composed from the userId and the appId. + * + * @hide + */ + public static int getUid(int userId, int appId) { + if (MU_ENABLED) { + return userId * PER_USER_RANGE + (appId % PER_USER_RANGE); + } else { + return appId; + } + } + + /** + * Returns the app id (or base uid) for a given uid, stripping out the user id from it. + * + * @hide + */ + public static int getAppId(int uid) { + return uid % PER_USER_RANGE; + } + + /** + * Returns true if this UserHandle refers to the owner user; false otherwise. + * + * @return true if this UserHandle refers to the owner user; false otherwise. + * @hide + * @deprecated please use {@link #isSystem()} or check for + */ + @Deprecated + public boolean isOwner() { + return this.equals(OWNER); + } + + /** + * @return true if this UserHandle refers to the system user; false otherwise. + * @hide + */ + public boolean isSystem() { + return this.equals(SYSTEM); + } + + /** + * @hide + */ + public BUserHandle(int h) { + this.mHandle = h; + } + + @NonNull + @Override + public String toString() { + return "UserHandle{" + mHandle + "}"; + } + + @Override + public boolean equals(Object obj) { + try { + if (obj instanceof BUserHandle) { + BUserHandle other = (BUserHandle) obj; + return mHandle == other.mHandle; + } + } catch (ClassCastException ignored) { } + return false; + } + + @Override + public int hashCode() { + return mHandle; + } + + public int describeContents() { + return 0; + } + + public void writeToParcel(Parcel out, int flags) { + out.writeInt(mHandle); + } + + /** + * Write a UserHandle to a Parcel, handling null pointers. Must be + * read with {@link #readFromParcel(Parcel)}. + * + * @param h The UserHandle to be written. + * @param out The Parcel in which the UserHandle will be placed. + * @see #readFromParcel(Parcel) + */ + public static void writeToParcel(BUserHandle h, Parcel out) { + if (h != null) { + h.writeToParcel(out, 0); + } else { + out.writeInt(USER_NULL); + } + } + + public static final Parcelable.Creator CREATOR = new Creator() { + public BUserHandle createFromParcel(Parcel in) { + return new BUserHandle(in); + } + + public BUserHandle[] newArray(int size) { + return new BUserHandle[size]; + } + }; + + /** + * Instantiate a new UserHandle from the data in a Parcel that was + * previously written with {@link #writeToParcel(Parcel, int)}. Note that you + * must not use this with data written by + * {@link #writeToParcel(BUserHandle, Parcel)} since it is not possible + * to handle a null UserHandle here. + * + * @param in The Parcel containing the previously written UserHandle, + * positioned at the location in the buffer where it was written. + */ + public BUserHandle(Parcel in) { + this.mHandle = in.readInt(); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserInfo.java similarity index 75% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserInfo.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserInfo.java index 87f5997..e0ca76c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserInfo.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserInfo.java @@ -1,24 +1,15 @@ -package top.niunaijun.blackbox.core.system.user; +package com.vcore.core.system.user; import android.os.Parcel; import android.os.Parcelable; -/** - * Created by Milk on 4/22/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BUserInfo implements Parcelable { public int id; public BUserStatus status; public String name; public long createTime; - BUserInfo() { - } + BUserInfo() { } @Override public int describeContents() { @@ -42,6 +33,7 @@ protected BUserInfo(Parcel in) { } public static final Creator CREATOR = new Creator() { + @Override public BUserInfo createFromParcel(Parcel source) { return new BUserInfo(source); @@ -55,11 +47,6 @@ public BUserInfo[] newArray(int size) { @Override public String toString() { - return "BUserInfo{" + - "id=" + id + - ", status=" + status + - ", name='" + name + '\'' + - ", createTime=" + createTime + - '}'; + return "BUserInfo{" + "id=" + id + ", status=" + status + ", name='" + name + '\'' + ", createTime=" + createTime + '}'; } } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserManagerService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserManagerService.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserManagerService.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserManagerService.java index 2f223a0..7c72f32 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/core/system/user/BUserManagerService.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserManagerService.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.core.system.user; +package com.vcore.core.system.user; import android.os.Parcel; import android.os.RemoteException; @@ -14,22 +14,15 @@ import java.util.HashMap; import java.util.List; -import top.niunaijun.blackbox.core.env.BEnvironment; -import top.niunaijun.blackbox.core.system.ISystemService; -import top.niunaijun.blackbox.core.system.pm.BPackageManagerService; -import top.niunaijun.blackbox.utils.CloseUtils; -import top.niunaijun.blackbox.utils.FileUtils; - -/** - * Created by Milk on 4/22/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.core.env.BEnvironment; +import com.vcore.core.system.ISystemService; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.utils.CloseUtils; +import com.vcore.utils.FileUtils; + + public class BUserManagerService extends IBUserManagerService.Stub implements ISystemService { - private static BUserManagerService sService = new BUserManagerService(); + private static final BUserManagerService sService = new BUserManagerService(); public final HashMap mUsers = new HashMap<>(); public final Object mUserLock = new Object(); @@ -57,7 +50,7 @@ public boolean exists(int userId) { } @Override - public BUserInfo createUser(int userId) throws RemoteException { + public BUserInfo createUser(int userId) { synchronized (mUserLock) { if (exists(userId)) { return getUserInfo(userId); @@ -114,9 +107,11 @@ private void saveUserInfoLocked() { Parcel parcel = Parcel.obtain(); AtomicFile atomicFile = new AtomicFile(BEnvironment.getUserInfoConf()); FileOutputStream fileOutputStream = null; + try { ArrayList bUsers = new ArrayList<>(mUsers.values()); parcel.writeTypedList(bUsers); + try { fileOutputStream = atomicFile.startWrite(); FileUtils.writeParcelToOutput(parcel, fileOutputStream); @@ -136,19 +131,23 @@ private void scanUserL() { synchronized (mUserLock) { Parcel parcel = Parcel.obtain(); InputStream is = null; + try { File userInfoConf = BEnvironment.getUserInfoConf(); if (!userInfoConf.exists()) { return; } + is = new FileInputStream(BEnvironment.getUserInfoConf()); byte[] bytes = FileUtils.toByteArray(is); parcel.unmarshall(bytes, 0, bytes.length); parcel.setDataPosition(0); ArrayList loadUsers = parcel.createTypedArrayList(BUserInfo.CREATOR); - if (loadUsers == null) + if (loadUsers == null) { return; + } + synchronized (mUsers) { mUsers.clear(); for (BUserInfo loadUser : loadUsers) { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserStatus.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserStatus.java new file mode 100644 index 0000000..05d6183 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/core/system/user/BUserStatus.java @@ -0,0 +1,6 @@ +package com.vcore.core.system.user; + +public enum BUserStatus { + ENABLE, DISABLE + +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/AppConfig.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/AppConfig.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/AppConfig.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/AppConfig.java index dc44f22..7c0860a 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/AppConfig.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/AppConfig.java @@ -1,25 +1,16 @@ -package top.niunaijun.blackbox.entity; +package com.vcore.entity; import android.os.IBinder; import android.os.Parcel; import android.os.Parcelable; - -/** - * Created by Milk on 4/1/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class AppConfig implements Parcelable { public static final String KEY = "BlackBox_client_config"; public String packageName; public String processName; - public int bpid; - public int buid; + public int bPID; + public int bUID; public int uid; public int userId; public int callingBUid; @@ -34,22 +25,21 @@ public int describeContents() { public void writeToParcel(Parcel dest, int flags) { dest.writeString(this.packageName); dest.writeString(this.processName); - dest.writeInt(this.bpid); - dest.writeInt(this.buid); + dest.writeInt(this.bPID); + dest.writeInt(this.bUID); dest.writeInt(this.uid); dest.writeInt(this.userId); dest.writeInt(this.callingBUid); dest.writeStrongBinder(token); } - public AppConfig() { - } + public AppConfig() { } protected AppConfig(Parcel in) { this.packageName = in.readString(); this.processName = in.readString(); - this.bpid = in.readInt(); - this.buid = in.readInt(); + this.bPID = in.readInt(); + this.bUID = in.readInt(); this.uid = in.readInt(); this.userId = in.readInt(); this.callingBUid = in.readInt(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/JobRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/JobRecord.java similarity index 85% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/JobRecord.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/JobRecord.java index 015ea0d..3e873a0 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/JobRecord.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/JobRecord.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.entity; +package com.vcore.entity; import android.app.job.JobInfo; import android.app.job.JobService; @@ -6,24 +6,13 @@ import android.os.Parcel; import android.os.Parcelable; - -/** - * Created by Milk on 4/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class JobRecord implements Parcelable { - public JobInfo mJobInfo; public ServiceInfo mServiceInfo; public JobService mJobService; - public JobRecord() { - } + public JobRecord() { } @Override public int describeContents() { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/ServiceRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/ServiceRecord.java similarity index 81% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/ServiceRecord.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/ServiceRecord.java index 83ffbce..ba6d500 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/ServiceRecord.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/ServiceRecord.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.entity; +package com.vcore.entity; import android.app.Service; import android.content.Intent; @@ -9,26 +9,18 @@ import java.util.Map; import java.util.concurrent.atomic.AtomicInteger; -/** - * Created by Milk on 4/7/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class ServiceRecord { private Service mService; - private Map mBounds = new HashMap<>(); + private final Map mBounds = new HashMap<>(); private boolean rebind; private int mStartId; - public class BoundInfo { + public static class BoundInfo { private IBinder mIBinder; - private AtomicInteger mBindCount = new AtomicInteger(0); + private final AtomicInteger mBindCount = new AtomicInteger(0); - public int incrementAndGetBindCount() { - return mBindCount.incrementAndGet(); + public void incrementAndGetBindCount() { + mBindCount.incrementAndGet(); } public int decrementAndGetBindCount() { @@ -77,6 +69,7 @@ public void addBinder(Intent intent, final IBinder iBinder) { boundInfo = new BoundInfo(); mBounds.put(filterComparison, boundInfo); } + boundInfo.setIBinder(iBinder); try { iBinder.linkToDeath(new IBinder.DeathRecipient() { @@ -91,22 +84,19 @@ public void binderDied() { } } - public int incrementAndGetBindCount(Intent intent) { + public void incrementAndGetBindCount(Intent intent) { BoundInfo boundInfo = getOrCreateBoundInfo(intent); - return boundInfo.incrementAndGetBindCount(); + boundInfo.incrementAndGetBindCount(); } public boolean decreaseConnectionCount(Intent intent) { Intent.FilterComparison filterComparison = new Intent.FilterComparison(intent); BoundInfo boundInfo = mBounds.get(filterComparison); - if (boundInfo == null) - return true; - int i = boundInfo.decrementAndGetBindCount(); - if (i <= 0) { -// mBounds.remove(filterComparison); + if (boundInfo == null) { return true; } - return false; + int i = boundInfo.decrementAndGetBindCount(); + return i <= 0; } public BoundInfo getOrCreateBoundInfo(Intent intent) { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/UnbindRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/UnbindRecord.java similarity index 86% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/UnbindRecord.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/UnbindRecord.java index a6e22c0..a866c3b 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/UnbindRecord.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/UnbindRecord.java @@ -1,17 +1,9 @@ -package top.niunaijun.blackbox.entity; +package com.vcore.entity; import android.content.ComponentName; import android.os.Parcel; import android.os.Parcelable; -/** - * Created by Milk on 4/7/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class UnbindRecord implements Parcelable { private int mBindCount; private int mStartId; @@ -25,10 +17,6 @@ public void setStartId(int startId) { mStartId = startId; } - public int getBindCount() { - return mBindCount; - } - public void setBindCount(int bindCount) { mBindCount = bindCount; } @@ -45,8 +33,7 @@ public static Creator getCREATOR() { return CREATOR; } - public UnbindRecord() { - } + public UnbindRecord() { } @Override public int describeContents() { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/PendingResultData.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/PendingResultData.java new file mode 100644 index 0000000..42cd772 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/PendingResultData.java @@ -0,0 +1,117 @@ +package com.vcore.entity.am; + +import android.content.BroadcastReceiver; +import android.os.Bundle; +import android.os.IBinder; +import android.os.Parcel; +import android.os.Parcelable; + +import androidx.annotation.NonNull; + +import java.util.UUID; + +import com.vcore.utils.compat.BuildCompat; + +public class PendingResultData implements Parcelable { + public final int mType; + public final boolean mOrderedHint; + public final boolean mInitialStickyHint; + public final IBinder mToken; + public final int mSendingUser; + public int mFlags; + public int mResultCode; + public final String mResultData; + public final Bundle mResultExtras; + public final boolean mAbortBroadcast; + public final boolean mFinished; + public final String mBToken; + + public PendingResultData(BroadcastReceiver.PendingResult pendingResult) { + this.mBToken = UUID.randomUUID().toString(); + if (BuildCompat.isM()) { + this.mType = black.android.content.BroadcastReceiver.PendingResultM.mType.get(pendingResult); + this.mOrderedHint = black.android.content.BroadcastReceiver.PendingResultM.mOrderedHint.get(pendingResult); + this.mInitialStickyHint = black.android.content.BroadcastReceiver.PendingResultM.mInitialStickyHint.get(pendingResult); + this.mToken = black.android.content.BroadcastReceiver.PendingResultM.mToken.get(pendingResult); + this.mSendingUser = black.android.content.BroadcastReceiver.PendingResultM.mSendingUser.get(pendingResult); + this.mFlags = black.android.content.BroadcastReceiver.PendingResultM.mFlags.get(pendingResult); + this.mResultData = black.android.content.BroadcastReceiver.PendingResultM.mResultData.get(pendingResult); + this.mResultExtras = black.android.content.BroadcastReceiver.PendingResultM.mResultExtras.get(pendingResult); + this.mAbortBroadcast = black.android.content.BroadcastReceiver.PendingResultM.mAbortBroadcast.get(pendingResult); + this.mFinished = black.android.content.BroadcastReceiver.PendingResultM.mFinished.get(pendingResult); + } else { + this.mType = black.android.content.BroadcastReceiver.PendingResult.mType.get(pendingResult); + this.mOrderedHint = black.android.content.BroadcastReceiver.PendingResult.mOrderedHint.get(pendingResult); + this.mInitialStickyHint = black.android.content.BroadcastReceiver.PendingResult.mInitialStickyHint.get(pendingResult); + this.mToken = black.android.content.BroadcastReceiver.PendingResult.mToken.get(pendingResult); + this.mSendingUser = black.android.content.BroadcastReceiver.PendingResult.mSendingUser.get(pendingResult); + this.mResultData = black.android.content.BroadcastReceiver.PendingResult.mResultData.get(pendingResult); + this.mResultExtras = black.android.content.BroadcastReceiver.PendingResult.mResultExtras.get(pendingResult); + this.mAbortBroadcast = black.android.content.BroadcastReceiver.PendingResult.mAbortBroadcast.get(pendingResult); + this.mFinished = black.android.content.BroadcastReceiver.PendingResult.mFinished.get(pendingResult); + } + } + + public BroadcastReceiver.PendingResult build() { + if (BuildCompat.isM()) { + return black.android.content.BroadcastReceiver.PendingResultM._new.newInstance(mResultCode, mResultData, mResultExtras, mType, mOrderedHint, mInitialStickyHint, mToken, mSendingUser, mFlags); + } + return black.android.content.BroadcastReceiver.PendingResult._new.newInstance(mResultCode, mResultData, mResultExtras, mType, mOrderedHint, mInitialStickyHint, mToken, mSendingUser); + } + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeInt(this.mType); + dest.writeByte(this.mOrderedHint ? (byte) 1 : (byte) 0); + dest.writeByte(this.mInitialStickyHint ? (byte) 1 : (byte) 0); + dest.writeStrongBinder(this.mToken); + dest.writeInt(this.mSendingUser); + dest.writeInt(this.mFlags); + dest.writeInt(this.mResultCode); + dest.writeString(this.mResultData); + dest.writeBundle(this.mResultExtras); + dest.writeByte(this.mAbortBroadcast ? (byte) 1 : (byte) 0); + dest.writeByte(this.mFinished ? (byte) 1 : (byte) 0); + dest.writeString(this.mBToken); + } + + protected PendingResultData(Parcel in) { + this.mType = in.readInt(); + this.mOrderedHint = in.readByte() != 0; + this.mInitialStickyHint = in.readByte() != 0; + this.mToken = in.readStrongBinder(); + this.mSendingUser = in.readInt(); + this.mFlags = in.readInt(); + this.mResultCode = in.readInt(); + this.mResultData = in.readString(); + this.mResultExtras = in.readBundle(); + this.mAbortBroadcast = in.readByte() != 0; + this.mFinished = in.readByte() != 0; + this.mBToken = in.readString(); + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public PendingResultData createFromParcel(Parcel source) { + return new PendingResultData(source); + } + + @Override + public PendingResultData[] newArray(int size) { + return new PendingResultData[size]; + } + }; + + @NonNull + @Override + public String toString() { + return "PendingResultData{" + "mType=" + mType + ", mOrderedHint=" + mOrderedHint + ", mInitialStickyHint=" + mInitialStickyHint + ", mToken=" + mToken + + ", mSendingUser=" + mSendingUser + ", mFlags=" + mFlags + ", mResultCode=" + mResultCode + ", mResultData='" + mResultData + '\'' + + ", mResultExtras=" + mResultExtras + ", mAbortBroadcast=" + mAbortBroadcast + ", mFinished=" + mFinished + '}'; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/ReceiverData.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/ReceiverData.java new file mode 100644 index 0000000..8d1c03c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/ReceiverData.java @@ -0,0 +1,44 @@ +package com.vcore.entity.am; + +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.os.Parcel; +import android.os.Parcelable; + +public class ReceiverData implements Parcelable { + public Intent intent; + public ActivityInfo activityInfo; + public PendingResultData data; + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeParcelable(this.intent, flags); + dest.writeParcelable(this.activityInfo, flags); + dest.writeParcelable(this.data, flags); + } + + public ReceiverData() { } + + protected ReceiverData(Parcel in) { + this.intent = in.readParcelable(Intent.class.getClassLoader()); + this.activityInfo = in.readParcelable(ActivityInfo.class.getClassLoader()); + this.data = in.readParcelable(PendingResultData.class.getClassLoader()); + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public ReceiverData createFromParcel(Parcel source) { + return new ReceiverData(source); + } + + @Override + public ReceiverData[] newArray(int size) { + return new ReceiverData[size]; + } + }; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningAppProcessInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningAppProcessInfo.java new file mode 100644 index 0000000..b56fa68 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningAppProcessInfo.java @@ -0,0 +1,42 @@ +package com.vcore.entity.am; + +import android.app.ActivityManager; +import android.os.Parcel; +import android.os.Parcelable; + +import java.util.ArrayList; +import java.util.List; + +public class RunningAppProcessInfo implements Parcelable { + public final List mAppProcessInfoList; + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeTypedList(this.mAppProcessInfoList); + } + + public RunningAppProcessInfo() { + this.mAppProcessInfoList = new ArrayList<>(); + } + + protected RunningAppProcessInfo(Parcel in) { + this.mAppProcessInfoList = in.createTypedArrayList(ActivityManager.RunningAppProcessInfo.CREATOR); + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public RunningAppProcessInfo createFromParcel(Parcel source) { + return new RunningAppProcessInfo(source); + } + + @Override + public RunningAppProcessInfo[] newArray(int size) { + return new RunningAppProcessInfo[size]; + } + }; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningServiceInfo.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningServiceInfo.java new file mode 100644 index 0000000..945abc3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/am/RunningServiceInfo.java @@ -0,0 +1,42 @@ +package com.vcore.entity.am; + +import android.app.ActivityManager; +import android.os.Parcel; +import android.os.Parcelable; + +import java.util.ArrayList; +import java.util.List; + +public class RunningServiceInfo implements Parcelable { + public final List mRunningServiceInfoList; + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeTypedList(this.mRunningServiceInfoList); + } + + public RunningServiceInfo() { + this.mRunningServiceInfoList = new ArrayList<>(); + } + + protected RunningServiceInfo(Parcel in) { + this.mRunningServiceInfoList = in.createTypedArrayList(ActivityManager.RunningServiceInfo.CREATOR); + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public RunningServiceInfo createFromParcel(Parcel source) { + return new RunningServiceInfo(source); + } + + @Override + public RunningServiceInfo[] newArray(int size) { + return new RunningServiceInfo[size]; + } + }; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/device/BDeviceConfig.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/device/BDeviceConfig.java new file mode 100644 index 0000000..41ae65f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/device/BDeviceConfig.java @@ -0,0 +1,14 @@ +package com.vcore.entity.device; + +import android.os.Parcel; +import android.os.Parcelable; + +public class BDeviceConfig implements Parcelable { + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BCell.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BCell.java new file mode 100644 index 0000000..9f80d18 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BCell.java @@ -0,0 +1,73 @@ +package com.vcore.entity.location; + +import android.os.Parcel; +import android.os.Parcelable; + +public class BCell implements Parcelable { + /** + * mnc : 1 + * lac : 41093 + * ci : 3865320 + * acc : 1177 + * location : {"lon":116.343278,"lat":39.531734} + * reference blog: https://liuschen.top/2016/09/15/BLocation.html + * MCC,Mobile Country Code,移动国家代码(中国的为460); + * MNC,Mobile Network Code,移动网络号码(00移动 01联通 11电信4G); + * LAC/TAC(1~65535),Location Area Code,位置区域码; + * CID/CI( 2G(1~65535), 3G/4G(1~268435455)),Cell Identity,基站编号; + * TYPE: Cdma/Lte/Gsm/Wcdma + */ + public int MCC; + public int MNC; + public int LAC; + public int CID; + public int TYPE; + + /** + * GSM phone + */ + public static final int PHONE_TYPE_GSM = 1; + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeInt(this.MCC); + dest.writeInt(this.MNC); + dest.writeInt(this.LAC); + dest.writeInt(this.CID); + dest.writeInt(this.TYPE); + } + + public BCell() { } + public BCell(int MCC, int MNC, int LAC, int CID) { + this.TYPE = PHONE_TYPE_GSM; + this.MCC = MCC; + this.CID = CID; + this.MNC = MNC; + this.LAC = LAC; + } + + public BCell(Parcel in) { + this.MCC = in.readInt(); + this.MNC = in.readInt(); + this.LAC = in.readInt(); + this.CID = in.readInt(); + this.TYPE = in.readInt(); + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public BCell createFromParcel(Parcel source) { + return new BCell(source); + } + + @Override + public BCell[] newArray(int size) { + return new BCell[size]; + } + }; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocation.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocation.java new file mode 100644 index 0000000..4aeb3e9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocation.java @@ -0,0 +1,152 @@ +package com.vcore.entity.location; + +import android.location.Location; +import android.location.LocationManager; +import android.os.Bundle; +import android.os.Parcel; +import android.os.Parcelable; + +import androidx.annotation.NonNull; + +public class BLocation implements Parcelable { + private double mLatitude = 0.0; + private double mLongitude = 0.0; + private double mAltitude = 0.0f; + private float mSpeed = 0.0f; + private float mBearing = 0.0f; + private float mAccuracy = 0.0f; + + @Override + public int describeContents() { + return 0; + } + + @Override + public void writeToParcel(Parcel dest, int flags) { + dest.writeDouble(this.mLatitude); + dest.writeDouble(this.mLongitude); + dest.writeDouble(this.mAltitude); + dest.writeFloat(this.mSpeed); + dest.writeFloat(this.mBearing); + dest.writeFloat(this.mAccuracy); + } + + public double getLatitude() { + return mLatitude; + } + + public double getLongitude() { + return mLongitude; + } + + public BLocation() { } + + public BLocation(double latitude, double mLongitude) { + this.mLatitude = latitude; + this.mLongitude = mLongitude; + } + + public BLocation(Parcel in) { + this.mLatitude = in.readDouble(); + this.mLongitude = in.readDouble(); + this.mAltitude = in.readDouble(); + this.mAccuracy = in.readFloat(); + this.mSpeed = in.readFloat(); + this.mBearing = in.readFloat(); + } + + public boolean isEmpty() { + return mLatitude == 0 && mLongitude == 0; + } + + public static final Parcelable.Creator CREATOR = new Parcelable.Creator() { + @Override + public BLocation createFromParcel(Parcel source) { + return new BLocation(source); + } + + @Override + public BLocation[] newArray(int size) { + return new BLocation[size]; + } + }; + + @NonNull + @Override + public String toString() { + return "BLocation{" + "latitude: " + mLatitude + ", longitude: " + mLongitude + ", altitude: " + mAltitude + ", speed: " + mSpeed + + ", bearing: " + mBearing + ", accuracy: " + mAccuracy + '}'; + } + + public Location convert2SystemLocation() { + Location location = new Location(LocationManager.GPS_PROVIDER); + location.setLatitude(mLatitude); + location.setLongitude(mLongitude); + location.setSpeed(mSpeed); + location.setBearing(mBearing); + location.setAccuracy(40f); + location.setTime(System.currentTimeMillis()); + Bundle extraBundle = new Bundle(); + // GPS satellite number + int satelliteCount = 10; + extraBundle.putInt("satellites", satelliteCount); + extraBundle.putInt("satellitesvalue", satelliteCount); + location.setExtras(extraBundle); + return location; + } + + public static String getSouthEast(BLocation location) { + if (location.mLongitude > 0.0d) { + return "E"; + } + return "W"; + } + + public static String getNorthWest(BLocation location) { + if (location.mLatitude > 0.0d) { + return "N"; + } + return "S"; + } + + public static String getGPSLatitude(double v) { + int du = (int) v; + double fen = (v - (double) du) * 60.0d; + + return du + leftZeroPad((int) fen) + ":" + String.valueOf(fen).substring(2); + } + + private static String leftZeroPad(int num) { + return leftZeroPad(String.valueOf(num)); + } + + private static String leftZeroPad(String num) { + StringBuilder sb = new StringBuilder(2); + int i; + + if (num == null) { + for (i = 0; i < 2; i++) { + sb.append('0'); + } + } else { + for (i = 0; i < 2 - num.length(); i++) { + sb.append('0'); + } + sb.append(num); + } + return sb.toString(); + } + + public static String checkSum(String nema) { + String checkStr = nema; + if (nema.startsWith("$")) { + checkStr = nema.substring(1); + } + + int sum = 0; + for (int i = 0; i < checkStr.length(); i++) { + sum ^= (byte) checkStr.charAt(i); + } + return nema + "*" + String.format("%02X", sum).toLowerCase(); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/location/BLocationConfig.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocationConfig.java similarity index 91% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/location/BLocationConfig.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocationConfig.java index 2798d7d..8b5aca7 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/location/BLocationConfig.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/location/BLocationConfig.java @@ -1,15 +1,11 @@ -package top.niunaijun.blackbox.entity.location; +package com.vcore.entity.location; import android.os.Parcel; import android.os.Parcelable; import java.util.List; -/** - * Created by BlackBoxing on 3/8/22. - **/ public class BLocationConfig implements Parcelable { - public int pattern; public BCell cell; public List allCell; @@ -21,8 +17,7 @@ public int describeContents() { return 0; } - public BLocationConfig() { - } + public BLocationConfig() { } public BLocationConfig(Parcel in) { refresh(in); @@ -36,7 +31,6 @@ public void refresh(Parcel in) { this.location = in.readParcelable(BLocation.class.getClassLoader()); } - @Override public void writeToParcel(Parcel dest, int flags) { dest.writeInt(this.pattern); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallOption.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallOption.java similarity index 89% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallOption.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallOption.java index e976335..8abf446 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallOption.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallOption.java @@ -1,16 +1,8 @@ -package top.niunaijun.blackbox.entity.pm; +package com.vcore.entity.pm; import android.os.Parcel; import android.os.Parcelable; -/** - * Created by Milk on 4/21/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class InstallOption implements Parcelable { public static final int FLAG_SYSTEM = 1; public static final int FLAG_STORAGE = 1 << 1; @@ -55,8 +47,7 @@ public void writeToParcel(Parcel dest, int flags) { dest.writeInt(this.flags); } - public InstallOption() { - } + public InstallOption() { } protected InstallOption(Parcel in) { this.flags = in.readInt(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallResult.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallResult.java similarity index 86% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallResult.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallResult.java index 86b5baa..2871f45 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstallResult.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstallResult.java @@ -1,18 +1,10 @@ -package top.niunaijun.blackbox.entity.pm; +package com.vcore.entity.pm; import android.os.Parcel; import android.os.Parcelable; -import top.niunaijun.blackbox.utils.Slog; +import com.vcore.utils.Slog; -/** - * Created by Milk on 4/20/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class InstallResult implements Parcelable { public static final String TAG = "InstallResult"; @@ -32,8 +24,7 @@ public void writeToParcel(Parcel dest, int flags) { dest.writeString(this.msg); } - public InstallResult() { - } + public InstallResult() { } protected InstallResult(Parcel in) { this.success = in.readByte() != 0; diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledModule.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledModule.java similarity index 85% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledModule.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledModule.java index 0559e16..4d4761b 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledModule.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledModule.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.entity.pm; +package com.vcore.entity.pm; import android.content.pm.ApplicationInfo; import android.content.pm.PackageInfo; @@ -6,17 +6,9 @@ import android.os.Parcel; import android.os.Parcelable; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.core.system.user.BUserHandle; +import com.vcore.BlackBoxCore; +import com.vcore.core.system.user.BUserHandle; -/** - * Created by Milk on 5/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class InstalledModule implements Parcelable { public String packageName; public String name; @@ -24,9 +16,7 @@ public class InstalledModule implements Parcelable { public String main; public boolean enable; - public InstalledModule() { - } - + public InstalledModule() { } public ApplicationInfo getApplication() { return BlackBoxCore.getBPackageManager().getApplicationInfo(packageName, PackageManager.GET_META_DATA, BUserHandle.USER_XPOSED); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledPackage.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledPackage.java similarity index 83% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledPackage.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledPackage.java index f2bd9f8..e464672 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/InstalledPackage.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/InstalledPackage.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.entity.pm; +package com.vcore.entity.pm; import android.content.pm.ApplicationInfo; import android.content.pm.PackageInfo; @@ -8,16 +8,8 @@ import java.util.Objects; -import top.niunaijun.blackbox.BlackBoxCore; +import com.vcore.BlackBoxCore; -/** - * Created by Milk on 4/20/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class InstalledPackage implements Parcelable { public int userId; public String packageName; @@ -41,8 +33,7 @@ public void writeToParcel(Parcel dest, int flags) { dest.writeString(this.packageName); } - public InstalledPackage() { - } + public InstalledPackage() { } public InstalledPackage(String packageName) { this.packageName = packageName; @@ -55,8 +46,13 @@ protected InstalledPackage(Parcel in) { @Override public boolean equals(Object o) { - if (this == o) return true; - if (o == null || getClass() != o.getClass()) return false; + if (o == this) { + return true; + } + + if (o == null || getClass() != o.getClass()) { + return false; + } InstalledPackage that = (InstalledPackage) o; return Objects.equals(packageName, that.packageName); } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/XposedConfig.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/XposedConfig.java similarity index 84% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/XposedConfig.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/XposedConfig.java index 9e16175..f68f664 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/entity/pm/XposedConfig.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/entity/pm/XposedConfig.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.entity.pm; +package com.vcore.entity.pm; import android.os.Parcel; import android.os.Parcelable; @@ -6,14 +6,6 @@ import java.util.HashMap; import java.util.Map; -/** - * Created by Milk on 5/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class XposedConfig implements Parcelable { public boolean enable; public Map moduleState = new HashMap<>(); @@ -33,13 +25,13 @@ public void writeToParcel(Parcel dest, int flags) { } } - public XposedConfig() { - } + public XposedConfig() { } public XposedConfig(Parcel in) { this.enable = in.readByte() != 0; int mModuleStateSize = in.readInt(); - this.moduleState = new HashMap(mModuleStateSize); + this.moduleState = new HashMap<>(mModuleStateSize); + for (int i = 0; i < mModuleStateSize; i++) { String key = in.readString(); Boolean value = (Boolean) in.readValue(Boolean.class.getClassLoader()); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/AppInstrumentation.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/AppInstrumentation.java new file mode 100644 index 0000000..586d0fb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/AppInstrumentation.java @@ -0,0 +1,149 @@ +package com.vcore.fake.delegate; + +import android.app.Activity; +import android.app.Application; +import android.app.Instrumentation; +import android.content.Context; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.graphics.Canvas; +import android.os.Bundle; +import android.os.PersistableBundle; +import android.util.Log; + +import java.lang.reflect.Field; + +import black.Reflector; +import black.android.app.ActivityThread; +import de.robv.android.xposed.XposedBridge; +import de.robv.android.xposed.XposedHelpers; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.HookManager; +import com.vcore.fake.hook.IInjectHook; +import com.vcore.fake.service.HCallbackProxy; +import com.vcore.fake.service.IActivityClientProxy; +import com.vcore.utils.compat.ActivityCompat; +import com.vcore.utils.compat.ActivityManagerCompat; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.ContextCompat; + +public final class AppInstrumentation extends BaseInstrumentationDelegate implements IInjectHook { + private static final String TAG = AppInstrumentation.class.getSimpleName(); + + private static final class SAppInstrumentationHolder { + static final AppInstrumentation sAppInstrumentation = new AppInstrumentation(); + } + + public static AppInstrumentation get() { + return SAppInstrumentationHolder.sAppInstrumentation; + } + + public AppInstrumentation() { } + + @Override + public void injectHook() { + try { + Instrumentation mInstrumentation = getCurrInstrumentation(); + if (mInstrumentation == this || checkInstrumentation(mInstrumentation)) { + return; + } + mBaseInstrumentation = mInstrumentation; + ActivityThread.mInstrumentation.set(BlackBoxCore.mainThread(), this); + } catch (Exception e) { + e.printStackTrace(); + } + } + + private Instrumentation getCurrInstrumentation() { + Object currentActivityThread = BlackBoxCore.mainThread(); + return ActivityThread.mInstrumentation.get(currentActivityThread); + } + + @Override + public boolean isBadEnv() { + return !checkInstrumentation(getCurrInstrumentation()); + } + + private boolean checkInstrumentation(Instrumentation instrumentation) { + if (instrumentation instanceof AppInstrumentation) { + return true; + } + + Class clazz = instrumentation.getClass(); + if (Instrumentation.class.equals(clazz)) { + return false; + } + + do { + assert clazz != null; + Field[] fields = clazz.getDeclaredFields(); + for (Field field : fields) { + if (Instrumentation.class.isAssignableFrom(field.getType())) { + field.setAccessible(true); + try { + Object obj = field.get(instrumentation); + if ((obj instanceof AppInstrumentation)) { + return true; + } + } catch (Exception e) { + return false; + } + } + } + clazz = clazz.getSuperclass(); + } while (!Instrumentation.class.equals(clazz)); + return false; + } + + private void checkHCallback() { + HookManager.get().checkEnv(HCallbackProxy.class); + } + + private void checkActivity(Activity activity) { + Log.d(TAG, "callActivityOnCreate: " + activity.getClass().getName()); + checkHCallback(); + HookManager.get().checkEnv(IActivityClientProxy.class); + + ActivityInfo info = black.android.app.Activity.mActivityInfo.get(activity); + ContextCompat.fix(activity); + ActivityCompat.fix(activity); + if (info.theme != 0) { + activity.getTheme().applyStyle(info.theme, true); + } + ActivityManagerCompat.setActivityOrientation(activity, info.screenOrientation); + } + + @Override + public Application newApplication(ClassLoader cl, String className, Context context) throws InstantiationException, IllegalAccessException, ClassNotFoundException { + ContextCompat.fix(context); + //BActivityThread.currentActivityThread().loadXposed(context); + return super.newApplication(cl, className, context); + } + + @Override + public void callActivityOnCreate(Activity activity, Bundle icicle, PersistableBundle persistentState) { + checkActivity(activity); + super.callActivityOnCreate(activity, icicle, persistentState); + } + + @Override + public void callActivityOnCreate(Activity activity, Bundle icicle) { + checkActivity(activity); + super.callActivityOnCreate(activity, icicle); + } + + @Override + public void callApplicationOnCreate(Application app) { + checkHCallback(); + super.callApplicationOnCreate(app); + } + + public Activity newActivity(ClassLoader cl, String className, Intent intent) throws InstantiationException, IllegalAccessException, ClassNotFoundException { + try { + return super.newActivity(cl, className, intent); + } catch (ClassNotFoundException e) { + return mBaseInstrumentation.newActivity(cl, className, intent); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/BaseInstrumentationDelegate.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/BaseInstrumentationDelegate.java new file mode 100644 index 0000000..cf2c703 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/BaseInstrumentationDelegate.java @@ -0,0 +1,361 @@ +package com.vcore.fake.delegate; + +import android.app.Activity; +import android.app.Application; +import android.app.Instrumentation; +import android.app.UiAutomation; +import android.content.ComponentName; +import android.content.Context; +import android.content.Intent; +import android.content.IntentFilter; +import android.content.pm.ActivityInfo; +import android.os.Build; +import android.os.Bundle; +import android.os.IBinder; +import android.os.PersistableBundle; +import android.view.KeyEvent; +import android.view.MotionEvent; + +import androidx.annotation.RequiresApi; + +import com.vcore.BlackBoxCore; +import com.vcore.app.configuration.AppLifecycleCallback; + +public class BaseInstrumentationDelegate extends Instrumentation { + protected Instrumentation mBaseInstrumentation; + + @Override + public void onCreate(Bundle arguments) { + mBaseInstrumentation.onCreate(arguments); + } + + @Override + public void start() { + mBaseInstrumentation.start(); + } + + @Override + public void onStart() { + mBaseInstrumentation.onStart(); + } + + @Override + public boolean onException(Object obj, Throwable e) { + return mBaseInstrumentation.onException(obj, e); + } + + @Override + public void sendStatus(int resultCode, Bundle results) { + mBaseInstrumentation.sendStatus(resultCode, results); + } + + @RequiresApi(api = Build.VERSION_CODES.O) + @Override + public void addResults(Bundle results) { + mBaseInstrumentation.addResults(results); + } + + @Override + public void finish(int resultCode, Bundle results) { + mBaseInstrumentation.finish(resultCode, results); + } + + @Override + public void setAutomaticPerformanceSnapshots() { + mBaseInstrumentation.setAutomaticPerformanceSnapshots(); + } + + @Override + public void startPerformanceSnapshot() { + mBaseInstrumentation.startPerformanceSnapshot(); + } + + @Override + public void endPerformanceSnapshot() { + mBaseInstrumentation.endPerformanceSnapshot(); + } + + @Override + public void onDestroy() { + mBaseInstrumentation.onDestroy(); + } + + @Override + public Context getContext() { + return mBaseInstrumentation.getContext(); + } + + @Override + public ComponentName getComponentName() { + return mBaseInstrumentation.getComponentName(); + } + + @Override + public Context getTargetContext() { + return mBaseInstrumentation.getTargetContext(); + } + + @Override + public boolean isProfiling() { + return mBaseInstrumentation.isProfiling(); + } + + @Override + public void startProfiling() { + mBaseInstrumentation.startProfiling(); + } + + @Override + public void stopProfiling() { + mBaseInstrumentation.stopProfiling(); + } + + @Override + public void setInTouchMode(boolean inTouch) { + mBaseInstrumentation.setInTouchMode(inTouch); + } + + @Override + public void waitForIdle(Runnable recipient) { + mBaseInstrumentation.waitForIdle(recipient); + } + + @Override + public void waitForIdleSync() { + mBaseInstrumentation.waitForIdleSync(); + } + + @Override + public void runOnMainSync(Runnable runner) { + mBaseInstrumentation.runOnMainSync(runner); + } + + @Override + public Activity startActivitySync(Intent intent) { + return mBaseInstrumentation.startActivitySync(intent); + } + + @Override + public void addMonitor(ActivityMonitor monitor) { + mBaseInstrumentation.addMonitor(monitor); + } + + @Override + public ActivityMonitor addMonitor(IntentFilter filter, ActivityResult result, boolean block) { + return mBaseInstrumentation.addMonitor(filter, result, block); + } + + @Override + public ActivityMonitor addMonitor(String cls, ActivityResult result, boolean block) { + return mBaseInstrumentation.addMonitor(cls, result, block); + } + + @Override + public boolean checkMonitorHit(ActivityMonitor monitor, int minHits) { + return mBaseInstrumentation.checkMonitorHit(monitor, minHits); + } + + @Override + public Activity waitForMonitor(ActivityMonitor monitor) { + return mBaseInstrumentation.waitForMonitor(monitor); + } + + @Override + public Activity waitForMonitorWithTimeout(ActivityMonitor monitor, long timeOut) { + return mBaseInstrumentation.waitForMonitorWithTimeout(monitor, timeOut); + } + + @Override + public void removeMonitor(ActivityMonitor monitor) { + mBaseInstrumentation.removeMonitor(monitor); + } + + @Override + public boolean invokeMenuActionSync(Activity targetActivity, int id, int flag) { + return mBaseInstrumentation.invokeMenuActionSync(targetActivity, id, flag); + } + + @Override + public boolean invokeContextMenuAction(Activity targetActivity, int id, int flag) { + return mBaseInstrumentation.invokeContextMenuAction(targetActivity, id, flag); + } + + @Override + public void sendStringSync(String text) { + mBaseInstrumentation.sendStringSync(text); + } + + @Override + public void sendKeySync(KeyEvent event) { + mBaseInstrumentation.sendKeySync(event); + } + + @Override + public void sendKeyDownUpSync(int key) { + mBaseInstrumentation.sendKeyDownUpSync(key); + } + + @Override + public void sendCharacterSync(int keyCode) { + mBaseInstrumentation.sendCharacterSync(keyCode); + } + + @Override + public void sendPointerSync(MotionEvent event) { + mBaseInstrumentation.sendPointerSync(event); + } + + @Override + public void sendTrackballEventSync(MotionEvent event) { + mBaseInstrumentation.sendTrackballEventSync(event); + } + + @Override + public Application newApplication(ClassLoader cl, String className, Context context) throws ClassNotFoundException, IllegalAccessException, InstantiationException { + return mBaseInstrumentation.newApplication(cl, className, context); + } + + @Override + public void callApplicationOnCreate(Application app) { + mBaseInstrumentation.callApplicationOnCreate(app); + } + + @Override + public Activity newActivity(Class clazz, Context context, IBinder token, Application application, Intent intent, ActivityInfo info, CharSequence title, Activity parent, String id, Object lastNonConfigurationInstance) throws IllegalAccessException, InstantiationException { + return mBaseInstrumentation.newActivity(clazz, context, token, application, intent, info, title, parent, id, lastNonConfigurationInstance); + } + + @Override + public Activity newActivity(ClassLoader cl, String className, Intent intent) throws ClassNotFoundException, IllegalAccessException, InstantiationException { + return mBaseInstrumentation.newActivity(cl, className, intent); + } + + @Override + public void callActivityOnCreate(Activity activity, Bundle icicle) { + mBaseInstrumentation.callActivityOnCreate(activity, icicle); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityCreated(activity, icicle); + } + } + + @Override + public void callActivityOnCreate(Activity activity, Bundle icicle, PersistableBundle persistentState) { + mBaseInstrumentation.callActivityOnCreate(activity, icicle, persistentState); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityCreated(activity, icicle); + } + } + + @Override + public void callActivityOnDestroy(Activity activity) { + mBaseInstrumentation.callActivityOnDestroy(activity); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityDestroyed(activity); + } + } + + @Override + public void callActivityOnRestoreInstanceState(Activity activity, Bundle savedInstanceState) { + mBaseInstrumentation.callActivityOnRestoreInstanceState(activity, savedInstanceState); + } + + @Override + public void callActivityOnRestoreInstanceState(Activity activity, Bundle savedInstanceState, PersistableBundle persistentState) { + mBaseInstrumentation.callActivityOnRestoreInstanceState(activity, savedInstanceState, persistentState); + } + + @Override + public void callActivityOnPostCreate(Activity activity, Bundle icicle) { + mBaseInstrumentation.callActivityOnPostCreate(activity, icicle); + } + + @Override + public void callActivityOnPostCreate(Activity activity, Bundle icicle, PersistableBundle persistentState) { + mBaseInstrumentation.callActivityOnPostCreate(activity, icicle, persistentState); + } + + @Override + public void callActivityOnNewIntent(Activity activity, Intent intent) { + mBaseInstrumentation.callActivityOnNewIntent(activity, intent); + } + + @Override + public void callActivityOnStart(Activity activity) { + mBaseInstrumentation.callActivityOnStart(activity); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityStarted(activity); + } + } + + @Override + public void callActivityOnRestart(Activity activity) { + mBaseInstrumentation.callActivityOnRestart(activity); + } + + @Override + public void callActivityOnResume(Activity activity) { + mBaseInstrumentation.callActivityOnResume(activity); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityResumed(activity); + } + } + + @Override + public void callActivityOnStop(Activity activity) { + mBaseInstrumentation.callActivityOnStop(activity); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityStopped(activity); + } + } + + @Override + public void callActivityOnSaveInstanceState(Activity activity, Bundle outState) { + mBaseInstrumentation.callActivityOnSaveInstanceState(activity, outState); + } + + @Override + public void callActivityOnSaveInstanceState(Activity activity, Bundle outState, PersistableBundle outPersistentState) { + mBaseInstrumentation.callActivityOnSaveInstanceState(activity, outState, outPersistentState); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivitySaveInstanceState(activity, outState); + } + } + + @Override + public void callActivityOnPause(Activity activity) { + mBaseInstrumentation.callActivityOnPause(activity); + for (AppLifecycleCallback appLifecycleCallback : BlackBoxCore.get().getAppLifecycleCallbacks()) { + appLifecycleCallback.onActivityPaused(activity); + } + } + + @Override + public void callActivityOnUserLeaving(Activity activity) { + mBaseInstrumentation.callActivityOnUserLeaving(activity); + } + + @Override + public void startAllocCounting() { + mBaseInstrumentation.startAllocCounting(); + } + + @Override + public void stopAllocCounting() { + mBaseInstrumentation.stopAllocCounting(); + } + + @Override + public Bundle getAllocCounts() { + return mBaseInstrumentation.getAllocCounts(); + } + + @Override + public Bundle getBinderCounts() { + return mBaseInstrumentation.getBinderCounts(); + } + + @Override + public UiAutomation getUiAutomation() { + return mBaseInstrumentation.getUiAutomation(); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ContentProviderDelegate.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ContentProviderDelegate.java new file mode 100644 index 0000000..dcad4b2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ContentProviderDelegate.java @@ -0,0 +1,109 @@ +package com.vcore.fake.delegate; + +import android.net.Uri; +import android.os.Build; +import android.os.IInterface; +import android.util.ArrayMap; + +import java.lang.reflect.Proxy; +import java.util.HashSet; +import java.util.Set; + +import black.android.app.ActivityThread; +import black.android.app.IActivityManager; +import black.android.content.ContentProviderHolderOreo; +import black.android.providers.Settings; +import com.vcore.BlackBoxCore; +import com.vcore.fake.service.context.providers.ContentProviderStub; +import com.vcore.fake.service.context.providers.SystemProviderStub; +import com.vcore.utils.compat.BuildCompat; + +public class ContentProviderDelegate { + public static final String TAG = "ContentProviderDelegate"; + private static final Set sInjected = new HashSet<>(); + + public static void update(Object holder, String auth) { + IInterface iInterface; + if (BuildCompat.isOreo()) { + iInterface = ContentProviderHolderOreo.provider.get(holder); + } else { + iInterface = IActivityManager.ContentProviderHolder.provider.get(holder); + } + + if (iInterface instanceof Proxy) { + return; + } + + IInterface bContentProvider; + switch (auth) { + case "media": + case "telephony": + case "settings": + bContentProvider = new SystemProviderStub().wrapper(iInterface, BlackBoxCore.getHostPkg()); + break; + default: + bContentProvider = new ContentProviderStub().wrapper(iInterface, BlackBoxCore.getHostPkg()); + break; + } + + if (BuildCompat.isOreo()) { + ContentProviderHolderOreo.provider.set(holder, bContentProvider); + } else { + IActivityManager.ContentProviderHolder.provider.set(holder, bContentProvider); + } + } + + public static void init() { + clearSettingProvider(); + + BlackBoxCore.getContext().getContentResolver().call(Uri.parse("content://settings"), "", null, null); + Object activityThread = BlackBoxCore.mainThread(); + ArrayMap map = (ArrayMap) ActivityThread.mProviderMap.get(activityThread); + + for (Object value : map.values()) { + String[] mNames = ActivityThread.ProviderClientRecordP.mNames.get(value); + if (mNames == null || mNames.length <= 0) { + continue; + } + + String providerName = mNames[0]; + if (!sInjected.contains(providerName)) { + sInjected.add(providerName); + IInterface iInterface = ActivityThread.ProviderClientRecordP.mProvider.get(value); + ActivityThread.ProviderClientRecordP.mProvider.set(value, new ContentProviderStub().wrapper(iInterface, BlackBoxCore.getHostPkg())); + ActivityThread.ProviderClientRecordP.mNames.set(value, new String[]{providerName}); + } + } + } + + public static void clearSettingProvider() { + Object cache; + cache = Settings.System.sNameValueCache.get(); + if (cache != null) { + clearContentProvider(cache); + } + + cache = Settings.Secure.sNameValueCache.get(); + if (cache != null) { + clearContentProvider(cache); + } + + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) { + cache = Settings.Global.sNameValueCache.get(); + if (cache != null) { + clearContentProvider(cache); + } + } + } + + private static void clearContentProvider(Object cache) { + if (BuildCompat.isOreo()) { + Object holder = Settings.NameValueCacheOreo.mProviderHolder.get(cache); + if (holder != null) { + Settings.ContentProviderHolder.mContentProvider.set(holder, null); + } + } else { + Settings.NameValueCache.mContentProvider.set(cache, null); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/InnerReceiverDelegate.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/InnerReceiverDelegate.java similarity index 78% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/InnerReceiverDelegate.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/InnerReceiverDelegate.java index 8937ae6..6de317c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/InnerReceiverDelegate.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/InnerReceiverDelegate.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.delegate; +package com.vcore.fake.delegate; import android.content.IIntentReceiver; import android.content.Intent; @@ -10,18 +10,9 @@ import java.util.HashMap; import java.util.Map; -import black.android.content.BRIIntentReceiver; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.proxy.record.ProxyBroadcastRecord; +import com.vcore.app.BActivityThread; +import com.vcore.proxy.record.ProxyBroadcastRecord; -/** - * Created by Milk on 4/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class InnerReceiverDelegate extends IIntentReceiver.Stub { public static final String TAG = "InnerReceiverDelegate"; @@ -32,10 +23,6 @@ private InnerReceiverDelegate(IIntentReceiver iIntentReceiver) { this.mIntentReceiver = new WeakReference<>(iIntentReceiver); } - public static InnerReceiverDelegate getDelegate(IBinder iBinder) { - return sInnerReceiverDelegate.get(iBinder); - } - public static IIntentReceiver createProxy(IIntentReceiver base) { if (base instanceof InnerReceiverDelegate) { return base; @@ -54,6 +41,7 @@ public void binderDied() { } catch (RemoteException e) { e.printStackTrace(); } + delegate = new InnerReceiverDelegate(base); sInnerReceiverDelegate.put(iBinder, delegate); } @@ -61,7 +49,7 @@ public void binderDied() { } @Override - public void performReceive(Intent intent, int resultCode, String data, Bundle extras, boolean ordered, boolean sticky, int sendingUser) throws RemoteException { + public void performReceive(Intent intent, int resultCode, String data, Bundle extras, boolean ordered, boolean sticky, int sendingUser) { intent.setExtrasClassLoader(BActivityThread.getApplication().getClassLoader()); ProxyBroadcastRecord proxyBroadcastRecord = ProxyBroadcastRecord.create(intent); Intent perIntent; @@ -71,9 +59,10 @@ public void performReceive(Intent intent, int resultCode, String data, Bundle ex } else { perIntent = intent; } + IIntentReceiver iIntentReceiver = mIntentReceiver.get(); if (iIntentReceiver != null) { - BRIIntentReceiver.get(iIntentReceiver).performReceive(perIntent, resultCode, data, extras, ordered, sticky, sendingUser); + black.android.content.IIntentReceiver.performReceive.call(iIntentReceiver, perIntent, resultCode, data, extras, ordered, sticky, sendingUser); } } } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/ServiceConnectionDelegate.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ServiceConnectionDelegate.java similarity index 85% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/ServiceConnectionDelegate.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ServiceConnectionDelegate.java index 96888f4..5803c1e 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/delegate/ServiceConnectionDelegate.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/delegate/ServiceConnectionDelegate.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.delegate; +package com.vcore.fake.delegate; import android.app.IServiceConnection; import android.content.ComponentName; @@ -9,17 +9,9 @@ import java.util.HashMap; import java.util.Map; -import black.android.app.BRIServiceConnectionO; -import top.niunaijun.blackbox.utils.compat.BuildCompat; +import black.android.app.IServiceConnectionO; +import com.vcore.utils.compat.BuildCompat; -/** - * Created by Milk on 4/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class ServiceConnectionDelegate extends IServiceConnection.Stub { private static final Map sServiceConnectDelegate = new HashMap<>(); private final IServiceConnection mConn; @@ -49,6 +41,7 @@ public void binderDied() { } catch (RemoteException e) { e.printStackTrace(); } + delegate = new ServiceConnectionDelegate(base, intent.getComponent()); sServiceConnectDelegate.put(iBinder, delegate); } @@ -62,7 +55,7 @@ public void connected(ComponentName name, IBinder service) throws RemoteExceptio public void connected(ComponentName name, IBinder service, boolean dead) throws RemoteException { if (BuildCompat.isOreo()) { - BRIServiceConnectionO.get(mConn).connected(mComponentName, service, dead); + IServiceConnectionO.connected.call(mConn, mComponentName, service, dead); } else { mConn.connected(name, service); } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BAccountManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BAccountManager.java similarity index 86% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BAccountManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BAccountManager.java index f6f93de..2279f0c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BAccountManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BAccountManager.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.accounts.Account; import android.accounts.AuthenticatorDescription; @@ -8,13 +8,10 @@ import java.util.Map; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.accounts.IBAccountManagerService; +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.accounts.IBAccountManagerService; -/** - * Created by BlackBox on 2022/3/3. - */ public class BAccountManager extends BlackManager { private static final BAccountManager sBAccountManager = new BAccountManager(); @@ -36,7 +33,6 @@ public String getPassword(Account account) { return null; } - public String getUserData(Account account, String key) { try { return getService().getUserData(account, key, BActivityThread.getUserId()); @@ -91,8 +87,7 @@ public void getAccountByTypeAndFeatures(IAccountManagerResponse response, String } } - public void getAccountsByFeatures(IAccountManagerResponse response, String accountType, - String[] features) { + public void getAccountsByFeatures(IAccountManagerResponse response, String accountType, String[] features) { try { getService().getAccountsByFeatures(response, accountType, features, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -109,8 +104,7 @@ public boolean addAccountExplicitly(Account account, String password, Bundle ext return false; } - public void removeAccountAsUser(IAccountManagerResponse response, Account account, - boolean expectActivityLaunch) { + public void removeAccountAsUser(IAccountManagerResponse response, Account account, boolean expectActivityLaunch) { try { getService().removeAccountAsUser(response, account, expectActivityLaunch, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -127,8 +121,7 @@ public boolean removeAccountExplicitly(Account account) { return false; } - public void copyAccountToUser(IAccountManagerResponse response, Account account, - int userFrom, int userTo) { + public void copyAccountToUser(IAccountManagerResponse response, Account account, int userFrom, int userTo) { try { getService().copyAccountToUser(response, account, userFrom, userTo); } catch (RemoteException e) { @@ -161,7 +154,6 @@ public void setAuthToken(Account account, String authTokenType, String authToken } } - public void setPassword(Account account, String password) { try { getService().setPassword(account, password, BActivityThread.getUserId()); @@ -194,9 +186,8 @@ public void updateAppPermission(Account account, String authTokenType, int uid, } } - public void getAuthToken(IAccountManagerResponse response, Account account, - String authTokenType, boolean notifyOnAuthFailure, boolean expectActivityLaunch, - Bundle options) { + public void getAuthToken(IAccountManagerResponse response, Account account, String authTokenType, boolean notifyOnAuthFailure, boolean expectActivityLaunch, + Bundle options) { try { getService().getAuthToken(response, account, authTokenType, notifyOnAuthFailure, expectActivityLaunch, options, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -204,9 +195,8 @@ public void getAuthToken(IAccountManagerResponse response, Account account, } } - public void addAccount(IAccountManagerResponse response, String accountType, - String authTokenType, String[] requiredFeatures, boolean expectActivityLaunch, - Bundle options) { + public void addAccount(IAccountManagerResponse response, String accountType, String authTokenType, String[] requiredFeatures, boolean expectActivityLaunch, + Bundle options) { try { getService().addAccount(response, accountType, authTokenType, requiredFeatures, expectActivityLaunch, options, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -214,9 +204,8 @@ public void addAccount(IAccountManagerResponse response, String accountType, } } - public void addAccountAsUser(IAccountManagerResponse response, String accountType, - String authTokenType, String[] requiredFeatures, boolean expectActivityLaunch, - Bundle options) { + public void addAccountAsUser(IAccountManagerResponse response, String accountType, String authTokenType, String[] requiredFeatures, + boolean expectActivityLaunch, Bundle options) { try { getService().addAccountAsUser(response, accountType, authTokenType, requiredFeatures, expectActivityLaunch, options, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -224,8 +213,7 @@ public void addAccountAsUser(IAccountManagerResponse response, String accountTyp } } - public void updateCredentials(IAccountManagerResponse response, Account account, - String authTokenType, boolean expectActivityLaunch, Bundle options) { + public void updateCredentials(IAccountManagerResponse response, Account account, String authTokenType, boolean expectActivityLaunch, Bundle options) { try { getService().updateCredentials(response, account, authTokenType, expectActivityLaunch, options, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -233,8 +221,7 @@ public void updateCredentials(IAccountManagerResponse response, Account account, } } - public void editProperties(IAccountManagerResponse response, String accountType, - boolean expectActivityLaunch) { + public void editProperties(IAccountManagerResponse response, String accountType, boolean expectActivityLaunch) { try { getService().editProperties(response, accountType, expectActivityLaunch, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -242,8 +229,7 @@ public void editProperties(IAccountManagerResponse response, String accountType, } } - public void confirmCredentialsAsUser(IAccountManagerResponse response, Account account, - Bundle options, boolean expectActivityLaunch) { + public void confirmCredentialsAsUser(IAccountManagerResponse response, Account account, Bundle options, boolean expectActivityLaunch) { try { getService().confirmCredentialsAsUser(response, account, options, expectActivityLaunch, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -251,17 +237,15 @@ public void confirmCredentialsAsUser(IAccountManagerResponse response, Account a } } - public boolean accountAuthenticated(Account account) { + public void accountAuthenticated(Account account) { try { - return getService().accountAuthenticated(account, BActivityThread.getUserId()); + getService().accountAuthenticated(account, BActivityThread.getUserId()); } catch (RemoteException e) { e.printStackTrace(); } - return false; } - public void getAuthTokenLabel(IAccountManagerResponse response, String accountType, - String authTokenType) { + public void getAuthTokenLabel(IAccountManagerResponse response, String accountType, String authTokenType) { try { getService().getAuthTokenLabel(response, accountType, authTokenType, BActivityThread.getUserId()); } catch (RemoteException e) { @@ -279,8 +263,7 @@ public Map getPackagesAndVisibilityForAccount(Account account) { return null; } - public boolean addAccountExplicitlyWithVisibility(Account account, String password, Bundle extras, - Map visibility) { + public boolean addAccountExplicitlyWithVisibility(Account account, String password, Bundle extras, Map visibility) { try { return getService().addAccountExplicitlyWithVisibility(account, password, extras, visibility, BActivityThread.getUserId()); } catch (RemoteException e) { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BActivityManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BActivityManager.java similarity index 85% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BActivityManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BActivityManager.java index 7534de0..2ce8b4c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BActivityManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BActivityManager.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.app.Activity; import android.content.ComponentName; @@ -8,23 +8,15 @@ import android.os.IBinder; import android.os.RemoteException; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.am.IBActivityManagerService; -import top.niunaijun.blackbox.entity.AppConfig; -import top.niunaijun.blackbox.entity.UnbindRecord; -import top.niunaijun.blackbox.entity.am.PendingResultData; -import top.niunaijun.blackbox.entity.am.RunningAppProcessInfo; -import top.niunaijun.blackbox.entity.am.RunningServiceInfo; - -/** - * Created by Milk on 4/14/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.am.IBActivityManagerService; +import com.vcore.entity.AppConfig; +import com.vcore.entity.UnbindRecord; +import com.vcore.entity.am.PendingResultData; +import com.vcore.entity.am.RunningAppProcessInfo; +import com.vcore.entity.am.RunningServiceInfo; + public class BActivityManager extends BlackManager { private static final BActivityManager sActivityManager = new BActivityManager(); @@ -62,13 +54,12 @@ public void startActivity(Intent intent, int userId) { } } - public int startActivityAms(int userId, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options) { + public void startActivityAms(int userId, Intent intent, String resolvedType, IBinder resultTo, String resultWho, int requestCode, int flags, Bundle options) { try { - return getService().startActivityAms(userId, intent, resolvedType, resultTo, resultWho, requestCode, flags, options); + getService().startActivityAms(userId, intent, resolvedType, resultTo, resultWho, requestCode, flags, options); } catch (RemoteException e) { e.printStackTrace(); } - return -1; } public int startActivities(int userId, Intent[] intent, String[] resolvedType, IBinder resultTo, Bundle options) { @@ -123,14 +114,6 @@ public void stopServiceToken(ComponentName componentName, IBinder token, int use } } - public void onStartCommand(Intent proxyIntent, int userId) { - try { - getService().onStartCommand(proxyIntent, userId); - } catch (RemoteException e) { - e.printStackTrace(); - } - } - public UnbindRecord onServiceUnbind(Intent proxyIntent, int userId) { try { return getService().onServiceUnbind(proxyIntent, userId); @@ -175,9 +158,9 @@ public IBinder peekService(Intent intent, String resolvedType, int userId) { return null; } - public void onActivityCreated(int taskId, IBinder token, IBinder activityRecord) { + public void onActivityCreated(int taskId, IBinder token, String activityToken) { try { - getService().onActivityCreated(taskId, token, activityRecord); + getService().onActivityCreated(taskId, token, activityToken); } catch (RemoteException e) { e.printStackTrace(); } @@ -192,8 +175,8 @@ public void onActivityResumed(IBinder token) { activityByToken.getWindow().getDecorView().clearFocus(); } } - } catch (Throwable ignored) { - } + } catch (Throwable ignored) { } + try { getService().onActivityResumed(token); } catch (RemoteException e) { @@ -217,7 +200,7 @@ public void onFinishActivity(IBinder token) { } } - public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int userId) throws RemoteException { + public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int userId) { try { return getService().getRunningAppProcesses(callerPackage, userId); } catch (RemoteException e) { @@ -226,7 +209,7 @@ public RunningAppProcessInfo getRunningAppProcesses(String callerPackage, int us return null; } - public RunningServiceInfo getRunningServices(String callerPackage, int userId) throws RemoteException { + public RunningServiceInfo getRunningServices(String callerPackage, int userId) { try { return getService().getRunningServices(callerPackage, userId); } catch (RemoteException e) { diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BJobManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BJobManager.java similarity index 78% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BJobManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BJobManager.java index 5db50ab..a90c66f 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BJobManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BJobManager.java @@ -1,21 +1,13 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.app.job.JobInfo; import android.os.RemoteException; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.am.IBJobManagerService; -import top.niunaijun.blackbox.entity.JobRecord; +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.am.IBJobManagerService; +import com.vcore.entity.JobRecord; -/** - * Created by Milk on 4/14/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BJobManager extends BlackManager { private static final BJobManager sJobManager = new BJobManager(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BLocationManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BLocationManager.java new file mode 100644 index 0000000..03c0150 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BLocationManager.java @@ -0,0 +1,115 @@ +package com.vcore.fake.frameworks; + +import android.os.IBinder; +import android.os.RemoteException; + +import java.util.ArrayList; +import java.util.List; + +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.location.IBLocationManagerService; +import com.vcore.entity.location.BCell; +import com.vcore.entity.location.BLocation; + +public class BLocationManager extends BlackManager { + private static final BLocationManager sLocationManager = new BLocationManager(); + + public static final int CLOSE_MODE = 0; + public static final int GLOBAL_MODE = 1; + public static final int OWN_MODE = 2; + + public static BLocationManager get() { + return sLocationManager; + } + + @Override + protected String getServiceName() { + return ServiceManager.LOCATION_MANAGER; + } + + public static boolean isFakeLocationEnable() { + return get().getPattern(BActivityThread.getUserId(), BActivityThread.getAppPackageName()) != CLOSE_MODE; + } + + public static void disableFakeLocation(int userId,String pkg) { + get().setPattern(userId, pkg, CLOSE_MODE); + } + + public void setPattern(int userId, String pkg, int pattern) { + try { + getService().setPattern(userId, pkg, pattern); + } catch (RemoteException e) { + e.printStackTrace(); + } + } + + public int getPattern(int userId, String pkg) { + try { + return getService().getPattern(userId, pkg); + } catch (RemoteException e) { + e.printStackTrace(); + } + return CLOSE_MODE; + } + + public List getNeighboringCell(int userId, String pkg) { + try { + return getService().getNeighboringCell(userId, pkg); + } catch (RemoteException e) { + e.printStackTrace(); + } + return null; + } + + public BCell getCell(int userId, String pkg) { + try { + return getService().getCell(userId, pkg); + } catch (RemoteException e) { + e.printStackTrace(); + } + return null; + } + + public List getAllCell(int userId, String pkg) { + try { + return getService().getAllCell(userId, pkg); + } catch (RemoteException e) { + e.printStackTrace(); + } + return new ArrayList<>(); + } + + public void setLocation(int userId, String pkg, BLocation location) { + try { + getService().setLocation(userId, pkg, location); + } catch (RemoteException e) { + e.printStackTrace(); + } + } + + public BLocation getLocation(int userId, String pkg) { + try { + return getService().getLocation(userId, pkg); + } catch (RemoteException e) { + e.printStackTrace(); + } + return null; + } + + public void requestLocationUpdates(IBinder listener) { + try { + getService().requestLocationUpdates(listener, BActivityThread.getAppPackageName(), BActivityThread.getUserId()); + } catch (RemoteException e) { + e.printStackTrace(); + } + } + + public void removeUpdates(IBinder listener) { + try { + getService().removeUpdates(listener); + } catch (RemoteException e) { + e.printStackTrace(); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BNotificationManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BNotificationManager.java similarity index 91% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BNotificationManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BNotificationManager.java index 017592b..7a1bd05 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BNotificationManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BNotificationManager.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.app.Notification; import android.app.NotificationChannel; @@ -8,13 +8,10 @@ import java.util.ArrayList; import java.util.List; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.notification.IBNotificationManagerService; +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.notification.IBNotificationManagerService; -/** - * Created by BlackBox on 2022/3/18. - */ public class BNotificationManager extends BlackManager { private static final BNotificationManager sNotificationManager = new BNotificationManager(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BPackageManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BPackageManager.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BPackageManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BPackageManager.java index 1bc86de..47351d0 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BPackageManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BPackageManager.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.content.ComponentName; import android.content.Intent; @@ -13,22 +13,13 @@ import java.util.Collections; import java.util.List; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.pm.IBPackageManagerService; -import top.niunaijun.blackbox.entity.pm.InstallOption; -import top.niunaijun.blackbox.entity.pm.InstallResult; -import top.niunaijun.blackbox.entity.pm.InstalledPackage; - -/** - * Created by Milk on 4/14/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.pm.IBPackageManagerService; +import com.vcore.entity.pm.InstallOption; +import com.vcore.entity.pm.InstallResult; + public class BPackageManager extends BlackManager { private static final BPackageManager sPackageManager = new BPackageManager(); @@ -45,29 +36,25 @@ public Intent getLaunchIntentForPackage(String packageName, int userId) { Intent intentToResolve = new Intent(Intent.ACTION_MAIN); intentToResolve.addCategory(Intent.CATEGORY_INFO); intentToResolve.setPackage(packageName); - List ris = queryIntentActivities(intentToResolve, - 0, - intentToResolve.resolveTypeIfNeeded(BlackBoxCore.getContext().getContentResolver()), - userId); + List ris = queryIntentActivities(intentToResolve, 0, + intentToResolve.resolveTypeIfNeeded(BlackBoxCore.getContext().getContentResolver()), userId); // Otherwise, try to find a main launcher activity. if (ris == null || ris.size() <= 0) { - // reuse the intent instance + // Reuse the intent instance. intentToResolve.removeCategory(Intent.CATEGORY_INFO); intentToResolve.addCategory(Intent.CATEGORY_LAUNCHER); intentToResolve.setPackage(packageName); - ris = queryIntentActivities(intentToResolve, - 0, - intentToResolve.resolveTypeIfNeeded(BlackBoxCore.getContext().getContentResolver()), - userId); + ris = queryIntentActivities(intentToResolve, 0, intentToResolve.resolveTypeIfNeeded(BlackBoxCore.getContext().getContentResolver()), userId); } + if (ris == null || ris.size() <= 0) { return null; } + Intent intent = new Intent(intentToResolve); intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK); - intent.setClassName(ris.get(0).activityInfo.packageName, - ris.get(0).activityInfo.name); + intent.setClassName(ris.get(0).activityInfo.packageName, ris.get(0).activityInfo.name); return intent; } @@ -116,6 +103,15 @@ public ApplicationInfo getApplicationInfo(String packageName, int flags, int use return null; } + public int getUidByPid(int pid) { + try { + return getService().getUidByPid(pid); + } catch (RemoteException e) { + crash(e); + } + return -1; + } + public PackageInfo getPackageInfo(String packageName, int flags, int userId) { try { return getService().getPackageInfo(packageName, flags, userId); @@ -256,15 +252,6 @@ public boolean isInstalled(String packageName, int userId) { return false; } - public List getInstalledPackagesAsUser(int userId) { - try { - return getService().getInstalledPackagesAsUser(userId); - } catch (RemoteException e) { - e.printStackTrace(); - } - return Collections.emptyList(); - } - public String[] getPackagesForUid(int uid) { try { return getService().getPackagesForUid(uid, BActivityThread.getUserId()); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BStorageManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BStorageManager.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BStorageManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BStorageManager.java index aa9a895..0b292bd 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BStorageManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BStorageManager.java @@ -1,20 +1,12 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.net.Uri; import android.os.RemoteException; import android.os.storage.StorageVolume; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.os.IBStorageManagerService; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.os.IBStorageManagerService; -/** - * Created by Milk on 4/14/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BStorageManager extends BlackManager { private static final BStorageManager sStorageManager = new BStorageManager(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BUserManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BUserManager.java similarity index 75% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BUserManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BUserManager.java index f2497af..ae402fe 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BUserManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BUserManager.java @@ -1,22 +1,14 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.os.RemoteException; import java.util.Collections; import java.util.List; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.user.BUserInfo; -import top.niunaijun.blackbox.core.system.user.IBUserManagerService; - -/** - * Created by Milk on 4/28/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.user.BUserInfo; +import com.vcore.core.system.user.IBUserManagerService; + public class BUserManager extends BlackManager { private static final BUserManager sUserManager = new BUserManager(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BXposedManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BXposedManager.java similarity index 81% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BXposedManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BXposedManager.java index d0df1e7..af0ae0c 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BXposedManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BXposedManager.java @@ -1,22 +1,14 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.os.RemoteException; import java.util.Collections; import java.util.List; -import top.niunaijun.blackbox.core.system.ServiceManager; -import top.niunaijun.blackbox.core.system.pm.IBXposedManagerService; -import top.niunaijun.blackbox.entity.pm.InstalledModule; +import com.vcore.core.system.ServiceManager; +import com.vcore.core.system.pm.IBXposedManagerService; +import com.vcore.entity.pm.InstalledModule; -/** - * Created by Milk on 5/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class BXposedManager extends BlackManager { private static final BXposedManager sXposedManager = new BXposedManager(); diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BlackManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BlackManager.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BlackManager.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BlackManager.java index 75f5ad8..093866f 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/frameworks/BlackManager.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/frameworks/BlackManager.java @@ -1,16 +1,13 @@ -package top.niunaijun.blackbox.fake.frameworks; +package com.vcore.fake.frameworks; import android.os.IBinder; import android.os.IInterface; import java.lang.reflect.ParameterizedType; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.utils.Reflector; +import black.Reflector; +import com.vcore.BlackBoxCore; -/** - * Created by BlackBox on 2022/3/23. - */ public abstract class BlackManager { public static final String TAG = "BlackManager"; @@ -23,8 +20,9 @@ public Service getService() { return mService; } try { - mService = Reflector.on(getTClass().getName() + "$Stub").method("asInterface", IBinder.class) - .call(BlackBoxCore.get().getService(getServiceName())); + // 通过反射调用T.Stub.asInterface + mService = Reflector.on(getTClass().getName() + "$Stub").staticMethod("asInterface", IBinder.class) + .callWithClass(BlackBoxCore.get().getService(getServiceName())); mService.asBinder().linkToDeath(new IBinder.DeathRecipient() { @Override public void binderDied() { @@ -42,4 +40,4 @@ public void binderDied() { private Class getTClass() { return (Class) ((ParameterizedType) getClass().getGenericSuperclass()).getActualTypeArguments()[0]; } -} +} \ No newline at end of file diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/BinderInvocationStub.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/BinderInvocationStub.java similarity index 83% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/BinderInvocationStub.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/BinderInvocationStub.java index fa01671..0ce6126 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/BinderInvocationStub.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/BinderInvocationStub.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.hook; +package com.vcore.fake.hook; import android.os.IBinder; import android.os.IInterface; @@ -11,26 +11,17 @@ import java.io.FileDescriptor; import java.util.Map; -import black.android.os.BRServiceManager; +import black.android.os.ServiceManager; -/** - * Created by Milk on 3/30/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public abstract class BinderInvocationStub extends ClassInvocationStub implements IBinder { - private IBinder mBaseBinder; + private final IBinder mBaseBinder; public BinderInvocationStub(IBinder baseBinder) { - mBaseBinder = baseBinder; + this.mBaseBinder = baseBinder; } @Override - protected void onBindMethod() { - } + protected void onBindMethod() { } @Nullable @Override @@ -79,9 +70,8 @@ public boolean unlinkToDeath(@NonNull DeathRecipient recipient, int flags) { return mBaseBinder.unlinkToDeath(recipient, flags); } - protected void replaceSystemService(String name) { - Map services = BRServiceManager.get().sCache(); + Map services = ServiceManager.sCache.get(); services.put(name, this); } } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/ClassInvocationStub.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ClassInvocationStub.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/ClassInvocationStub.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ClassInvocationStub.java index f9c6f14..ab59c25 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/hook/ClassInvocationStub.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ClassInvocationStub.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.hook; +package com.vcore.fake.hook; import android.text.TextUtils; @@ -7,17 +7,11 @@ import java.lang.reflect.Proxy; import java.util.HashMap; import java.util.Map; +import java.util.Objects; -import top.niunaijun.blackbox.utils.MethodParameterUtils; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.Slog; -/** - * Created by Milk on 3/30/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public abstract class ClassInvocationStub implements InvocationHandler, IInjectHook { public static final String TAG = ClassInvocationStub.class.getSimpleName(); @@ -30,20 +24,14 @@ public abstract class ClassInvocationStub implements InvocationHandler, IInjectH protected abstract void inject(Object baseInvocation, Object proxyInvocation); - protected void onBindMethod() { + protected void onBindMethod() { } - } - - protected Object getProxyInvocation() { + public Object getProxyInvocation() { return mProxyInvocation; } - protected Object getBase() { - return mBase; - } - - protected void onlyProxy(boolean o) { - onlyProxy = o; + protected void onlyProxy(boolean onlyStatus) { + onlyProxy = onlyStatus; } @Override @@ -59,6 +47,7 @@ public void injectHook() { for (Class declaredClass : declaredClasses) { initAnnotation(declaredClass); } + ScanClass scanClass = this.getClass().getAnnotation(ScanClass.class); if (scanClass != null) { for (Class aClass : scanClass.value()) { @@ -70,6 +59,7 @@ public void injectHook() { } protected void initAnnotation(Class clazz) { + // Get proxy method annotation. ProxyMethod proxyMethod = clazz.getAnnotation(ProxyMethod.class); if (proxyMethod != null) { final String name = proxyMethod.value(); @@ -81,6 +71,7 @@ protected void initAnnotation(Class clazz) { } } } + ProxyMethods proxyMethods = clazz.getAnnotation(ProxyMethods.class); if (proxyMethods != null) { String[] value = proxyMethods.value(); @@ -107,9 +98,10 @@ public Object invoke(Object proxy, Method method, Object[] args) throws Throwabl MethodHook methodHook = mMethodHookMap.get(method.getName()); if (methodHook == null || !methodHook.isEnable()) { try { + //Slog.e(TAG, mBase.getClass().getName() + ", " + method.getName()); return method.invoke(mBase, args); } catch (Throwable e) { - throw e.getCause(); + throw Objects.requireNonNull(e.getCause()); } } @@ -117,6 +109,7 @@ public Object invoke(Object proxy, Method method, Object[] args) throws Throwabl if (result != null) { return result; } + result = methodHook.hook(mBase, method, args); result = methodHook.afterHook(result); return result; diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/HookManager.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/HookManager.java new file mode 100644 index 0000000..5922f87 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/HookManager.java @@ -0,0 +1,216 @@ +package com.vcore.fake.hook; + +import android.util.Log; + +import java.util.HashMap; +import java.util.Map; + +import black.oem.flyme.IFlymePermissionService; +import black.oem.vivo.IPhysicalFlingManager; +import black.oem.vivo.IPopupCameraManager; +import black.oem.vivo.ISuperResolutionManager; +import black.oem.vivo.ISystemDefenceManager; +import black.oem.vivo.IVivoPermissonService; +import com.vcore.BlackBoxCore; +import com.vcore.fake.delegate.AppInstrumentation; +import com.vcore.fake.service.BuildProxy; +import com.vcore.fake.service.HCallbackProxy; +import com.vcore.fake.service.IAccessibilityManagerProxy; +import com.vcore.fake.service.IAccountManagerProxy; +import com.vcore.fake.service.IActivityClientProxy; +import com.vcore.fake.service.IActivityManagerProxy; +import com.vcore.fake.service.IActivityTaskManagerProxy; +import com.vcore.fake.service.IAlarmManagerProxy; +import com.vcore.fake.service.IAppOpsManagerProxy; +import com.vcore.fake.service.IAppWidgetManagerProxy; +import com.vcore.fake.service.IAutofillManagerProxy; +import com.vcore.fake.service.IBluetoothManagerProxy; +import com.vcore.fake.service.IConnectivityManagerProxy; +import com.vcore.fake.service.IContextHubServiceProxy; +import com.vcore.fake.service.IDeviceIdentifiersPolicyProxy; +import com.vcore.fake.service.IDevicePolicyManagerProxy; +import com.vcore.fake.service.IDisplayManagerProxy; +import com.vcore.fake.service.IFingerprintManagerProxy; +import com.vcore.fake.service.IFlymePermissionServiceProxy; +import com.vcore.fake.service.IGraphicsStatsProxy; +import com.vcore.fake.service.IJobServiceProxy; +import com.vcore.fake.service.ILauncherAppsProxy; +import com.vcore.fake.service.ILocationManagerProxy; +import com.vcore.fake.service.IMediaRouterServiceProxy; +import com.vcore.fake.service.IMediaSessionManagerProxy; +import com.vcore.fake.service.INetworkManagementServiceProxy; +import com.vcore.fake.service.INotificationManagerProxy; +import com.vcore.fake.service.IPackageManagerProxy; +import com.vcore.fake.service.IPermissionManagerProxy; +import com.vcore.fake.service.IPersistentDataBlockServiceProxy; +import com.vcore.fake.service.IPhoneSubInfoProxy; +import com.vcore.fake.service.IPhysicalFlingManagerProxy; +import com.vcore.fake.service.IPopupCameraManagerProxy; +import com.vcore.fake.service.IPowerManagerProxy; +import com.vcore.fake.service.IRoleManagerProxy; +import com.vcore.fake.service.ISearchManagerProxy; +import com.vcore.fake.service.IShortcutManagerProxy; +import com.vcore.fake.service.IStorageManagerProxy; +import com.vcore.fake.service.IStorageStatsManagerProxy; +import com.vcore.fake.service.ISubProxy; +import com.vcore.fake.service.ISuperResolutionManagerProxy; +import com.vcore.fake.service.ISystemDefenceManagerProxy; +import com.vcore.fake.service.ISystemUpdateProxy; +import com.vcore.fake.service.ITelephonyManagerProxy; +import com.vcore.fake.service.ITelephonyRegistryProxy; +import com.vcore.fake.service.IUserManagerProxy; +import com.vcore.fake.service.IVibratorServiceProxy; +import com.vcore.fake.service.IVivoPermissionServiceProxy; +import com.vcore.fake.service.IVpnManagerProxy; +import com.vcore.fake.service.IWifiManagerProxy; +import com.vcore.fake.service.IWifiScannerProxy; +import com.vcore.fake.service.IWindowManagerProxy; +import com.vcore.fake.service.context.ContentServiceProxy; +import com.vcore.fake.service.context.RestrictionsManagerProxy; +import com.vcore.fake.service.libcore.OsProxy; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BuildCompat; + +public class HookManager { + public static final String TAG = "HookManager"; + + private static final HookManager sHookManager = new HookManager(); + private final Map, IInjectHook> mInjectors = new HashMap<>(); + + public static HookManager get() { + return sHookManager; + } + + public void init() { + if (BlackBoxCore.get().isBlackProcess() || BlackBoxCore.get().isServerProcess()) { + addInjector(new IDisplayManagerProxy()); + addInjector(new OsProxy()); + + addInjector(new ILocationManagerProxy()); + // AM and PM hook + addInjector(new IActivityManagerProxy()); + addInjector(new IPackageManagerProxy()); + addInjector(new ITelephonyManagerProxy()); + addInjector(new HCallbackProxy()); + + /* + * It takes time to test and enhance the compatibility of WifiManager + * (only tested in Android 10). + * commented by BlackBoxing at 2022/03/08 + * */ + addInjector(new IWifiManagerProxy()); + addInjector(new IWifiScannerProxy()); + addInjector(new IBluetoothManagerProxy()); + + addInjector(new ISubProxy()); + addInjector(new IAppOpsManagerProxy()); + addInjector(new INotificationManagerProxy()); + addInjector(new IAlarmManagerProxy()); + addInjector(new IAppWidgetManagerProxy()); + addInjector(new ContentServiceProxy()); + addInjector(new IWindowManagerProxy()); + addInjector(new IUserManagerProxy()); + addInjector(new RestrictionsManagerProxy()); + addInjector(new IMediaSessionManagerProxy()); + addInjector(new IStorageManagerProxy()); + addInjector(new ILauncherAppsProxy()); + addInjector(new IJobServiceProxy()); + addInjector(new IAccessibilityManagerProxy()); + addInjector(new ITelephonyRegistryProxy()); + addInjector(new IDevicePolicyManagerProxy()); + addInjector(new IAccountManagerProxy()); + addInjector(new ISearchManagerProxy()); + addInjector(new IConnectivityManagerProxy()); + addInjector(new IPhoneSubInfoProxy()); + addInjector(new IMediaRouterServiceProxy()); + addInjector(new IPowerManagerProxy()); + addInjector(new IVibratorServiceProxy()); + addInjector(new IPersistentDataBlockServiceProxy()); + addInjector(AppInstrumentation.get()); + + addInjector(new BuildProxy()); + // 12.0 + if (BuildCompat.isS()) { + addInjector(new IActivityClientProxy(null)); + addInjector(new IVpnManagerProxy()); + } + // 11.0 + if (BuildCompat.isR()) { + addInjector(new IPermissionManagerProxy()); + } + // 10.0 + if (BuildCompat.isQ()) { + addInjector(new IDeviceIdentifiersPolicyProxy()); + addInjector(new IRoleManagerProxy()); + addInjector(new IActivityTaskManagerProxy()); + } + // 9.0 + if (BuildCompat.isPie()) { + addInjector(new ISystemUpdateProxy()); + } + //fix flyme service + if (IFlymePermissionService.TYPE != null) { + addInjector(new IFlymePermissionServiceProxy()); + } + // 8.0 + if (BuildCompat.isOreo()) { + addInjector(new IAutofillManagerProxy()); + addInjector(new IStorageStatsManagerProxy()); + } + // 7.0 + if (BuildCompat.isN()) { + addInjector(new IContextHubServiceProxy()); + addInjector(new INetworkManagementServiceProxy()); + addInjector(new IShortcutManagerProxy()); + } + // 6.0 + if (BuildCompat.isM()) { + addInjector(new IFingerprintManagerProxy()); + addInjector(new IGraphicsStatsProxy()); + } + // 5.0 + if (BuildCompat.isL()) { + addInjector(new IJobServiceProxy()); + } + if (IPhysicalFlingManager.TYPE != null) { + addInjector(new IPhysicalFlingManagerProxy()); + } + if (IPopupCameraManager.TYPE != null) { + addInjector(new IPopupCameraManagerProxy()); + } + if (ISuperResolutionManager.TYPE != null) { + addInjector(new ISuperResolutionManagerProxy()); + } + if (ISystemDefenceManager.TYPE != null) { + addInjector(new ISystemDefenceManagerProxy()); + } + if (IVivoPermissonService.TYPE != null) { + addInjector(new IVivoPermissionServiceProxy()); + } + } + injectAll(); + } + + public void checkEnv(Class clazz) { + IInjectHook iInjectHook = mInjectors.get(clazz); + if (iInjectHook != null && iInjectHook.isBadEnv()) { + Log.d(TAG, "checkEnv: " + clazz.getSimpleName() + " is bad env"); + iInjectHook.injectHook(); + } + } + + void addInjector(IInjectHook injectHook) { + mInjectors.put(injectHook.getClass(), injectHook); + } + + void injectAll() { + for (IInjectHook value : mInjectors.values()) { + try { + Slog.d(TAG, "hook: " + value); + value.injectHook(); + } catch (Exception e) { + Slog.d(TAG, "hook error: " + value + " " + e.getMessage()); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/IInjectHook.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/IInjectHook.java new file mode 100644 index 0000000..744e5d2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/IInjectHook.java @@ -0,0 +1,7 @@ +package com.vcore.fake.hook; + +public interface IInjectHook { + void injectHook(); + + boolean isBadEnv(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/MethodHook.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/MethodHook.java new file mode 100644 index 0000000..80efe1b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/MethodHook.java @@ -0,0 +1,25 @@ +package com.vcore.fake.hook; + +import java.lang.reflect.Method; + +import com.vcore.BlackBoxCore; + +public abstract class MethodHook { + protected String getMethodName() { + return null; + } + + protected Object afterHook(Object result) { + return result; + } + + protected Object beforeHook(Object who, Method method, Object[] args) throws Throwable { + return null; + } + + protected abstract Object hook(Object who, Method method, Object[] args) throws Throwable; + + protected boolean isEnable() { + return BlackBoxCore.get().isBlackProcess(); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethod.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethod.java new file mode 100644 index 0000000..d3bad7f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethod.java @@ -0,0 +1,12 @@ +package com.vcore.fake.hook; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target(ElementType.TYPE) +@Retention(RetentionPolicy.RUNTIME) +public @interface ProxyMethod { + String value(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethods.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethods.java new file mode 100644 index 0000000..f5e61a4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ProxyMethods.java @@ -0,0 +1,12 @@ +package com.vcore.fake.hook; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target(ElementType.TYPE) +@Retention(RetentionPolicy.RUNTIME) +public @interface ProxyMethods { + String[] value() default {}; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ScanClass.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ScanClass.java new file mode 100644 index 0000000..24df877 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/hook/ScanClass.java @@ -0,0 +1,12 @@ +package com.vcore.fake.hook; + +import java.lang.annotation.ElementType; +import java.lang.annotation.Retention; +import java.lang.annotation.RetentionPolicy; +import java.lang.annotation.Target; + +@Target(ElementType.TYPE) +@Retention(RetentionPolicy.RUNTIME) +public @interface ScanClass { + Class[] value() default {}; +} \ No newline at end of file diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/provider/FileProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProvider.java similarity index 90% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/provider/FileProvider.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProvider.java index d790d58..64d036d 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/provider/FileProvider.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProvider.java @@ -1,4 +1,7 @@ -package top.niunaijun.blackbox.fake.provider; +package com.vcore.fake.provider; + +import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; +import static org.xmlpull.v1.XmlPullParser.START_TAG; import android.content.ContentProvider; import android.content.ContentValues; @@ -27,23 +30,12 @@ import java.util.HashMap; import java.util.Map; -import static org.xmlpull.v1.XmlPullParser.END_DOCUMENT; -import static org.xmlpull.v1.XmlPullParser.START_TAG; - -/** - * Created by Milk on 4/18/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class FileProvider extends ContentProvider { private static final String[] COLUMNS = { - OpenableColumns.DISPLAY_NAME, OpenableColumns.SIZE }; + OpenableColumns.DISPLAY_NAME, OpenableColumns.SIZE + }; - private static final String - META_DATA_FILE_PROVIDER_PATHS = "android.support.FILE_PROVIDER_PATHS"; + private static final String META_DATA_FILE_PROVIDER_PATHS = "android.support.FILE_PROVIDER_PATHS"; private static final String TAG_ROOT_PATH = "root-path"; private static final String TAG_FILES_PATH = "files-path"; @@ -58,7 +50,7 @@ public class FileProvider extends ContentProvider { private static final File DEVICE_ROOT = new File("/"); - private static HashMap sCache = new HashMap(); + private static final HashMap sCache = new HashMap<>(); private PathStrategy mStrategy; @@ -89,7 +81,6 @@ public void attachInfo(Context context, ProviderInfo info) { if (!info.grantUriPermissions) { throw new SecurityException("Provider must grant uri permissions"); } - mStrategy = getPathStrategy(context, info.authority); } @@ -113,14 +104,12 @@ public void attachInfo(Context context, ProviderInfo info) { * @throws IllegalArgumentException When the given {@link File} is outside * the paths supported by the provider. */ - public static Uri getUriForFile(Context context, String authority, - File file) { + public static Uri getUriForFile(Context context, String authority, File file) { final PathStrategy strategy = getPathStrategy(context, authority); return strategy.getUriForFile(file); } - public static File getFileForUri(Context context, String authority, - Uri uri) { + public static File getFileForUri(Context context, String authority, Uri uri) { final PathStrategy strategy = getPathStrategy(context, authority); return strategy.getFileForUri(uri); } @@ -154,9 +143,7 @@ public static File getFileForUri(Context context, String authority, * */ @Override - public Cursor query(Uri uri, String[] projection, String selection, - String[] selectionArgs, - String sortOrder) { + public Cursor query(Uri uri, String[] projection, String selection, String[] selectionArgs, String sortOrder) { // ContentProvider has already checked granted permissions final File file = mStrategy.getFileForUri(uri); @@ -207,7 +194,6 @@ public String getType(Uri uri) { return mime; } } - return "application/octet-stream"; } @@ -225,8 +211,7 @@ public Uri insert(Uri uri, ContentValues values) { * subclass FileProvider if you want to provide different functionality. */ @Override - public int update(Uri uri, ContentValues values, String selection, - String[] selectionArgs) { + public int update(Uri uri, ContentValues values, String selection, String[] selectionArgs) { throw new UnsupportedOperationException("No external updates"); } @@ -242,8 +227,7 @@ public int update(Uri uri, ContentValues values, String selection, * @return 1 if the delete succeeds; otherwise, 0. */ @Override - public int delete(Uri uri, String selection, - String[] selectionArgs) { + public int delete(Uri uri, String selection, String[] selectionArgs) { // ContentProvider has already checked granted permissions final File file = mStrategy.getFileForUri(uri); return file.delete() ? 1 : 0; @@ -265,8 +249,7 @@ public int delete(Uri uri, String selection, * @return A new {@link ParcelFileDescriptor} with which you can access the file. */ @Override - public ParcelFileDescriptor openFile(Uri uri, String mode) - throws FileNotFoundException { + public ParcelFileDescriptor openFile(Uri uri, String mode) throws FileNotFoundException { // ContentProvider has already checked granted permissions final File file = mStrategy.getFileForUri(uri); final int fileMode = modeToMode(mode); @@ -284,12 +267,8 @@ private static PathStrategy getPathStrategy(Context context, String authority) { if (strat == null) { try { strat = parsePathStrategy(context, authority); - } catch (IOException e) { - throw new IllegalArgumentException( - "Failed to parse " + META_DATA_FILE_PROVIDER_PATHS + " meta-data", e); - } catch (XmlPullParserException e) { - throw new IllegalArgumentException( - "Failed to parse " + META_DATA_FILE_PROVIDER_PATHS + " meta-data", e); + } catch (IOException | XmlPullParserException e) { + throw new IllegalArgumentException("Failed to parse " + META_DATA_FILE_PROVIDER_PATHS + " meta-data", e); } sCache.put(authority, strat); } @@ -305,20 +284,17 @@ private static PathStrategy getPathStrategy(Context context, String authority) { */ private static PathStrategy parsePathStrategy(Context context, String authority) throws IOException, XmlPullParserException { - final SimplePathStrategy strat = new SimplePathStrategy(authority); + final SimplePathStrategy simplePathStrategy = new SimplePathStrategy(authority); final ProviderInfo info = context.getPackageManager() .resolveContentProvider(authority, PackageManager.GET_META_DATA); if (info == null) { - throw new IllegalArgumentException( - "Couldn't find meta-data for provider with authority " + authority); + throw new IllegalArgumentException("Couldn't find meta-data for provider with authority " + authority); } - final XmlResourceParser in = info.loadXmlMetaData( - context.getPackageManager(), META_DATA_FILE_PROVIDER_PATHS); + final XmlResourceParser in = info.loadXmlMetaData(context.getPackageManager(), META_DATA_FILE_PROVIDER_PATHS); if (in == null) { - throw new IllegalArgumentException( - "Missing " + META_DATA_FILE_PROVIDER_PATHS + " meta-data"); + throw new IllegalArgumentException("Missing " + META_DATA_FILE_PROVIDER_PATHS + " meta-data"); } int type; @@ -357,12 +333,11 @@ private static PathStrategy parsePathStrategy(Context context, String authority) } if (target != null) { - strat.addRoot(name, buildPath(target, path)); + simplePathStrategy.addRoot(name, buildPath(target, path)); } } } - - return strat; + return simplePathStrategy; } /** @@ -402,7 +377,7 @@ interface PathStrategy { */ static class SimplePathStrategy implements PathStrategy { private final String mAuthority; - private final HashMap mRoots = new HashMap(); + private final HashMap mRoots = new HashMap<>(); SimplePathStrategy(String authority) { mAuthority = authority; @@ -424,7 +399,6 @@ void addRoot(String name, File root) { throw new IllegalArgumentException( "Failed to resolve canonical path for " + root, e); } - mRoots.put(name, root); } @@ -441,15 +415,13 @@ public Uri getUriForFile(File file) { Map.Entry mostSpecific = null; for (Map.Entry root : mRoots.entrySet()) { final String rootPath = root.getValue().getPath(); - if (path.startsWith(rootPath) && (mostSpecific == null - || rootPath.length() > mostSpecific.getValue().getPath().length())) { + if (path.startsWith(rootPath) && (mostSpecific == null || rootPath.length() > mostSpecific.getValue().getPath().length())) { mostSpecific = root; } } if (mostSpecific == null) { - throw new IllegalArgumentException( - "Failed to find configured root that contains " + path); + throw new IllegalArgumentException("Failed to find configured root that contains " + path); } // Start at first char of path under root @@ -489,7 +461,6 @@ public File getFileForUri(Uri uri) { if (!file.getPath().startsWith(root.getPath())) { throw new SecurityException("Resolved path jumped beyond configured root"); } - return file; } } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProviderHandler.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProviderHandler.java new file mode 100644 index 0000000..4ea44b1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/provider/FileProviderHandler.java @@ -0,0 +1,38 @@ +package com.vcore.fake.provider; + +import android.content.Context; +import android.content.pm.ProviderInfo; +import android.net.Uri; + +import java.io.File; +import java.util.List; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.utils.compat.BuildCompat; + +public class FileProviderHandler { + public static Uri convertFileUri(Context context, Uri uri) { + if (BuildCompat.isN()) { + File file = convertFile(context, uri); + if (file == null) { + return null; + } + return BlackBoxCore.getBStorageManager().getUriForFile(file.getAbsolutePath()); + } + return uri; + } + + public static File convertFile(Context context, Uri uri) { + List providers = BActivityThread.getProviders(); + for (ProviderInfo provider : providers) { + try { + File fileForUri = FileProvider.getFileForUri(context, provider.authority, uri); + if (fileForUri != null && fileForUri.exists()) { + return fileForUri; + } + } catch (Exception ignored) { } + } + return null; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ActivityManagerCommonProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ActivityManagerCommonProxy.java new file mode 100644 index 0000000..4e8484d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ActivityManagerCommonProxy.java @@ -0,0 +1,307 @@ +package com.vcore.fake.service; + +import static android.content.pm.PackageManager.GET_META_DATA; + +import android.content.ComponentName; +import android.content.Intent; +import android.content.pm.ResolveInfo; +import android.net.Uri; +import android.os.Bundle; +import android.os.IBinder; + +import java.io.File; +import java.lang.reflect.Method; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.provider.FileProviderHandler; +import com.vcore.utils.ComponentUtils; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BuildCompat; + +public class ActivityManagerCommonProxy { + public static final String TAG = "ActivityManagerCommonProxy"; + + @ProxyMethod("startActivity") + public static class StartActivity extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + Intent intent = getIntent(args); + + Slog.d(TAG, "Hook in : " + intent); + assert intent != null; + if (intent.getParcelableExtra("_B_|_target_") != null) { + return method.invoke(who, args); + } + + if (ComponentUtils.isRequestInstall(intent)) { + File file = FileProviderHandler.convertFile(BActivityThread.getApplication(), intent.getData()); + if (BlackBoxCore.get().requestInstallPackage(file, BActivityThread.getUserId())) { + return 0; + } + + intent.setData(FileProviderHandler.convertFileUri(BActivityThread.getApplication(), intent.getData())); + return method.invoke(who, args); + } + + String dataString = intent.getDataString(); + if (dataString != null && dataString.equals("package:" + BActivityThread.getAppPackageName())) { + intent.setData(Uri.parse("package:" + BlackBoxCore.getHostPkg())); + } + + ResolveInfo resolveInfo = BlackBoxCore.getBPackageManager().resolveActivity(intent, GET_META_DATA, getResolvedType(args), + BActivityThread.getUserId()); + if (resolveInfo == null) { + String origPackage = intent.getPackage(); + if (intent.getPackage() == null && intent.getComponent() == null) { + intent.setPackage(BActivityThread.getAppPackageName()); + } else { + origPackage = intent.getPackage(); + } + + resolveInfo = BlackBoxCore.getBPackageManager().resolveActivity(intent, GET_META_DATA, getResolvedType(args), + BActivityThread.getUserId()); + if (resolveInfo == null) { + intent.setPackage(origPackage); + return method.invoke(who, args); + } + } + + intent.setExtrasClassLoader(who.getClass().getClassLoader()); + intent.setComponent(new ComponentName(resolveInfo.activityInfo.packageName, resolveInfo.activityInfo.name)); + BlackBoxCore.getBActivityManager().startActivityAms(BActivityThread.getUserId(), getIntent(args), + getResolvedType(args), getResultTo(args), getResultWho(args), + getRequestCode(args), getFlags(args), getOptions(args)); + return 0; + } + + private Intent getIntent(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 3; + } else { + index = 2; + } + + if (args[index] instanceof Intent) { + return (Intent) args[index]; + } + + for (Object arg : args) { + if (arg instanceof Intent) { + return (Intent) arg; + } + } + return null; + } + + private String getResolvedType(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 4; + } else { + index = 3; + } + + if (args[index] instanceof String) { + return (String) args[index]; + } + + for (Object arg : args) { + if (arg instanceof String) { + return (String) arg; + } + } + return null; + } + + private IBinder getResultTo(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 5; + } else { + index = 4; + } + + if (args[index] instanceof IBinder) { + return (IBinder) args[index]; + } + + for (Object arg : args) { + if (arg instanceof IBinder) { + return (IBinder) arg; + } + } + return null; + } + + private String getResultWho(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 6; + } else { + index = 5; + } + + if (args[index] instanceof String) { + return (String) args[index]; + } + + for (Object arg : args) { + if (arg instanceof String) { + return (String) arg; + } + } + return null; + } + + private int getRequestCode(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 7; + } else { + index = 6; + } + + if (args[index] instanceof Integer) { + return (Integer) args[index]; + } + + for (Object arg : args) { + if (arg instanceof Integer) { + return (Integer) arg; + } + } + return 0; + } + + private int getFlags(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 8; + } else { + index = 7; + } + + if (args[index] instanceof Integer) { + return (Integer) args[index]; + } + + for (Object arg : args) { + if (arg instanceof Integer) { + return (Integer) arg; + } + } + return 0; + } + + private Bundle getOptions(Object[] args) { + int index; + if (BuildCompat.isR()) { + index = 9; + } else { + index = 8; + } + + if (args[index] instanceof Bundle) { + return (Bundle) args[index]; + } + + for (Object arg : args) { + if (arg instanceof Bundle) { + return (Bundle) arg; + } + } + return null; + } + } + + @ProxyMethod("startActivities") + public static class StartActivities extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int index = getIntents(); + Intent[] intents = (Intent[]) args[index++]; + String[] resolvedTypes = (String[]) args[index++]; + IBinder resultTo = (IBinder) args[index++]; + Bundle options = (Bundle) args[index]; + + if (!ComponentUtils.isSelf(intents)) { + return method.invoke(who, args); + } + + for (Intent intent : intents) { + intent.setExtrasClassLoader(who.getClass().getClassLoader()); + } + return BlackBoxCore.getBActivityManager().startActivities(BActivityThread.getUserId(), intents, resolvedTypes, resultTo, options); + } + + public int getIntents() { + return 2; + } + } + + @ProxyMethod("activityResumed") + public static class ActivityResumed extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + BlackBoxCore.getBActivityManager().onActivityResumed((IBinder) args[0]); + return method.invoke(who, args); + } + } + + @ProxyMethod("activityDestroyed") + public static class ActivityDestroyed extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + BlackBoxCore.getBActivityManager().onActivityDestroyed((IBinder) args[0]); + return method.invoke(who, args); + } + } + + @ProxyMethod("finishActivity") + public static class FinishActivity extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + BlackBoxCore.getBActivityManager().onFinishActivity((IBinder) args[0]); + return method.invoke(who, args); + } + } + + @ProxyMethod("getAppTasks") + public static class GetAppTasks extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("getCallingPackage") + public static class GetCallingPackage extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return BlackBoxCore.getBActivityManager().getCallingPackage((IBinder) args[0], BActivityThread.getUserId()); + } + } + + @ProxyMethod("getCallingActivity") + public static class GetCallingActivity extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return BlackBoxCore.getBActivityManager().getCallingActivity((IBinder) args[0], BActivityThread.getUserId()); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/BuildProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/BuildProxy.java new file mode 100644 index 0000000..2401999 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/BuildProxy.java @@ -0,0 +1,33 @@ +package com.vcore.fake.service; + +import black.android.os.Build; +import com.vcore.fake.hook.ClassInvocationStub; + +public class BuildProxy extends ClassInvocationStub { + + @Override + protected Object getWho() { + return Build.REF; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + Build.BOARD.set("umi"); + Build.BRAND.set("Xiaomi"); + Build.DEVICE.set("umi"); + Build.DISPLAY.set("QKQ1.191117.002 test-keys"); + Build.HOST.set("c5-miui-ota-bd074.bj"); + Build.ID.set("QKQ1.191117.002"); + Build.MANUFACTURER.set("Xiaomi"); + Build.MODEL.set("Mi 10"); + Build.PRODUCT.set("umi"); + Build.TAGS.set("release-keys"); + Build.TYPE.set("user"); + Build.USER.set("builder"); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/HCallbackProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/HCallbackProxy.java new file mode 100644 index 0000000..1dc8c5a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/HCallbackProxy.java @@ -0,0 +1,213 @@ +package com.vcore.fake.service; + +import android.content.ComponentName; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ServiceInfo; +import android.os.Build; +import android.os.Handler; +import android.os.IBinder; +import android.os.Message; + +import androidx.annotation.NonNull; + +import java.lang.reflect.Proxy; +import java.util.List; +import java.util.concurrent.atomic.AtomicBoolean; + +import black.android.app.ActivityClient; +import black.android.app.ActivityManagerNative; +import black.android.app.ActivityThread; +import black.android.app.IActivityManager; +import black.android.app.servertransaction.ClientTransaction; +import black.android.app.servertransaction.LaunchActivityItem; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.IInjectHook; +import com.vcore.proxy.ProxyManifest; +import com.vcore.proxy.record.ProxyActivityRecord; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BuildCompat; + +public class HCallbackProxy implements IInjectHook, Handler.Callback { + public static final String TAG = "HCallbackProxy"; + private Handler.Callback mOtherCallback; + private final AtomicBoolean mBeing = new AtomicBoolean(false); + + private Handler.Callback getHCallback() { + return black.android.os.Handler.mCallback.get(getH()); + } + + private Handler getH() { + Object currentActivityThread = BlackBoxCore.mainThread(); + return ActivityThread.mH.get(currentActivityThread); + } + + @Override + public void injectHook() { + mOtherCallback = getHCallback(); + if (mOtherCallback != null && (mOtherCallback == this || mOtherCallback.getClass().getName().equals(this.getClass().getName()))) { + mOtherCallback = null; + } + black.android.os.Handler.mCallback.set(getH(), this); + } + + @Override + public boolean isBadEnv() { + Handler.Callback hCallback = getHCallback(); + return hCallback != null && hCallback != this; + } + + @Override + public boolean handleMessage(@NonNull Message msg) { + if (!mBeing.getAndSet(true)) { + try { + if (BuildCompat.isPie()) { + if (msg.what == ActivityThread.H.EXECUTE_TRANSACTION.get()) { + if (handleLaunchActivity(msg.obj)) { + getH().sendMessageAtFrontOfQueue(Message.obtain(msg)); + return true; + } + } + } else { + if (msg.what == ActivityThread.H.LAUNCH_ACTIVITY.get()) { + if (handleLaunchActivity(msg.obj)) { + getH().sendMessageAtFrontOfQueue(Message.obtain(msg)); + return true; + } + } + } + + if (msg.what == ActivityThread.H.CREATE_SERVICE.get()) { + return handleCreateService(msg.obj); + } + + if (mOtherCallback != null) { + return mOtherCallback.handleMessage(msg); + } + return false; + } finally { + mBeing.set(false); + } + } + return false; + } + + private Object getLaunchActivityItem(Object clientTransaction) { + List mActivityCallbacks = ClientTransaction.mActivityCallbacks.get(clientTransaction); + + for (Object obj : mActivityCallbacks) { + if (LaunchActivityItem.REF.getClazz().getName().equals(obj.getClass().getCanonicalName())) { + return obj; + } + } + return null; + } + + private boolean handleLaunchActivity(Object client) { + Object r; + if (BuildCompat.isPie()) { + // ClientTransaction + r = getLaunchActivityItem(client); + } else { + // ActivityClientRecord + r = client; + } + + if (r == null) { + return false; + } + + Intent intent; + IBinder token; + if (BuildCompat.isPie()) { + intent = LaunchActivityItem.mIntent.get(r); + token = ClientTransaction.mActivityToken.get(client); + } else { + intent = ActivityThread.ActivityClientRecord.intent.get(r); + token = ActivityThread.ActivityClientRecord.token.get(r); + } + + if (intent == null) { + return false; + } + + ProxyActivityRecord stubRecord = ProxyActivityRecord.create(intent); + ActivityInfo activityInfo = stubRecord.mActivityInfo; + if (activityInfo != null) { + if (BActivityThread.getAppConfig() == null) { + BlackBoxCore.getBActivityManager().restartProcess(activityInfo.packageName, activityInfo.processName, stubRecord.mUserId); + + Intent launchIntentForPackage = BlackBoxCore.getBPackageManager().getLaunchIntentForPackage(activityInfo.packageName, stubRecord.mUserId); + intent.setExtrasClassLoader(this.getClass().getClassLoader()); + ProxyActivityRecord.saveStub(intent, launchIntentForPackage, stubRecord.mActivityInfo, stubRecord.mActivityToken, stubRecord.mUserId); + if (BuildCompat.isPie()) { + LaunchActivityItem.mIntent.set(r, intent); + LaunchActivityItem.mInfo.set(r, activityInfo); + } else { + ActivityThread.ActivityClientRecord.intent.set(r, intent); + ActivityThread.ActivityClientRecord.activityInfo.set(r, activityInfo); + } + return true; + } + + if (!BActivityThread.currentActivityThread().isInit()) { + BActivityThread.currentActivityThread().bindApplication(activityInfo.packageName, activityInfo.processName); + return true; + } + + int taskId = IActivityManager.getTaskForActivity.call(ActivityManagerNative.getDefault.call(), token, false); + BlackBoxCore.getBActivityManager().onActivityCreated(taskId, token, stubRecord.mActivityToken); + + if (Build.VERSION.SDK_INT == Build.VERSION_CODES.S || (Build.VERSION.SDK_INT == Build.VERSION_CODES.R && Build.VERSION.PREVIEW_SDK_INT == 1)) { + Object record = ActivityThread.getLaunchingActivity.call(BlackBoxCore.mainThread(), token); + ActivityThread.ActivityClientRecord.intent.set(record, stubRecord.mTarget); + ActivityThread.ActivityClientRecord.activityInfo.set(record, activityInfo); + ActivityThread.ActivityClientRecord.packageInfo.set(record, BActivityThread.currentActivityThread().getPackageInfo()); + checkActivityClient(); + } else if (BuildCompat.isPie()) { + LaunchActivityItem.mIntent.set(r, stubRecord.mTarget); + LaunchActivityItem.mInfo.set(r, activityInfo); + } else { + ActivityThread.ActivityClientRecord.intent.set(r, stubRecord.mTarget); + ActivityThread.ActivityClientRecord.activityInfo.set(r, activityInfo); + } + } + return false; + } + + private boolean handleCreateService(Object data) { + if (BActivityThread.getAppConfig() != null) { + String appPackageName = BActivityThread.getAppPackageName(); + assert appPackageName != null; + + ServiceInfo serviceInfo = ActivityThread.CreateServiceData.info.get(data); + if (!serviceInfo.name.equals(ProxyManifest.getProxyService(BActivityThread.getAppPid())) + && !serviceInfo.name.equals(ProxyManifest.getProxyJobService(BActivityThread.getAppPid()))) { + Slog.d(TAG, "handleCreateService: " + data); + Intent intent = new Intent(); + intent.setComponent(new ComponentName(appPackageName, serviceInfo.name)); + BlackBoxCore.getBActivityManager().startService(intent, null, false, BActivityThread.getUserId()); + return true; + } + } + return false; + } + + private void checkActivityClient() { + try { + Object activityClientController = ActivityClient.getActivityClientController.call(); + if (!(activityClientController instanceof Proxy)) { + IActivityClientProxy iActivityClientProxy = new IActivityClientProxy(activityClientController); + iActivityClientProxy.onlyProxy(true); + iActivityClientProxy.injectHook(); + + Object instance = ActivityClient.getInstance.call(); + Object o = ActivityClient.INTERFACE_SINGLETON.get(instance); + ActivityClient.ActivityClientControllerSingleton.mKnownInstance.set(o, iActivityClientProxy.getProxyInvocation()); + } + } catch (Throwable t) { + t.printStackTrace(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccessibilityManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccessibilityManagerProxy.java new file mode 100644 index 0000000..11afaed --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccessibilityManagerProxy.java @@ -0,0 +1,55 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.content.pm.ApplicationInfo; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.android.view.accessibility.IAccessibilityManager; +import com.vcore.BlackBoxCore; +import com.vcore.core.system.user.BUserHandle; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethods; + +public class IAccessibilityManagerProxy extends BinderInvocationStub { + public IAccessibilityManagerProxy() { + super(ServiceManager.getService.call(Context.ACCESSIBILITY_SERVICE)); + } + + @Override + protected Object getWho() { + return IAccessibilityManager.Stub.asInterface.call(ServiceManager.getService.call(Context.ACCESSIBILITY_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.ACCESSIBILITY_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethods({"interrupt", "sendAccessibilityEvent", "addClient", "removeClient", "getInstalledAccessibilityServiceList", + "getEnabledAccessibilityServiceList", "addAccessibilityInteractionConnection", "getWindowToken", "setSystemAudioCaptioningEnabled", + "isSystemAudioCaptioningUiEnabled", "setSystemAudioCaptioningUiEnabled"}) + public static class ReplaceUserId extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args != null) { + int index = args.length - 1; + Object arg = args[index]; + + if (arg instanceof Integer) { + ApplicationInfo applicationInfo = BlackBoxCore.getContext().getApplicationInfo(); + args[index] = BUserHandle.getUserId(applicationInfo.uid); + } + } + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAccountManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccountManagerProxy.java similarity index 78% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAccountManagerProxy.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccountManagerProxy.java index 8934467..a25c98d 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAccountManagerProxy.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAccountManagerProxy.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.fake.service; +package com.vcore.fake.service; import android.accounts.Account; import android.accounts.IAccountManagerResponse; @@ -8,32 +8,23 @@ import java.lang.reflect.Method; import java.util.Map; -import black.android.accounts.BRIAccountManagerStub; -import black.android.os.BRServiceManager; -import top.niunaijun.blackbox.fake.frameworks.BAccountManager; -import top.niunaijun.blackbox.fake.hook.BinderInvocationStub; -import top.niunaijun.blackbox.fake.hook.MethodHook; -import top.niunaijun.blackbox.fake.hook.ProxyMethod; -import top.niunaijun.blackbox.utils.Slog; - -/** - * Created by Milk on 2022/2/14. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import black.android.accounts.IAccountManager; +import black.android.os.ServiceManager; +import com.vcore.fake.frameworks.BAccountManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + public class IAccountManagerProxy extends BinderInvocationStub { public static final String TAG = "IAccountManagerProxy"; public IAccountManagerProxy() { - super(BRServiceManager.get().getService(Context.ACCOUNT_SERVICE)); + super(ServiceManager.getService.call(Context.ACCOUNT_SERVICE)); } @Override protected Object getWho() { - return BRIAccountManagerStub.get().asInterface(BRServiceManager.get().getService(Context.ACCOUNT_SERVICE)); + return IAccountManager.Stub.asInterface.call(ServiceManager.getService.call(Context.ACCOUNT_SERVICE)); } @Override @@ -41,24 +32,15 @@ protected void inject(Object baseInvocation, Object proxyInvocation) { replaceSystemService(Context.ACCOUNT_SERVICE); } - @Override - protected void onBindMethod() { - super.onBindMethod(); - } + @Override public boolean isBadEnv() { return false; } - @Override - public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { - Slog.d(TAG, "call " + method.getName()); - return super.invoke(proxy, method, args); - } - @ProxyMethod("getPassword") - public static class getPassword extends MethodHook { + public static class GetPassword extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -67,7 +49,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getUserData") - public static class getUserData extends MethodHook { + public static class GetUserData extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -76,7 +58,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAuthenticatorTypes") - public static class getAuthenticatorTypes extends MethodHook { + public static class GetAuthenticatorTypes extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -85,7 +67,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountsForPackage") - public static class getAccountsForPackage extends MethodHook { + public static class GetAccountsForPackage extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -94,7 +76,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountsByTypeForPackage") - public static class getAccountsByTypeForPackage extends MethodHook { + public static class GetAccountsByTypeForPackage extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -103,7 +85,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountByTypeAndFeatures") - public static class getAccountByTypeAndFeatures extends MethodHook { + public static class GetAccountByTypeAndFeatures extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -113,7 +95,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountsByFeatures") - public static class getAccountsByFeatures extends MethodHook { + public static class GetAccountsByFeatures extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -123,7 +105,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountsAsUser") - public static class getAccountsAsUser extends MethodHook { + public static class GetAccountsAsUser extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -132,7 +114,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("addAccountExplicitly") - public static class addAccountExplicitly extends MethodHook { + public static class AddAccountExplicitly extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -141,7 +123,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("removeAccountAsUser") - public static class removeAccountAsUser extends MethodHook { + public static class RemoveAccountAsUser extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -151,7 +133,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("removeAccountExplicitly") - public static class removeAccountExplicitly extends MethodHook { + public static class RemoveAccountExplicitly extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -160,7 +142,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("copyAccountToUser") - public static class copyAccountToUser extends MethodHook { + public static class CopyAccountToUser extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -170,7 +152,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("invalidateAuthToken") - public static class invalidateAuthToken extends MethodHook { + public static class InvalidateAuthToken extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -180,7 +162,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("peekAuthToken") - public static class peekAuthToken extends MethodHook { + public static class PeekAuthToken extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -189,7 +171,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("setAuthToken") - public static class setAuthToken extends MethodHook { + public static class SetAuthToken extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -199,7 +181,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("setPassword") - public static class setPassword extends MethodHook { + public static class SetPassword extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -209,7 +191,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("clearPassword") - public static class clearPassword extends MethodHook { + public static class ClearPassword extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -219,7 +201,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("setUserData") - public static class setUserData extends MethodHook { + public static class SetUserData extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -229,7 +211,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("updateAppPermission") - public static class updateAppPermission extends MethodHook { + public static class UpdateAppPermission extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -239,7 +221,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAuthToken") - public static class getAuthToken extends MethodHook { + public static class GetAuthToken extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -254,7 +236,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("addAccount") - public static class addAccount extends MethodHook { + public static class AddAccount extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -269,7 +251,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("addAccountAsUser") - public static class addAccountAsUser extends MethodHook { + public static class AddAccountAsUser extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -284,7 +266,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("updateCredentials") - public static class updateCredentials extends MethodHook { + public static class UpdateCredentials extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -298,7 +280,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("editProperties") - public static class editProperties extends MethodHook { + public static class EditProperties extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -310,7 +292,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("confirmCredentialsAsUser") - public static class confirmCredentialsAsUser extends MethodHook { + public static class ConfirmCredentialsAsUser extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -323,7 +305,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("accountAuthenticated") - public static class accountAuthenticated extends MethodHook { + public static class AccountAuthenticated extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -333,7 +315,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAuthTokenLabel") - public static class getAuthTokenLabel extends MethodHook { + public static class GetAuthTokenLabel extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -345,7 +327,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getPackagesAndVisibilityForAccount") - public static class getPackagesAndVisibilityForAccount extends MethodHook { + public static class GetPackagesAndVisibilityForAccount extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -354,20 +336,20 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("addAccountExplicitlyWithVisibility") - public static class addAccountExplicitlyWithVisibility extends MethodHook { + public static class AddAccountExplicitlyWithVisibility extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { return BAccountManager.get().addAccountExplicitlyWithVisibility((Account) args[0], (String) args[1], (Bundle) args[2], - (Map) args[3] + (Map) args[3] ); } } @ProxyMethod("setAccountVisibility") - public static class setAccountVisibility extends MethodHook { + public static class SetAccountVisibility extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -379,7 +361,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountVisibility") - public static class getAccountVisibility extends MethodHook { + public static class GetAccountVisibility extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -390,7 +372,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("getAccountsAndVisibilityForPackage") - public static class getAccountsAndVisibilityForPackage extends MethodHook { + public static class GetAccountsAndVisibilityForPackage extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -401,7 +383,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("registerAccountListener") - public static class registerAccountListener extends MethodHook { + public static class RegisterAccountListener extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { @@ -413,7 +395,7 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable } @ProxyMethod("unregisterAccountListener") - public static class unregisterAccountListener extends MethodHook { + public static class UnregisterAccountListener extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityClientProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityClientProxy.java new file mode 100644 index 0000000..ce35dcc --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityClientProxy.java @@ -0,0 +1,98 @@ +package com.vcore.fake.service; + +import android.app.ActivityManager; +import android.os.IBinder; + +import java.lang.reflect.Method; + +import black.android.app.ActivityClient; +import black.android.util.Singleton; +import com.vcore.fake.frameworks.BActivityManager; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.fake.hook.HookManager; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.compat.TaskDescriptionCompat; + +public class IActivityClientProxy extends ClassInvocationStub { + public static final String TAG = "IActivityClientProxy"; + private final Object who; + + public IActivityClientProxy(Object who) { + this.who = who; + } + + @Override + protected Object getWho() { + if (who != null) { + return who; + } + + Object instance = ActivityClient.getInstance.call(); + Object singleton = ActivityClient.INTERFACE_SINGLETON.get(instance); + return Singleton.get.call(singleton); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + Object instance = ActivityClient.getInstance.call(); + Object singleton = ActivityClient.INTERFACE_SINGLETON.get(instance); + Singleton.mInstance.set(singleton, proxyInvocation); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + public void onlyProxy(boolean only) { + super.onlyProxy(only); + } + + @ProxyMethod("finishActivity") + public static class FinishActivity extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IBinder token = (IBinder) args[0]; + BActivityManager.get().onFinishActivity(token); + return method.invoke(who, args); + } + } + + @ProxyMethod("activityResumed") + public static class ActivityResumed extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IBinder token = (IBinder) args[0]; + BActivityManager.get().onActivityResumed(token); + return method.invoke(who, args); + } + } + + @ProxyMethod("activityDestroyed") + public static class ActivityDestroyed extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IBinder token = (IBinder) args[0]; + BActivityManager.get().onActivityDestroyed(token); + return method.invoke(who, args); + } + } + + // for >= Android 12 + @ProxyMethod("setTaskDescription") + public static class SetTaskDescription extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ActivityManager.TaskDescription td = (ActivityManager.TaskDescription) args[1]; + args[1] = TaskDescriptionCompat.fix(td); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityManagerProxy.java new file mode 100644 index 0000000..3952634 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityManagerProxy.java @@ -0,0 +1,654 @@ +package com.vcore.fake.service; + +import static android.content.pm.PackageManager.GET_META_DATA; +import static android.content.pm.PackageManager.PERMISSION_GRANTED; + +import android.Manifest; +import android.app.ActivityManager; +import android.app.IServiceConnection; +import android.app.Notification; +import android.content.ComponentName; +import android.content.IIntentReceiver; +import android.content.Intent; +import android.content.pm.PackageManager; +import android.content.pm.ProviderInfo; +import android.content.pm.ResolveInfo; +import android.os.Build; +import android.os.IBinder; +import android.os.IInterface; +import android.util.Log; + +import java.lang.ref.WeakReference; +import java.lang.reflect.Method; +import java.util.ArrayList; + +import black.android.app.ActivityManagerNative; +import black.android.app.ActivityManagerOreo; +import black.android.app.IActivityManager; +import black.android.app.LoadedApk; +import black.android.content.ContentProviderNative; +import black.android.content.pm.UserInfo; +import black.android.util.Singleton; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.core.env.AppSystemEnv; +import com.vcore.core.system.DaemonService; +import com.vcore.entity.AppConfig; +import com.vcore.entity.am.RunningAppProcessInfo; +import com.vcore.entity.am.RunningServiceInfo; +import com.vcore.fake.delegate.ContentProviderDelegate; +import com.vcore.fake.delegate.InnerReceiverDelegate; +import com.vcore.fake.delegate.ServiceConnectionDelegate; +import com.vcore.fake.frameworks.BActivityManager; +import com.vcore.fake.frameworks.BPackageManager; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.hook.ScanClass; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.fake.service.context.providers.ContentProviderStub; +import com.vcore.proxy.ProxyManifest; +import com.vcore.proxy.record.ProxyBroadcastRecord; +import com.vcore.proxy.record.ProxyPendingRecord; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.ActivityManagerCompat; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.ParceledListSliceCompat; +import com.vcore.utils.compat.TaskDescriptionCompat; + +@ScanClass(ActivityManagerCommonProxy.class) +public class IActivityManagerProxy extends ClassInvocationStub { + public static final String TAG = "IActivityManagerProxy"; + + @Override + protected Object getWho() { + Object iActivityManager = null; + if (BuildCompat.isOreo()) { + iActivityManager = ActivityManagerOreo.IActivityManagerSingleton.get(); + } else if (BuildCompat.isL()) { + iActivityManager = ActivityManagerNative.gDefault.get(); + } + return Singleton.get.call(iActivityManager); + } + + @Override + protected void inject(Object base, Object proxy) { + Object iActivityManager = null; + if (BuildCompat.isOreo()) { + iActivityManager = ActivityManagerOreo.IActivityManagerSingleton.get(); + } else if (BuildCompat.isL()) { + iActivityManager = ActivityManagerNative.gDefault.get(); + } + Singleton.mInstance.set(iActivityManager, proxy); + } + + @Override + public boolean isBadEnv() { + return getProxyInvocation() != getWho(); + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new PkgMethodProxy("getAppStartMode")); + addMethodHook(new PkgMethodProxy("setAppLockedVerifying")); + addMethodHook(new PkgMethodProxy("reportJunkFromApp")); + } + + @ProxyMethod("getContentProvider") + public static class GetContentProvider extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Exception { + int authIndex = getAuthIndex(); + Object auth = args[authIndex]; + Object content; + + Slog.d(TAG, "Innovate getContentProvider: " + auth); + if (auth instanceof String) { + if (ProxyManifest.isProxy((String) auth)) { + Slog.d(TAG, "ProxyManifest.isProxy: " + auth); + return method.invoke(who, args); + } + + if (BuildCompat.isQ()) { + args[1] = BlackBoxCore.getHostPkg(); + } + + if (auth.equals("settings") || auth.equals("media") || auth.equals("telephony")) { + content = method.invoke(who, args); + ContentProviderDelegate.update(content, (String) auth); + return content; + } else { + Slog.d(TAG, "Hook getContentProvider: " + auth); + ProviderInfo providerInfo = BlackBoxCore.getBPackageManager().resolveContentProvider((String) auth, GET_META_DATA, BActivityThread.getUserId()); + + Slog.d(TAG, "Hook app: " + auth); + IBinder providerBinder = null; + if (BActivityThread.getAppPid() != -1 && providerInfo != null) { + AppConfig appConfig = BlackBoxCore.getBActivityManager().initProcess(providerInfo.packageName, providerInfo.processName, BActivityThread.getUserId()); + if (appConfig.bPID != BActivityThread.getAppPid()) { + providerBinder = BlackBoxCore.getBActivityManager().acquireContentProviderClient(providerInfo); + } + + args[authIndex] = ProxyManifest.getProxyAuthorities(appConfig.bPID); + args[getUserIndex()] = BlackBoxCore.getHostUserId(); + } + + if (providerBinder == null) { + return null; + } + + content = method.invoke(who, args); + IActivityManager.ContentProviderHolder.info.set(content, providerInfo); + IActivityManager.ContentProviderHolder.provider.set(content, new ContentProviderStub().wrapper(ContentProviderNative.asInterface.call(providerBinder), BActivityThread.getAppPackageName())); + } + return content; + } + return method.invoke(who, args); + } + + private int getAuthIndex() { + // 10.0 + if (BuildCompat.isQ()) { + return 2; + } else { + return 1; + } + } + + private int getUserIndex() { + return getAuthIndex() + 1; + } + } + + @ProxyMethod("startService") + public static class StartService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[1]; + String resolvedType = (String) args[2]; + + ResolveInfo resolveInfo = BlackBoxCore.getBPackageManager().resolveService(intent, 0, resolvedType, BActivityThread.getUserId()); + if (resolveInfo == null) { + return method.invoke(who, args); + } + + int requireForegroundIndex = getRequireForeground(); + boolean requireForeground = false; + if (requireForegroundIndex != -1) { + requireForeground = (boolean) args[requireForegroundIndex]; + } + return BlackBoxCore.getBActivityManager().startService(intent, resolvedType, requireForeground, BActivityThread.getUserId()); + } + + public int getRequireForeground() { + if (BuildCompat.isOreo()) { + return 3; + } + return -1; + } + } + + @ProxyMethod("stopService") + public static class StopService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[1]; + String resolvedType = (String) args[2]; + return BlackBoxCore.getBActivityManager().stopService(intent, resolvedType, BActivityThread.getUserId()); + } + } + + @ProxyMethod("stopServiceToken") + public static class StopServiceToken extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName componentName = (ComponentName) args[0]; + IBinder token = (IBinder) args[1]; + BlackBoxCore.getBActivityManager().stopServiceToken(componentName, token, BActivityThread.getUserId()); + return true; + } + } + + @ProxyMethod("bindService") + public static class BindService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[2]; + String resolvedType = (String) args[3]; + IServiceConnection connection = (IServiceConnection) args[4]; + int userId = intent.getIntExtra("_B_|_UserId", -1); + userId = userId == -1 ? BActivityThread.getUserId() : userId; + int callingPkgIdx = false ? 7 : (char) 6; + if (Build.VERSION.SDK_INT >= 23 && args.length >= 8 && (args[callingPkgIdx] instanceof String)) { + args[callingPkgIdx] = BlackBoxCore.getHostPkg(); + } + long flags = getIntOrLongValue(args[5]); + ResolveInfo resolveInfo = BlackBoxCore.getBPackageManager().resolveService(intent, 0, resolvedType, userId); + if (resolveInfo != null || AppSystemEnv.isOpenPackage(intent.getComponent())) { + if (BuildCompat.isU()){ + args[5] = Long.valueOf(flags & 2147483647L); + }else{ + args[5] = Integer.valueOf((int) (flags & 2147483647L)); + } + Intent proxyIntent = BlackBoxCore.getBActivityManager().bindService(intent, connection == null ? null : connection.asBinder(), resolvedType, + userId); + if (connection != null) { + if (intent.getComponent() == null && resolveInfo != null) { + intent.setComponent(new ComponentName(resolveInfo.serviceInfo.packageName, resolveInfo.serviceInfo.name)); + } + + IServiceConnection proxy = ServiceConnectionDelegate.createProxy(connection, intent); + args[4] = proxy; + + WeakReference weakReference = LoadedApk.ServiceDispatcher.InnerConnection.mDispatcher.get(connection); + if (weakReference != null) { + LoadedApk.ServiceDispatcher.mConnection.set(weakReference.get(), proxy); + } + } + if (BuildCompat.isT()){ + if (proxyIntent != null) { + args[2] = proxyIntent; + return method.invoke(who, args); + } + }else{ + return method.invoke(who, args); + } + } + return method.invoke(who, args); + } + + @Override + protected boolean isEnable() { + return BlackBoxCore.get().isBlackProcess() || BlackBoxCore.get().isServerProcess(); + } + } + + public static long getIntOrLongValue(Object obj) { + if (obj == null) { + return 0L; + } + if (obj instanceof Integer) { + return ((Integer) obj).longValue(); + } + if (obj instanceof Long) { + return ((Long) obj).longValue(); + } + return -1L; + } + + // 10.0 + @ProxyMethod("bindIsolatedService") + public static class BindIsolatedService extends BindService { + + @Override + protected Object beforeHook(Object who, Method method, Object[] args) throws Throwable { + // instanceName + args[6] = null; + return super.beforeHook(who, method, args); + } + } + + @ProxyMethod("unbindService") + public static class UnbindService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IServiceConnection iServiceConnection = (IServiceConnection) args[0]; + if (iServiceConnection == null) { + return method.invoke(who, args); + } + + BlackBoxCore.getBActivityManager().unbindService(iServiceConnection.asBinder(), BActivityThread.getUserId()); + ServiceConnectionDelegate delegate = ServiceConnectionDelegate.getDelegate(iServiceConnection.asBinder()); + if (delegate != null) { + args[0] = delegate; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getRunningAppProcesses") + public static class GetRunningAppProcesses extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + RunningAppProcessInfo runningAppProcesses = BActivityManager.get().getRunningAppProcesses(BActivityThread.getAppPackageName(), BActivityThread.getUserId()); + if (runningAppProcesses == null) { + return new ArrayList<>(); + } + return runningAppProcesses.mAppProcessInfoList; + } + } + + @ProxyMethod("getServices") + public static class GetServices extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + RunningServiceInfo runningServices = BActivityManager.get().getRunningServices(BActivityThread.getAppPackageName(), BActivityThread.getUserId()); + if (runningServices == null) { + return new ArrayList<>(); + } + return runningServices.mRunningServiceInfoList; + } + } + + @ProxyMethod("getIntentSender") + public static class GetIntentSender extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int type = (int) args[0]; + Intent[] intents = (Intent[]) args[getIntentsIndex(args)]; + MethodParameterUtils.replaceFirstAppPkg(args); + + for (int i = 0; i < intents.length; i++) { + Intent intent = intents[i]; + if (type == ActivityManagerCompat.INTENT_SENDER_ACTIVITY) { + Intent shadow = new Intent(); + shadow.setComponent(new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyPendingActivity(BActivityThread.getAppPid()))); + + ProxyPendingRecord.saveStub(shadow, intent, BActivityThread.getUserId()); + intents[i] = shadow; + } + } + + IInterface invoke = (IInterface) method.invoke(who, args); + if (invoke != null) { + String[] packagesForUid = BPackageManager.get().getPackagesForUid(BActivityThread.getCallingBUid()); + if (packagesForUid.length < 1) { + packagesForUid = new String[]{BlackBoxCore.getHostPkg()}; + } + BlackBoxCore.getBActivityManager().getIntentSender(invoke.asBinder(), packagesForUid[0], BActivityThread.getCallingBUid()); + } + return invoke; + } + + private int getIntentsIndex(Object[] args) { + for (int i = 0; i < args.length; i++) { + if (args[i] instanceof Intent[]) { + return i; + } + } + if (BuildCompat.isR()) { + return 6; + } else { + return 5; + } + } + } + + @ProxyMethod("getPackageForIntentSender") + public static class GetPackageForIntentSender extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IInterface invoke = (IInterface) args[0]; + return BlackBoxCore.getBActivityManager().getPackageForIntentSender(invoke.asBinder()); + } + } + + @ProxyMethod("getUidForIntentSender") + public static class getUidForIntentSender extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IInterface invoke = (IInterface) args[0]; + return BlackBoxCore.getBActivityManager().getUidForIntentSender(invoke.asBinder()); + } + } + + @ProxyMethod("broadcastIntent") + public static class BroadcastIntent extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int intentIndex = getIntentIndex(args); + Intent intent = (Intent) args[intentIndex]; + String resolvedType = (String) args[intentIndex + 1]; + + Intent proxyIntent = BlackBoxCore.getBActivityManager().sendBroadcast(intent, resolvedType, BActivityThread.getUserId()); + if (proxyIntent != null) { + proxyIntent.setExtrasClassLoader(BActivityThread.getApplication().getClassLoader()); + + ProxyBroadcastRecord.saveStub(proxyIntent, intent, BActivityThread.getUserId()); + args[intentIndex] = proxyIntent; + } + // ignore permission + for (int i = 0; i < args.length; i++) { + Object o = args[i]; + if (o instanceof String[]) { + args[i] = null; + } + } + return method.invoke(who, args); + } + + int getIntentIndex(Object[] args) { + for (int i = 0; i < args.length; i++) { + Object arg = args[i]; + if (arg instanceof Intent) { + return i; + } + } + return 1; + } + } + + @ProxyMethod("peekService") + public static class PeekService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceLastAppPkg(args); + Intent intent = (Intent) args[0]; + String resolvedType = (String) args[1]; + return BlackBoxCore.getBActivityManager().peekService(intent, resolvedType, BActivityThread.getUserId()); + } + } + + // TODO + @ProxyMethod("sendIntentSender") + public static class SendIntentSender extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } + + @ProxyMethod("registerReceiver") + public static class RegisterReceiver extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + int receiverIndex = getReceiverIndex(); + if (args[receiverIndex] != null) { + IIntentReceiver intentReceiver = (IIntentReceiver) args[receiverIndex]; + IIntentReceiver proxy = InnerReceiverDelegate.createProxy(intentReceiver); + + WeakReference weakReference = LoadedApk.ReceiverDispatcher.InnerReceiver.mDispatcher.get(intentReceiver); + if (weakReference != null) { + LoadedApk.ReceiverDispatcher.mIIntentReceiver.set(weakReference.get(), proxy); + } + + args[receiverIndex] = proxy; + } + // ignore permission + if (args[getPermissionIndex()] != null) { + args[getPermissionIndex()] = null; + } + return method.invoke(who, args); + } + + public int getReceiverIndex() { + if (BuildCompat.isS()) { + return 4; + } else if (BuildCompat.isR()) { + return 3; + } + return 2; + } + + public int getPermissionIndex() { + if (BuildCompat.isS()) { + return 6; + } else if (BuildCompat.isR()) { + return 5; + } + return 4; + } + } + + @ProxyMethod("grantUriPermission") + public static class GrantUriPermission extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceLastUid(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("setServiceForeground") + public static class SetServiceForeground extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Notification notification = (Notification) args[3]; + + Intent intent = new Intent(BlackBoxCore.getContext(), DaemonService.class); + if (notification != null) { + if (BuildCompat.isOreo()) { + BlackBoxCore.getContext().startForegroundService(intent); + } else { + BlackBoxCore.getContext().startService(intent); + } + } else { + BlackBoxCore.getContext().stopService(intent); + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getHistoricalProcessExitReasons") + public static class GetHistoricalProcessExitReasons extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return ParceledListSliceCompat.create(new ArrayList<>()); + } + } + + @ProxyMethod("getCurrentUser") + public static class GetCurrentUser extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return UserInfo._new.newInstance(BActivityThread.getUserId(), "BlackBox", UserInfo.FLAG_PRIMARY.get()); + } + } + + @ProxyMethod("checkPermission") + public static class CheckPermission extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceLastUid(args); + String permission = (String) args[0]; + + if (permission.equals(Manifest.permission.ACCOUNT_MANAGER) || permission.equals(Manifest.permission.SEND_SMS)) { + return PackageManager.PERMISSION_GRANTED; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("checkUriPermission") + public static class CheckUriPermission extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return PERMISSION_GRANTED; + } + } + + // for < Android 10 + @ProxyMethod("setTaskDescription") + public static class SetTaskDescription extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ActivityManager.TaskDescription td = (ActivityManager.TaskDescription) args[1]; + args[1] = TaskDescriptionCompat.fix(td); + return method.invoke(who, args); + } + } + + @ProxyMethod("overridePendingTransition") + public static class OverridePendingTransition extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String packageName = (String) args[1]; + if ("com.tencent.mm".equals(packageName)) { + return null; + }else{ + return method.invoke(who, args); + } + } + } + + @ProxyMethod("setPackageAskScreenCompat") + public static class SetPackageAskScreenCompat extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.ICE_CREAM_SANDWICH_MR1) { + if (args.length > 0 && args[0] instanceof String) { + args[0] = BlackBoxCore.getHostPkg(); + } + } + return method.invoke(who,args); + } + } + + @ProxyMethod("handleIncomingUser") + public static class HandleIncomingUser extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BlackBoxCore.get().isBlackProcess()){ + int lastIndex = args.length - 1; + if (args[lastIndex] instanceof String) { + args[lastIndex] = BlackBoxCore.getHostPkg(); + } + return method.invoke(who, args); + }else{ + return method.invoke(who, args); + } + } + } + + @ProxyMethod("getPersistedUriPermissions") + public static class GetPersistedUriPermissions extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BlackBoxCore.get().isBlackProcess()){ + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + }else{ + return method.invoke(who, args); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityTaskManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityTaskManagerProxy.java new file mode 100644 index 0000000..72bdb3f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IActivityTaskManagerProxy.java @@ -0,0 +1,60 @@ +package com.vcore.fake.service; + +import android.app.ActivityManager; + +import java.lang.reflect.Method; + +import black.android.app.ActivityTaskManager; +import black.android.app.IActivityTaskManager; +import black.android.os.ServiceManager; +import black.android.util.Singleton; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.hook.ScanClass; +import com.vcore.utils.compat.TaskDescriptionCompat; + +@ScanClass(ActivityManagerCommonProxy.class) +public class IActivityTaskManagerProxy extends BinderInvocationStub { + public static final String TAG = "ActivityTaskManager"; + + public IActivityTaskManagerProxy() { + super(ServiceManager.getService.call("activity_task")); + } + + @Override + protected Object getWho() { + return IActivityTaskManager.Stub.asInterface.call(ServiceManager.getService.call("activity_task")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("activity_task"); + + Object o = ActivityTaskManager.IActivityTaskManagerSingleton.get(); + Singleton.mInstance.set(o, IActivityTaskManager.Stub.asInterface.call(this)); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new SetTaskDescription()); + } + + // for >= Android 10 && < Android 12 + @ProxyMethod("setTaskDescription") + public static class SetTaskDescription extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ActivityManager.TaskDescription td = (ActivityManager.TaskDescription) args[1]; + args[1] = TaskDescriptionCompat.fix(td); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAlarmManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAlarmManagerProxy.java new file mode 100644 index 0000000..0db7654 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAlarmManagerProxy.java @@ -0,0 +1,92 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.Build; +import android.os.WorkSource; + +import java.lang.reflect.Method; + +import black.android.app.IAlarmManager; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.ValueMethodProxy; +import com.vcore.utils.ArrayUtils; + +public class IAlarmManagerProxy extends BinderInvocationStub { + public IAlarmManagerProxy() { + super(ServiceManager.getService.call(Context.ALARM_SERVICE)); + } + + @Override + protected Object getWho() { + return IAlarmManager.Stub.asInterface.call(ServiceManager.getService.call(Context.ALARM_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.ALARM_SERVICE); + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + //addMethodHook(new ValueMethodProxy("set", 0)); + addMethodHook(new ValueMethodProxy("setTimeZone",null)); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("set") + public static class Set extends MethodHook { + + @Override + protected String getMethodName() { + return "set"; + } + + @Override + protected Object beforeHook(Object who, Method method, Object[] args) throws Throwable { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && args[0] instanceof String) { + args[0] = BlackBoxCore.getHostPkg(); + } + int index = ArrayUtils.indexOfFirst(args, WorkSource.class); + if (index >= 0) { + args[index] = null; + } + return true; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + try { + return method.invoke(who, method, args); + } catch (Throwable e) { + e.printStackTrace(); + } + return 0; + } + } + + @ProxyMethod("setTime") + public static class SetTime extends MethodHook { + + @Override + protected String getMethodName() { + return "setTime"; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { + return false; + } + return null; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppOpsManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppOpsManagerProxy.java new file mode 100644 index 0000000..188b727 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppOpsManagerProxy.java @@ -0,0 +1,90 @@ +package com.vcore.fake.service; + +import android.app.AppOpsManager; +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.com.android.internal.app.IAppOpsService; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class IAppOpsManagerProxy extends BinderInvocationStub { + public IAppOpsManagerProxy() { + super(ServiceManager.getService.call(Context.APP_OPS_SERVICE)); + } + + @Override + protected Object getWho() { + return IAppOpsService.Stub.asInterface.call(ServiceManager.getService.call(Context.APP_OPS_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + if (black.android.app.AppOpsManager.mService != null) { + AppOpsManager appOpsManager = (AppOpsManager) BlackBoxCore.getContext().getSystemService(Context.APP_OPS_SERVICE); + try { + black.android.app.AppOpsManager.mService.set(appOpsManager, getProxyInvocation()); + } catch (Exception e) { + e.printStackTrace(); + } + } + replaceSystemService(Context.APP_OPS_SERVICE); + + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + MethodParameterUtils.replaceLastUid(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("noteProxyOperation") + public static class NoteProxyOperation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return AppOpsManager.MODE_ALLOWED; + } + } + + @ProxyMethod("checkPackage") + public static class CheckPackage extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + // TODO + return AppOpsManager.MODE_ALLOWED; + } + } + + @ProxyMethod("checkOperation") + public static class CheckOperation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceLastUid(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("noteOperation") + public static class NoteOperation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAppWidgetManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppWidgetManagerProxy.java similarity index 79% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAppWidgetManagerProxy.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppWidgetManagerProxy.java index 01ad073..65e4038 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/IAppWidgetManagerProxy.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAppWidgetManagerProxy.java @@ -1,32 +1,23 @@ -package top.niunaijun.blackbox.fake.service; +package com.vcore.fake.service; import android.content.Context; import java.lang.reflect.Method; -import black.android.os.BRServiceManager; -import black.com.android.internal.appwidget.BRIAppWidgetServiceStub; -import top.niunaijun.blackbox.fake.hook.BinderInvocationStub; -import top.niunaijun.blackbox.fake.service.base.ValueMethodProxy; -import top.niunaijun.blackbox.utils.MethodParameterUtils; +import black.android.os.ServiceManager; +import black.com.android.internal.appwidget.IAppWidgetService; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; +import com.vcore.utils.MethodParameterUtils; -/** - * Created by Milk on 4/5/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class IAppWidgetManagerProxy extends BinderInvocationStub { - public IAppWidgetManagerProxy() { - super(BRServiceManager.get().getService(Context.APPWIDGET_SERVICE)); + super(ServiceManager.getService.call(Context.APPWIDGET_SERVICE)); } @Override protected Object getWho() { - return BRIAppWidgetServiceStub.get().asInterface(BRServiceManager.get().getService(Context.APPWIDGET_SERVICE)); + return IAppWidgetService.Stub.asInterface.call(ServiceManager.getService.call(Context.APPWIDGET_SERVICE)); } @Override diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAutofillManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAutofillManagerProxy.java new file mode 100644 index 0000000..da0ce97 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IAutofillManagerProxy.java @@ -0,0 +1,63 @@ +package com.vcore.fake.service; + +import android.content.ComponentName; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.android.view.IAutoFillManager; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.proxy.ProxyManifest; + +public class IAutofillManagerProxy extends BinderInvocationStub { + public static final String TAG = "AutofillManagerStub"; + + public IAutofillManagerProxy() { + super(ServiceManager.getService.call("autofill")); + } + + @Override + protected Object getWho() { + return IAutoFillManager.Stub.asInterface.call(ServiceManager.getService.call("autofill")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("autofill"); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new StartSession()); + } + + @ProxyMethod("startSession") + public static class StartSession extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args != null) { + for (int i = 0; i < args.length; i++) { + if (args[i] == null) { + continue; + } + + if (args[i] instanceof ComponentName) { + args[i] = new ComponentName(BlackBoxCore.getHostPkg(), ProxyManifest.getProxyActivity(BActivityThread.getAppPid())); + } + } + } + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IBluetoothManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IBluetoothManagerProxy.java new file mode 100644 index 0000000..2516db7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IBluetoothManagerProxy.java @@ -0,0 +1,47 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; + +import black.android.bluetooth.IBluetoothManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IBluetoothManagerProxy extends BinderInvocationStub { + public static final String TAG = "IBluetoothManagerProxy"; + + public IBluetoothManagerProxy() { + super(ServiceManager.getService.call("bluetooth_manager")); + } + + @Override + protected Object getWho() { + return IBluetoothManager.Stub.asInterface.call(ServiceManager.getService.call("bluetooth_manager")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("bluetooth_manager"); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new GetName()); + } + + @ProxyMethod("getName") + public static class GetName extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return null; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IConnectivityManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IConnectivityManagerProxy.java new file mode 100644 index 0000000..2e4906a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IConnectivityManagerProxy.java @@ -0,0 +1,38 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import black.android.net.IConnectivityManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; + +public class IConnectivityManagerProxy extends BinderInvocationStub { + public static final String TAG = "IConnectivityManagerProxy"; + + public IConnectivityManagerProxy() { + super(ServiceManager.getService.call(Context.CONNECTIVITY_SERVICE)); + } + + @Override + protected Object getWho() { + return IConnectivityManager.Stub.asInterface.call(ServiceManager.getService.call(Context.CONNECTIVITY_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.CONNECTIVITY_SERVICE); + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new ValueMethodProxy("getAllNetworkInfo", null)); + addMethodHook(new ValueMethodProxy("getAllNetworks",null)); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IContextHubServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IContextHubServiceProxy.java new file mode 100644 index 0000000..6ac4643 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IContextHubServiceProxy.java @@ -0,0 +1,40 @@ +package com.vcore.fake.service; + +import black.android.hardware.location.IContextHubService; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; +import com.vcore.utils.compat.BuildCompat; + +public class IContextHubServiceProxy extends BinderInvocationStub { + public IContextHubServiceProxy() { + super(ServiceManager.getService.call(getServiceName())); + } + + private static String getServiceName() { + return BuildCompat.isOreo() ? "contexthub" : "contexthub_service"; + } + + @Override + protected Object getWho() { + return IContextHubService.Stub.asInterface.call(ServiceManager.getService.call(getServiceName())); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(getServiceName()); + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new ValueMethodProxy("registerCallback", 0)); + addMethodHook(new ValueMethodProxy("getContextHubInfo", null)); + addMethodHook(new ValueMethodProxy("getContextHubHandles",new int[]{})); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDeviceIdentifiersPolicyProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDeviceIdentifiersPolicyProxy.java new file mode 100644 index 0000000..5cee674 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDeviceIdentifiersPolicyProxy.java @@ -0,0 +1,48 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; + +import black.android.os.IDeviceIdentifiersPolicyService; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.utils.Md5Utils; + +public class IDeviceIdentifiersPolicyProxy extends BinderInvocationStub { + public IDeviceIdentifiersPolicyProxy() { + super(ServiceManager.getService.call("device_identifiers")); + } + + @Override + protected Object getWho() { + return IDeviceIdentifiersPolicyService.Stub.asInterface.call(ServiceManager.getService.call("device_identifiers")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("device_identifiers"); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("getSerialForPackage")); + } + + @ProxyMethod("getSerialForPackage") + public static class GetSerialForPackage extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDevicePolicyManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDevicePolicyManagerProxy.java new file mode 100644 index 0000000..5598c22 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDevicePolicyManagerProxy.java @@ -0,0 +1,82 @@ +package com.vcore.fake.service; + +import android.content.ComponentName; +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.app.admin.IDevicePolicyManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class IDevicePolicyManagerProxy extends BinderInvocationStub { + public IDevicePolicyManagerProxy() { + super(ServiceManager.getService.call(Context.DEVICE_POLICY_SERVICE)); + } + + @Override + protected Object getWho() { + return IDevicePolicyManager.Stub.asInterface.call(ServiceManager.getService.call(Context.DEVICE_POLICY_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.DEVICE_POLICY_SERVICE); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("getStorageEncryptionStatus") + public static class GetStorageEncryptionStatus extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("getDeviceOwnerComponent") + public static class GetDeviceOwnerComponent extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return new ComponentName("", ""); + } + } + + @ProxyMethod("getDeviceOwnerName") + public static class GetDeviceOwnerName extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return "BlackBox"; + } + } + + @ProxyMethod("getProfileOwnerName") + public static class GetProfileOwnerName extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return "BlackBox"; + } + } + + @ProxyMethod("isDeviceProvisioned") + public static class IsDeviceProvisioned extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return true; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDisplayManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDisplayManagerProxy.java new file mode 100644 index 0000000..f23336a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IDisplayManagerProxy.java @@ -0,0 +1,49 @@ +package com.vcore.fake.service; + +import android.os.IInterface; + +import java.lang.reflect.Method; + +import black.android.hardware.display.DisplayManagerGlobal; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class IDisplayManagerProxy extends ClassInvocationStub { + public IDisplayManagerProxy() { } + + @Override + protected Object getWho() { + return DisplayManagerGlobal.mDm.get(DisplayManagerGlobal.getInstance.call()); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + Object dmg = DisplayManagerGlobal.getInstance.call(); + DisplayManagerGlobal.mDm.set(dmg, getProxyInvocation()); + + } + + @Override + protected void onBindMethod() { + addMethodHook(new CreateVirtualDisplay()); + } + + @Override + public boolean isBadEnv() { + Object dmg = DisplayManagerGlobal.getInstance.call(); + IInterface mDm = DisplayManagerGlobal.mDm.get(dmg); + return mDm != getProxyInvocation(); + } + + @ProxyMethod("createVirtualDisplay") + public static class CreateVirtualDisplay extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFingerprintManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFingerprintManagerProxy.java new file mode 100644 index 0000000..5d226a8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFingerprintManagerProxy.java @@ -0,0 +1,40 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import black.android.os.ServiceManager; +import black.android.view.IGraphicsStats; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +public class IFingerprintManagerProxy extends BinderInvocationStub { + public IFingerprintManagerProxy() { + super(ServiceManager.getService.call(Context.FINGERPRINT_SERVICE)); + } + + @Override + protected Object getWho() { + return IGraphicsStats.Stub.asInterface.call(ServiceManager.getService.call(Context.FINGERPRINT_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.FINGERPRINT_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new PkgMethodProxy("isHardwareDetected")); + addMethodHook(new PkgMethodProxy("hasEnrolledFingerprints")); + addMethodHook(new PkgMethodProxy("authenticate")); + addMethodHook(new PkgMethodProxy("cancelAuthentication")); + addMethodHook(new PkgMethodProxy("getEnrolledFingerprints")); + addMethodHook(new PkgMethodProxy("getAuthenticatorId")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFlymePermissionServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFlymePermissionServiceProxy.java new file mode 100644 index 0000000..5ff974f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IFlymePermissionServiceProxy.java @@ -0,0 +1,34 @@ +package com.vcore.fake.service; + +import android.os.IBinder; + +import black.android.os.ServiceManager; +import black.oem.flyme.IFlymePermissionService; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/9 12:34 + **/ +public class IFlymePermissionServiceProxy extends BinderInvocationStub { + public IFlymePermissionServiceProxy() { + super(ServiceManager.getService.call("flyme_permission")); + } + + @Override + protected Object getWho() { + return IFlymePermissionService.Stub.TYPE; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + addMethodHook(new PkgMethodProxy("noteIntentOperation")); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IGraphicsStatsProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IGraphicsStatsProxy.java new file mode 100644 index 0000000..2d78202 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IGraphicsStatsProxy.java @@ -0,0 +1,43 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.android.view.IGraphicsStats; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class IGraphicsStatsProxy extends BinderInvocationStub { + public IGraphicsStatsProxy() { + super(ServiceManager.getService.call("graphicsstats")); + } + + @Override + protected Object getWho() { + return IGraphicsStats.Stub.asInterface.call(ServiceManager.getService.call("graphicsstats")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("graphicsstats"); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("requestBufferForProcess") + public static class RequestBufferForProcess extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IJobServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IJobServiceProxy.java new file mode 100644 index 0000000..1bdc7f6 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IJobServiceProxy.java @@ -0,0 +1,86 @@ +package com.vcore.fake.service; + +import android.app.job.JobInfo; +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.app.job.IJobScheduler; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IJobServiceProxy extends BinderInvocationStub { + public static final String TAG = "JobServiceStub"; + + public IJobServiceProxy() { + super(ServiceManager.getService.call(Context.JOB_SCHEDULER_SERVICE)); + } + + @Override + protected Object getWho() { + return IJobScheduler.Stub.asInterface.call(ServiceManager.getService.call(Context.JOB_SCHEDULER_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.JOB_SCHEDULER_SERVICE); + + } + + + @ProxyMethod("schedule") + public static class Schedule extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + JobInfo jobInfo = (JobInfo) args[0]; + JobInfo proxyJobInfo = BlackBoxCore.getBJobManager() + .schedule(jobInfo); + args[0] = proxyJobInfo; + return method.invoke(who, args); + } + } + + @ProxyMethod("cancel") + public static class Cancel extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + args[0] = BlackBoxCore.getBJobManager() + .cancel(BActivityThread.getAppConfig().processName, (Integer) args[0]); + return method.invoke(who, args); + } + } + + @ProxyMethod("cancelAll") + public static class CancelAll extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + BlackBoxCore.getBJobManager().cancelAll(BActivityThread.getAppConfig().processName); + return method.invoke(who, args); + } + } + + @ProxyMethod("enqueue") + public static class Enqueue extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + JobInfo jobInfo = (JobInfo) args[0]; + JobInfo proxyJobInfo = BlackBoxCore.getBJobManager() + .schedule(jobInfo); + args[0] = proxyJobInfo; + return method.invoke(who, args); + } + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILauncherAppsProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILauncherAppsProxy.java new file mode 100644 index 0000000..2bdb7ec --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILauncherAppsProxy.java @@ -0,0 +1,38 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.content.pm.ILauncherApps; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.utils.MethodParameterUtils; + +public class ILauncherAppsProxy extends BinderInvocationStub { + public ILauncherAppsProxy() { + super(ServiceManager.getService.call(Context.LAUNCHER_APPS_SERVICE)); + } + + @Override + protected Object getWho() { + return ILauncherApps.Stub.asInterface.call(ServiceManager.getService.call(Context.LAUNCHER_APPS_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.LAUNCHER_APPS_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + // TODO: shouldHideFromSuggestions + return super.invoke(proxy, method, args); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILocationManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILocationManagerProxy.java new file mode 100644 index 0000000..c9adb86 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ILocationManagerProxy.java @@ -0,0 +1,259 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.location.ILocationListener; +import android.location.LocationManager; +import android.os.IInterface; +import android.util.Log; + +import java.lang.reflect.Method; +import java.text.SimpleDateFormat; +import java.util.Arrays; +import java.util.Date; +import java.util.Locale; +import java.util.Objects; + +import black.android.location.ILocationManager; +import black.android.location.provider.ProviderProperties; +import black.android.os.ServiceManager; +import com.vcore.app.BActivityThread; +import com.vcore.entity.location.BLocation; +import com.vcore.fake.frameworks.BLocationManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.context.LocationListenerProxy; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.BuildCompat; + +public class ILocationManagerProxy extends BinderInvocationStub { + public static final String TAG = "ILocationManagerProxy"; + + public ILocationManagerProxy() { + super(ServiceManager.getService.call(Context.LOCATION_SERVICE)); + } + + @Override + protected Object getWho() { + return ILocationManager.Stub.asInterface.call(ServiceManager.getService.call(Context.LOCATION_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.LOCATION_SERVICE); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return super.invoke(proxy, method, args); + } + + + @ProxyMethod("registerGnssStatusCallback") + public static class RegisterGnssStatusCallback extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BLocationManager.isFakeLocationEnable()) { + Object transport = MethodParameterUtils.getFirstParam(args, black.android.location.LocationManager.GnssStatusListenerTransport.REF.getClazz()); + + if (transport != null) { + black.android.location.LocationManager.GnssStatusListenerTransport.onGnssStarted.call(transport); + BLocation location = BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()); + + if (location != null) { + try { + String date = new SimpleDateFormat("HHmmss:SS", Locale.US).format(new Date()); + String latitude = BLocation.getGPSLatitude(location.getLatitude()); + String longitude = BLocation.getGPSLatitude(location.getLongitude()); + String latitudeNorthWest = BLocation.getNorthWest(location); + String longitudeSouthEast = BLocation.getSouthEast(location); + String $GPGGA = BLocation.checkSum(String.format("$GPGGA,%s,%s,%s,%s,%s,1,%s,692,.00,M,.00,M,,,", date, latitude, latitudeNorthWest, longitude, longitudeSouthEast, location.convert2SystemLocation().getExtras().getInt("satellites"))); + String $GPRMC = BLocation.checkSum(String.format("$GPRMC,%s,A,%s,%s,%s,%s,0,0,260717,,,A,", date, latitude, latitudeNorthWest, longitude, longitudeSouthEast)); + + black.android.location.LocationManager.GnssStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), "$GPGSV,1,1,04,12,05,159,36,15,41,087,15,19,38,262,30,31,56,146,19,*73"); + if (BuildCompat.isN()) { + black.android.location.LocationManager.GpsStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), "$GPGSV,1,1,04,12,05,159,36,15,41,087,15,19,38,262,30,31,56,146,19,*73"); + black.android.location.LocationManager.GpsStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), $GPGGA); + black.android.location.LocationManager.GpsStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), "$GPVTG,0,T,0,M,0,N,0,K,A,*25"); + black.android.location.LocationManager.GpsStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), $GPRMC); + black.android.location.LocationManager.GpsStatusListenerTransport.onNmeaReceived.call(transport, System.currentTimeMillis(), "$GPGSA,A,2,12,15,19,31,,,,,,,,,604,712,986,*27"); + } + } catch (Exception e) { + e.printStackTrace(); + } + } + } + return true; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("registerLocationListener") + public static class RegisterLocationListener extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BLocationManager.isFakeLocationEnable()) { + Object listener = MethodParameterUtils.getFirstParamByInstance(args, ILocationListener.Stub.class); + if (listener != null) { + try { + black.android.location.LocationManager.LocationListenerTransport.mListener.set(listener, + new LocationListenerProxy().wrapper(black.android.location.LocationManager.LocationListenerTransport.mListener.get())); + } catch (Exception e) { + e.printStackTrace(); + } + } + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getLastLocation") + public static class GetLastLocation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "GetLastLocation"); + if (BLocationManager.isFakeLocationEnable()) { + return BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()).convert2SystemLocation(); + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getLastKnownLocation") + public static class GetLastKnownLocation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "GetLastKnownLocation"); + if (BLocationManager.isFakeLocationEnable()) { + return BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()).convert2SystemLocation(); + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getCurrentLocation") + public static class GetCurrentLocation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "GetCurrentLocation"); + if (BLocationManager.isFakeLocationEnable()) { + return BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()).convert2SystemLocation(); + } + return method.invoke(who, args); + } + } + + @ProxyMethod("requestLocationUpdates") + public static class RequestLocationUpdates extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BLocationManager.isFakeLocationEnable()) { + Log.d(TAG, "isFakeLocationEnable RequestLocationUpdates"); + + if (args[1] instanceof IInterface) { + IInterface listener = (IInterface) args[1]; + BLocationManager.get().requestLocationUpdates(listener.asBinder()); + return 0; + } + } + return method.invoke(who, args); + } + } + + @ProxyMethod("removeUpdates") + public static class RemoveUpdates extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args[0] instanceof IInterface) { + IInterface listener = (IInterface) args[0]; + BLocationManager.get().removeUpdates(listener.asBinder()); + return 0; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getProviderProperties") + public static class GetProviderProperties extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Object providerProperties = method.invoke(who, args); + if (BLocationManager.isFakeLocationEnable()) { + ProviderProperties.mHasNetworkRequirement.set(providerProperties, false); + + if (BLocationManager.get().getCell(BActivityThread.getUserId(), BActivityThread.getAppPackageName()) == null) { + ProviderProperties.mHasCellRequirement.set(providerProperties, false); + } + } + return providerProperties; + } + } + + @ProxyMethod("removeGpsStatusListener") + public static class RemoveGpsStatusListener extends MethodHook { + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceLastAppPkg(args); + if (BLocationManager.isFakeLocationEnable()) { + return 0; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getBestProvider") + public static class GetBestProvider extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BLocationManager.isFakeLocationEnable()) { + return LocationManager.GPS_PROVIDER; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getAllProviders") + public static class GetAllProviders extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Arrays.asList(LocationManager.GPS_PROVIDER, LocationManager.NETWORK_PROVIDER); + } + } + + @ProxyMethod("isProviderEnabledForUser") + public static class isProviderEnabledForUser extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String provider = (String) args[0]; + return Objects.equals(provider, LocationManager.GPS_PROVIDER); + } + } + + @ProxyMethod("setExtraLocationControllerPackageEnabled") + public static class setExtraLocationControllerPackageEnabled extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaRouterServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaRouterServiceProxy.java new file mode 100644 index 0000000..28203ea --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaRouterServiceProxy.java @@ -0,0 +1,59 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.media.IMediaRouterService; +import black.android.os.ServiceManager; +import com.vcore.core.system.accounts.RegisteredServicesParser; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class IMediaRouterServiceProxy extends BinderInvocationStub { + public IMediaRouterServiceProxy() { + super(ServiceManager.getService.call(Context.MEDIA_ROUTER_SERVICE)); + } + + @Override + protected Object getWho() { + return IMediaRouterService.Stub.asInterface.call(ServiceManager.getService.call(Context.MEDIA_ROUTER_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.MEDIA_ROUTER_SERVICE); + + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("registerClientAsUser") + public static class registerClientAsUser extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return method.invoke(who, args); + } + } + + @ProxyMethod("registerRouter2") + public static class registerRouter2 extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaSessionManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaSessionManagerProxy.java new file mode 100644 index 0000000..d35ea16 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IMediaSessionManagerProxy.java @@ -0,0 +1,47 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.media.session.ISessionManager; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IMediaSessionManagerProxy extends BinderInvocationStub { + public IMediaSessionManagerProxy() { + super(ServiceManager.getService.call(Context.MEDIA_SESSION_SERVICE)); + } + + @Override + protected Object getWho() { + return ISessionManager.Stub.asInterface.call(ServiceManager.getService.call(Context.MEDIA_SESSION_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.MEDIA_SESSION_SERVICE); + + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("createSession") + public static class CreateSession extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args != null && args.length > 0 && args[0] instanceof String) { + args[0] = BlackBoxCore.getHostPkg(); + } + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INetworkManagementServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INetworkManagementServiceProxy.java new file mode 100644 index 0000000..3800374 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INetworkManagementServiceProxy.java @@ -0,0 +1,52 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; + +import black.android.os.INetworkManagementService; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.UidMethodProxy; +import com.vcore.utils.MethodParameterUtils; + +public class INetworkManagementServiceProxy extends BinderInvocationStub { + + public INetworkManagementServiceProxy() { + super(ServiceManager.getService.call("network_management")); + } + + @Override + protected Object getWho() { + return INetworkManagementService.Stub.asInterface.call(ServiceManager.getService.call("network_management")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("network_management"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new UidMethodProxy("setUidCleartextNetworkPolicy", 0)); + addMethodHook(new UidMethodProxy("setUidMeteredNetworkBlacklist", 0)); + addMethodHook(new UidMethodProxy("setUidMeteredNetworkWhitelist", 0)); + } + + @ProxyMethod("getNetworkStatsUidDetail") + public static class GetNetworkStatsUidDetail extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstUid(args); + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/INotificationManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INotificationManagerProxy.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/INotificationManagerProxy.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INotificationManagerProxy.java index a88c599..9cbc3bb 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/fake/service/INotificationManagerProxy.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/INotificationManagerProxy.java @@ -1,56 +1,51 @@ -package top.niunaijun.blackbox.fake.service; +package com.vcore.fake.service; import android.app.Notification; import android.app.NotificationChannel; import android.app.NotificationChannelGroup; import android.content.Context; +import android.content.Intent; import android.os.Build; +import android.os.IBinder; import androidx.annotation.RequiresApi; import java.lang.reflect.Method; import java.util.List; -import black.android.app.BRNotificationManager; -import black.android.content.pm.BRParceledListSlice; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.fake.frameworks.BNotificationManager; -import top.niunaijun.blackbox.fake.hook.BinderInvocationStub; -import top.niunaijun.blackbox.fake.hook.MethodHook; -import top.niunaijun.blackbox.fake.hook.ProxyMethod; -import top.niunaijun.blackbox.utils.MethodParameterUtils; -import top.niunaijun.blackbox.utils.compat.BuildCompat; -import top.niunaijun.blackbox.utils.compat.ParceledListSliceCompat; - -/** - * Created by Milk on 4/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ +import black.android.app.NotificationManager; +import black.android.content.pm.ParceledListSlice; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.frameworks.BActivityManager; +import com.vcore.fake.frameworks.BNotificationManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.ParceledListSliceCompat; + public class INotificationManagerProxy extends BinderInvocationStub { public static final String TAG = "INotificationManagerProxy"; public INotificationManagerProxy() { - super(BRNotificationManager.get().getService().asBinder()); + super(NotificationManager.getService.call().asBinder()); } @Override protected Object getWho() { - return BRNotificationManager.get().getService(); + return NotificationManager.getService.call(); } @Override protected void inject(Object baseInvocation, Object proxyInvocation) { - BRNotificationManager.get()._set_sService(getProxyInvocation()); + NotificationManager.sService.set(getProxyInvocation()); replaceSystemService(Context.NOTIFICATION_SERVICE); } @Override public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { -// Slog.d(TAG, "call: " + method.getName()); MethodParameterUtils.replaceAllAppPkg(args); return super.invoke(proxy, method, args); } @@ -60,13 +55,13 @@ public boolean isBadEnv() { return false; } + @ProxyMethod("getNotificationChannel") public static class GetNotificationChannel extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { - NotificationChannel notificationChannel = BNotificationManager.get().getNotificationChannel((String) args[args.length - 1]); - return notificationChannel; + return BNotificationManager.get().getNotificationChannel((String) args[args.length - 1]); } } @@ -87,6 +82,7 @@ public static class CancelNotificationWithTag extends MethodHook { protected Object hook(Object who, Method method, Object[] args) throws Throwable { String tag = (String) args[getTagIndex()]; int id = (int) args[getIdIndex()]; + BNotificationManager.get().cancelNotificationWithTag(id, tag); return 0; } @@ -111,6 +107,7 @@ public static class EnqueueNotificationWithTag extends MethodHook { protected Object hook(Object who, Method method, Object[] args) throws Throwable { String tag = (String) args[getTagIndex()]; int id = (int) args[getIdIndex()]; + Notification notification = MethodParameterUtils.getFirstParam(args, Notification.class); BNotificationManager.get().enqueueNotificationWithTag(id, tag, notification); return 0; @@ -131,9 +128,11 @@ public static class CreateNotificationChannels extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { - List list = BRParceledListSlice.get(args[1]).getList(); - if (list == null) + List list = ParceledListSlice.getList.call(args[1]); + if (list == null) { return 0; + } + for (Object o : list) { BNotificationManager.get().createNotificationChannel((NotificationChannel) o); } @@ -157,7 +156,7 @@ public static class CreateNotificationChannelGroups extends MethodHook { @Override protected Object hook(Object who, Method method, Object[] args) throws Throwable { - List list = BRParceledListSlice.get(args[1]).getList(); + List list = ParceledListSlice.getList.call(args[1]); for (Object o : list) { BNotificationManager.get().createNotificationChannelGroup((NotificationChannelGroup) o); } @@ -184,4 +183,17 @@ protected Object hook(Object who, Method method, Object[] args) throws Throwable return ParceledListSliceCompat.create(notificationChannelGroups); } } + + @ProxyMethod("removeEdgeNotification") + public static class RemoveEdgeNotification extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (BuildCompat.isSamsung()){ + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who,args); + } + return null; + } + } } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPackageManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPackageManagerProxy.java new file mode 100644 index 0000000..03688e8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPackageManagerProxy.java @@ -0,0 +1,499 @@ +package com.vcore.fake.service; + +import android.content.ComponentName; +import android.content.Intent; +import android.content.pm.ActivityInfo; +import android.content.pm.ApplicationInfo; +import android.content.pm.PackageInfo; +import android.content.pm.PackageManager; +import android.content.pm.ProviderInfo; +import android.content.pm.ResolveInfo; +import android.content.pm.ServiceInfo; +import android.content.pm.VersionedPackage; + +import java.lang.reflect.Method; +import java.util.ArrayList; +import java.util.Arrays; +import java.util.List; + +import black.android.app.ActivityThread; +import black.android.app.ApplicationPackageManager; +import black.android.app.ContextImpl; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.core.env.AppSystemEnv; +import com.vcore.core.system.pm.BPackageManagerService; +import com.vcore.core.system.pm.BPackageSettings; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.Slog; +import com.vcore.utils.compat.BuildCompat; +import com.vcore.utils.compat.ParceledListSliceCompat; + +public class IPackageManagerProxy extends BinderInvocationStub { + public static final String TAG = "PackageManagerProxy"; + + public IPackageManagerProxy() { + super(ActivityThread.sPackageManager.get().asBinder()); + } + + @Override + protected Object getWho() { + return ActivityThread.sPackageManager.get(); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + ActivityThread.sPackageManager.set(proxyInvocation); + replaceSystemService("package"); + + Object systemContext = ActivityThread.getSystemContext.call(BlackBoxCore.mainThread()); + PackageManager packageManager = ContextImpl.mPackageManager.get(systemContext); + if (packageManager != null) { + try { + ApplicationPackageManager.mPM.set(packageManager, proxyInvocation); + } catch (Exception e) { + e.printStackTrace(); + } + } + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new PkgMethodProxy("getPackageUid")); + addMethodHook(new PkgMethodProxy("canRequestPackageInstalls")); + if (BuildCompat.isOreo()) { + addMethodHook("getPackageInfoVersioned", new MethodHook() { + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + VersionedPackage versionedPackage = (VersionedPackage) args[0]; + String packageName = versionedPackage.getPackageName(); + PackageInfo packageInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + packageInfo = BlackBoxCore.getBPackageManager().getPackageInfo(packageName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + packageInfo = BlackBoxCore.getBPackageManager().getPackageInfo(packageName, flags, BActivityThread.getUserId()); + } + + if (packageInfo != null) { + return packageInfo; + } + + if (AppSystemEnv.isOpenPackage(packageName)) { + return method.invoke(who, args); + } + return null; + } + }); + } + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("resolveIntent") + public static class ResolveIntent extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[0]; + String resolvedType = (String) args[1]; + ResolveInfo resolveInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[2]; + resolveInfo = BlackBoxCore.getBPackageManager().resolveIntent(intent, resolvedType, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[2]; + resolveInfo = BlackBoxCore.getBPackageManager().resolveIntent(intent, resolvedType, flags, BActivityThread.getUserId()); + } + + if (resolveInfo != null) { + return resolveInfo; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("resolveService") + public static class ResolveService extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[0]; + String resolvedType = (String) args[1]; + ResolveInfo resolveInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[2]; + resolveInfo = BlackBoxCore.getBPackageManager().resolveService(intent, Math.toIntExact(flags), resolvedType, BActivityThread.getUserId()); + } else { + int flags = (int) args[2]; + resolveInfo = BlackBoxCore.getBPackageManager().resolveService(intent, flags, resolvedType, BActivityThread.getUserId()); + } + + if (resolveInfo != null) { + return resolveInfo; + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getPackageInfo") + public static class GetPackageInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String packageName = (String) args[0]; + PackageInfo packageInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + packageInfo = BlackBoxCore.getBPackageManager().getPackageInfo(packageName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + packageInfo = BlackBoxCore.getBPackageManager().getPackageInfo(packageName, flags, BActivityThread.getUserId()); + } + + if (packageInfo != null) { + return packageInfo; + } + + if (AppSystemEnv.isOpenPackage(packageName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("getProviderInfo") + public static class GetProviderInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName componentName = (ComponentName) args[0]; + ProviderInfo providerInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + providerInfo = BlackBoxCore.getBPackageManager().getProviderInfo(componentName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + providerInfo = BlackBoxCore.getBPackageManager().getProviderInfo(componentName, flags, BActivityThread.getUserId()); + } + + if (providerInfo != null) { + return providerInfo; + } + + if (AppSystemEnv.isOpenPackage(componentName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("getReceiverInfo") + public static class GetReceiverInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName componentName = (ComponentName) args[0]; + ActivityInfo receiverInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + receiverInfo = BlackBoxCore.getBPackageManager().getReceiverInfo(componentName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + receiverInfo = BlackBoxCore.getBPackageManager().getReceiverInfo(componentName, flags, BActivityThread.getUserId()); + } + + if (receiverInfo != null) { + return receiverInfo; + } + + if (AppSystemEnv.isOpenPackage(componentName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("getActivityInfo") + public static class GetActivityInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName componentName = (ComponentName) args[0]; + ActivityInfo activityInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + activityInfo = BlackBoxCore.getBPackageManager().getActivityInfo(componentName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + activityInfo = BlackBoxCore.getBPackageManager().getActivityInfo(componentName, Math.toIntExact(flags), BActivityThread.getUserId()); + } + + if (activityInfo != null) { + return activityInfo; + } + + if (AppSystemEnv.isOpenPackage(componentName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("getServiceInfo") + public static class GetServiceInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName componentName = (ComponentName) args[0]; + ServiceInfo serviceInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + serviceInfo = BlackBoxCore.getBPackageManager().getServiceInfo(componentName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + serviceInfo = BlackBoxCore.getBPackageManager().getServiceInfo(componentName, flags, BActivityThread.getUserId()); + } + + if (serviceInfo != null) { + return serviceInfo; + } + + if (AppSystemEnv.isOpenPackage(componentName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("getInstalledApplications") + public static class GetInstalledApplications extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + List installedApplications; + + if (BuildCompat.isT()) { + long flags = (long) args[0]; + installedApplications = BlackBoxCore.getBPackageManager().getInstalledApplications(Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[0]; + installedApplications = BlackBoxCore.getBPackageManager().getInstalledApplications(flags, BActivityThread.getUserId()); + } + return ParceledListSliceCompat.create(installedApplications); + } + } + + @ProxyMethod("queryIntentActivities") + public static class QueryIntentActivities extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = (Intent) args[0]; + String resolvedType = (String) args[1]; + List intentActivities; + + if (BuildCompat.isT()) { + long flags = (long) args[2]; + intentActivities = BlackBoxCore.getBPackageManager().queryIntentActivities(intent, Math.toIntExact(flags), resolvedType, BActivityThread.getUserId()); + } else { + int flags = (int) args[2]; + intentActivities = BlackBoxCore.getBPackageManager().queryIntentActivities(intent, flags, resolvedType, BActivityThread.getUserId()); + } + return ParceledListSliceCompat.create(intentActivities); + } + } + + @ProxyMethod("getInstalledPackages") + public static class GetInstalledPackages extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + List installedPackages; + + if (BuildCompat.isT()) { + long flags = (long) args[0]; + installedPackages = BlackBoxCore.getBPackageManager().getInstalledPackages(Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[0]; + installedPackages = BlackBoxCore.getBPackageManager().getInstalledPackages(flags, BActivityThread.getUserId()); + } + return ParceledListSliceCompat.create(installedPackages); + } + } + + @ProxyMethod("getApplicationInfo") + public static class GetApplicationInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String packageName = (String) args[0]; + ApplicationInfo applicationInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + applicationInfo = BlackBoxCore.getBPackageManager().getApplicationInfo(packageName, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + applicationInfo = BlackBoxCore.getBPackageManager().getApplicationInfo(packageName, flags, BActivityThread.getUserId()); + } + + if (applicationInfo != null) { + return applicationInfo; + } + + if (AppSystemEnv.isOpenPackage(packageName)) { + return method.invoke(who, args); + } + return null; + } + } + + @ProxyMethod("queryContentProviders") + public static class QueryContentProviders extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + List providers; + + if (BuildCompat.isT()) { + long flags = (long) args[2]; + + providers = BlackBoxCore.getBPackageManager() + .queryContentProviders(BActivityThread.getAppProcessName(), BActivityThread.getBUid(), Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[2]; + + providers = BlackBoxCore.getBPackageManager() + .queryContentProviders(BActivityThread.getAppProcessName(), BActivityThread.getBUid(), flags, BActivityThread.getUserId()); + } + return ParceledListSliceCompat.create(providers); + } + } + + @ProxyMethod("queryIntentReceivers") + public static class QueryBroadcastReceivers extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Intent intent = MethodParameterUtils.getFirstParam(args, Intent.class); + String type = MethodParameterUtils.getFirstParam(args, String.class); + List resolves; + + if (BuildCompat.isT()) { + Long flags = MethodParameterUtils.getFirstParam(args, Long.class); + resolves = BlackBoxCore.getBPackageManager().queryBroadcastReceivers(intent, Math.toIntExact(flags), type, BActivityThread.getUserId()); + } else { + Integer flags = MethodParameterUtils.getFirstParam(args, Integer.class); + resolves = BlackBoxCore.getBPackageManager().queryBroadcastReceivers(intent, flags, type, BActivityThread.getUserId()); + } + + Slog.d(TAG, "queryIntentReceivers: " + resolves); + + // http://androidxref.com/7.0.0_r1/xref/frameworks/base/core/java/android/app/ApplicationPackageManager.java#872 + if (BuildCompat.isN()) { + return ParceledListSliceCompat.create(resolves); + } + + // http://androidxref.com/6.0.1_r10/xref/frameworks/base/core/java/android/app/ApplicationPackageManager.java#699 + return resolves; + } + } + + @ProxyMethod("resolveContentProvider") + public static class ResolveContentProvider extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String authority = (String) args[0]; + ProviderInfo providerInfo; + + if (BuildCompat.isT()) { + long flags = (long) args[1]; + providerInfo = BlackBoxCore.getBPackageManager().resolveContentProvider(authority, Math.toIntExact(flags), BActivityThread.getUserId()); + } else { + int flags = (int) args[1]; + providerInfo = BlackBoxCore.getBPackageManager().resolveContentProvider(authority, flags, BActivityThread.getUserId()); + } + + if (providerInfo == null) { + return method.invoke(who, args); + } + return providerInfo; + } + } + + @ProxyMethod("getPackagesForUid") + public static class GetPackagesForUid extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int uid = (Integer) args[0]; + if (uid == BlackBoxCore.getHostUid()) { + args[0] = BActivityThread.getBUid(); + uid = (int) args[0]; + } + + String[] packagesForUid = BlackBoxCore.getBPackageManager().getPackagesForUid(uid); + Slog.d(TAG, args[0] + " , " + BActivityThread.getAppProcessName() + " getPackagesForUid: " + Arrays.toString(packagesForUid)); + return packagesForUid; + } + } + + @ProxyMethod("getInstallerPackageName") + public static class GetInstallerPackageName extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return "com.android.vending"; + } + } + + @ProxyMethod("getSharedLibraries") + public static class GetSharedLibraries extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + String packageName = (String) args[0]; + BPackageSettings packageSettings = BPackageManagerService.get().getBPackageSetting(packageName); + if (packageSettings != null) { + ArrayList packageLibraries = new ArrayList<>(); + if (packageSettings.pkg.usesLibraries != null) { + packageLibraries.addAll(packageSettings.pkg.usesLibraries); + } + + if (packageSettings.pkg.usesOptionalLibraries != null) { + packageLibraries.addAll(packageSettings.pkg.usesOptionalLibraries); + } + return ParceledListSliceCompat.create(packageLibraries); + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getComponentEnabledSetting") + public static class GetComponentEnabledSetting extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return PackageManager.COMPONENT_ENABLED_STATE_DEFAULT; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPermissionManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPermissionManagerProxy.java new file mode 100644 index 0000000..3b1f4ef --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPermissionManagerProxy.java @@ -0,0 +1,93 @@ +package com.vcore.fake.service; + +import android.content.pm.PackageManager; +import android.os.Build; + +import java.lang.reflect.Method; + +import black.android.app.ActivityThread; +import black.android.app.ApplicationPackageManager; +import black.android.app.ContextImpl; +import black.android.os.ServiceManager; +import black.android.permission.IPermissionManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.fake.service.base.UidMethodProxy; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.BuildCompat; + +public class IPermissionManagerProxy extends BinderInvocationStub { + public static final String TAG = "IPermissionManagerProxy"; + + public IPermissionManagerProxy() { + super(ServiceManager.getService.call("permissionmgr")); + } + + @Override + protected Object getWho() { + return IPermissionManager.Stub.asInterface.call(ServiceManager.getService.call("permissionmgr")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("permissionmgr"); + ActivityThread.sPermissionManager.set(proxyInvocation); + + Object systemContext = ActivityThread.getSystemContext.call(BlackBoxCore.mainThread()); + PackageManager packageManager = ContextImpl.mPackageManager.get(systemContext); + if (packageManager != null) { + try { + ApplicationPackageManager.mPermissionManager.set(packageManager, proxyInvocation); + } catch (Exception e) { + e.printStackTrace(); + } + } + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new PkgMethodProxy("getPermissionInfo")); + addMethodHook(new PkgMethodProxy("getPermissionFlags")); + addMethodHook(new PkgMethodProxy("updatePermissionFlags")); + addMethodHook(new PkgMethodProxy("grantRuntimePermission")); + addMethodHook(new PkgMethodProxy("revokeRuntimePermission")); + addMethodHook(new PkgMethodProxy("shouldShowRequestPermissionRationale")); + addMethodHook(new PkgMethodProxy("isPermissionRevokedByPolicy")); + addMethodHook(new PkgMethodProxy("startOneTimePermissionSession")); + addMethodHook(new PkgMethodProxy("stopOneTimePermissionSession")); + addMethodHook(new PkgMethodProxy("setAutoRevokeExempted")); + addMethodHook(new PkgMethodProxy("isAutoRevokeExempted")); + + if (BuildCompat.isT()) { + addMethodHook(new PkgMethodProxy("getAllowlistedRestrictedPermissions")); + addMethodHook(new PkgMethodProxy("addAllowlistedRestrictedPermission")); + addMethodHook(new PkgMethodProxy("removeAllowlistedRestrictedPermission")); + } else if (Build.VERSION.SDK_INT == Build.VERSION_CODES.S) { + addMethodHook(new PkgMethodProxy("revokePostNotificationPermissionWithoutKillForTest")); + } else { + addMethodHook(new PkgMethodProxy("checkPermission")); + addMethodHook(new UidMethodProxy("checkUidPermission", 1)); + addMethodHook(new PkgMethodProxy("getWhitelistedRestrictedPermissions")); + addMethodHook(new PkgMethodProxy("addWhitelistedRestrictedPermission")); + addMethodHook(new PkgMethodProxy("removeWhitelistedRestrictedPermission")); + addMethodHook(new PkgMethodProxy("setDefaultBrowser")); + addMethodHook(new PkgMethodProxy("grantDefaultPermissionsToActiveLuiApp")); + addMethodHook("checkDeviceIdentifierAccess", new MethodHook() { + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + MethodParameterUtils.replaceLastUid(args); + return method.invoke(who, args); + } + }); + } + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPersistentDataBlockServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPersistentDataBlockServiceProxy.java new file mode 100644 index 0000000..57fd714 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPersistentDataBlockServiceProxy.java @@ -0,0 +1,40 @@ +package com.vcore.fake.service; + +import black.android.os.ServiceManager; +import black.android.service.persistentdata.IPersistentDataBlockService; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; + +public class IPersistentDataBlockServiceProxy extends BinderInvocationStub { + + public IPersistentDataBlockServiceProxy() { + super(ServiceManager.getService.call("persistent_data_block")); + } + + @Override + protected Object getWho() { + return IPersistentDataBlockService.Stub.asInterface.call(ServiceManager.getService.call("persistent_data_block")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("persistent_data_block"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new ValueMethodProxy("write", -1)); + addMethodHook(new ValueMethodProxy("read", new byte[0])); + addMethodHook(new ValueMethodProxy("wipe", null)); + addMethodHook(new ValueMethodProxy("getDataBlockSize", 0)); + addMethodHook(new ValueMethodProxy("getMaximumDataBlockSize", 0)); + addMethodHook(new ValueMethodProxy("setOemUnlockEnabled", 0)); + addMethodHook(new ValueMethodProxy("getOemUnlockEnabled", false)); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhoneSubInfoProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhoneSubInfoProxy.java new file mode 100644 index 0000000..8df8a5b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhoneSubInfoProxy.java @@ -0,0 +1,119 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.util.Log; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.android.telephony.TelephonyManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.utils.Md5Utils; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.BuildCompat; + +public class IPhoneSubInfoProxy extends BinderInvocationStub { + public static final String TAG = "IPhoneSubInfoProxy"; + + public IPhoneSubInfoProxy() { + super(ServiceManager.getService.call("iphonesubinfo")); + } + + @Override + protected Object getWho() { + if (BuildCompat.isR()) { + return TelephonyManager.sIPhoneSubInfo.get(); + } + android.telephony.TelephonyManager telephonyManager = (android.telephony.TelephonyManager) BlackBoxCore.getContext().getSystemService(Context.TELEPHONY_SERVICE); + return TelephonyManager.getSubscriberInfo.call(telephonyManager); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + if (BuildCompat.isR()) { + TelephonyManager.sIPhoneSubInfo.set(proxyInvocation); + } + replaceSystemService("iphonesubinfo"); + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + Log.e(TAG, "Test"); + MethodParameterUtils.replaceLastAppPkg(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("getNaiForSubscriber")); + addMethodHook(new PkgMethodProxy("getDeviceSvn")); + addMethodHook(new PkgMethodProxy("getDeviceSvnUsingSubId")); + addMethodHook(new PkgMethodProxy("getGroupIdLevel1")); + addMethodHook(new PkgMethodProxy("getGroupIdLevel1ForSubscriber")); + addMethodHook(new PkgMethodProxy("getLine1AlphaTag")); + addMethodHook(new PkgMethodProxy("getLine1AlphaTagForSubscriber")); + addMethodHook(new PkgMethodProxy("getMsisdn")); + addMethodHook(new PkgMethodProxy("getMsisdnForSubscriber")); + addMethodHook(new PkgMethodProxy("getVoiceMailNumber")); + addMethodHook(new PkgMethodProxy("getVoiceMailNumberForSubscriber")); + addMethodHook(new PkgMethodProxy("getVoiceMailAlphaTag")); + addMethodHook(new PkgMethodProxy("getVoiceMailAlphaTagForSubscriber")); + addMethodHook(new PkgMethodProxy("getLine1Number")); + } + + @ProxyMethod("getSubscriberId") + private static class GetSubscriberId extends MethodHook{ + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + try { + if (BuildCompat.isQ()) { + return "unknown"; + } + return method.invoke(who, method, args); + } catch (Throwable th) { + return "unknown"; + } + } + } + + + @ProxyMethod("getLine1NumberForSubscriber") + public static class GetLine1NumberForSubscriber extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return null; + } + } + + @ProxyMethod("getSubscriberIdForSubscriber") + public static class GetSubscriberIdForSubscriber extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("getIccSerialNumber") + public static class GetIccSerialNumber extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return "89860221919704198154"; + } + } + + @ProxyMethod("getIccSerialNumberForSubscriber") + public static class GetIccSerialNumberForSubscriber extends GetIccSerialNumber { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhysicalFlingManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhysicalFlingManagerProxy.java new file mode 100644 index 0000000..e24707a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPhysicalFlingManagerProxy.java @@ -0,0 +1,40 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IBinder; + +import black.android.os.ServiceManager; +import black.oem.vivo.IPhysicalFlingManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:11 + **/ +public class IPhysicalFlingManagerProxy extends BinderInvocationStub { + public IPhysicalFlingManagerProxy() { + super(ServiceManager.getService.call("physical_fling_service")); + } + + @Override + protected Object getWho() { + return IPhysicalFlingManager.Stub.asInterface.call(ServiceManager.getService.call("physical_fling_service")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("physical_fling_service"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("isSupportPhysicalFling")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPopupCameraManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPopupCameraManagerProxy.java new file mode 100644 index 0000000..f653dc4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPopupCameraManagerProxy.java @@ -0,0 +1,40 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import black.android.os.ServiceManager; +import black.oem.vivo.IPopupCameraManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:19 + **/ +public class IPopupCameraManagerProxy extends BinderInvocationStub { + + public IPopupCameraManagerProxy() { + super(ServiceManager.getService.call("popup_camera_service")); + } + + @Override + protected Object getWho() { + return IPopupCameraManager.Stub.asInterface.call(ServiceManager.getService.call("popup_camera_service")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("popup_camera_service"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("notifyCameraStatus")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPowerManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPowerManagerProxy.java new file mode 100644 index 0000000..0dfe7ef --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IPowerManagerProxy.java @@ -0,0 +1,42 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import black.android.os.IPowerManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; + +public class IPowerManagerProxy extends BinderInvocationStub { + public IPowerManagerProxy() { + super(ServiceManager.getService.call(Context.POWER_SERVICE)); + } + + @Override + protected Object getWho() { + return IPowerManager.Stub.asInterface.call(ServiceManager.getService.call(Context.POWER_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.POWER_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new ValueMethodProxy("acquireWakeLock", 0)); + addMethodHook(new ValueMethodProxy("acquireWakeLockWithUid", 0)); + addMethodHook(new ValueMethodProxy("releaseWakeLock", 0)); + addMethodHook(new ValueMethodProxy("updateWakeLockWorkSource", 0)); + addMethodHook(new ValueMethodProxy("isWakeLockLevelSupported", true)); + addMethodHook(new ValueMethodProxy("reboot", null)); + addMethodHook(new ValueMethodProxy("rebootSafeMode", null)); + addMethodHook(new ValueMethodProxy("shutdown", null)); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IRoleManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IRoleManagerProxy.java new file mode 100644 index 0000000..9f65542 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IRoleManagerProxy.java @@ -0,0 +1,43 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IBinder; + +import black.android.os.IPowerManager; +import black.android.os.ServiceManager; +import black.android.role.IRoleManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.fake.service.base.ValueMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 19:45 + **/ +public class IRoleManagerProxy extends BinderInvocationStub { + + public IRoleManagerProxy() { + super(ServiceManager.getService.call(Context.ROLE_SERVICE)); + } + + @Override + protected Object getWho() { + return IRoleManager.Stub.asInterface.call(ServiceManager.getService.call(Context.ROLE_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.ROLE_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("isRoleHeld")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISearchManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISearchManagerProxy.java new file mode 100644 index 0000000..c16de27 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISearchManagerProxy.java @@ -0,0 +1,68 @@ +package com.vcore.fake.service; + +import android.content.ComponentName; +import android.content.Context; +import android.content.pm.ActivityInfo; +import android.os.IBinder; + +import java.lang.reflect.Method; + +import black.android.app.ISearchManager; +import black.android.os.ServiceManager; +import black.android.role.IRoleManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 19:56 + **/ +public class ISearchManagerProxy extends BinderInvocationStub { + + public ISearchManagerProxy() { + super(ServiceManager.getService.call(Context.SEARCH_SERVICE)); + } + + @Override + protected Object getWho() { + return ISearchManager.Stub.asInterface.call(ServiceManager.getService.call(Context.SEARCH_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("search"); + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("launchLegacyAssist")); + } + + private static class GetSearchableInfo extends MethodHook{ + + @Override + protected String getMethodName() { + return "getSearchableInfo"; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + ComponentName component = (ComponentName) args[0]; + if (component != null) { + ActivityInfo activityInfo = BlackBoxCore.getPackageManager().getActivityInfo(component, 0); + if (activityInfo != null) { + return null; + } + } + return method.invoke(who,args); + } + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IShortcutManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IShortcutManagerProxy.java new file mode 100644 index 0000000..97eff40 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IShortcutManagerProxy.java @@ -0,0 +1,147 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.content.Intent; +import android.content.pm.ShortcutInfo; +import android.os.Build; + +import androidx.annotation.RequiresApi; + +import java.lang.reflect.Method; +import java.util.ArrayList; + +import black.android.content.pm.IShortcutService; +import black.android.os.ServiceManager; +import black.com.android.internal.infra.AndroidFuture; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.ParceledListSliceCompat; + +public class IShortcutManagerProxy extends BinderInvocationStub { + public IShortcutManagerProxy() { + super(ServiceManager.getService.call(Context.SHORTCUT_SERVICE)); + } + + @Override + protected Object getWho() { + return IShortcutService.Stub.asInterface.call(ServiceManager.getService.call(Context.SHORTCUT_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.SHORTCUT_SERVICE); + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceAllAppPkg(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new PkgMethodProxy("getShortcuts")); //修复WhatsApp启动黑屏问题 + addMethodHook(new PkgMethodProxy("disableShortcuts")); + addMethodHook(new PkgMethodProxy("enableShortcuts")); + addMethodHook(new PkgMethodProxy("getRemainingCallCount")); + addMethodHook(new PkgMethodProxy("getRateLimitResetTime")); + addMethodHook(new PkgMethodProxy("getIconMaxDimensions")); + addMethodHook(new PkgMethodProxy("getMaxShortcutCountPerActivity")); + addMethodHook(new PkgMethodProxy("reportShortcutUsed")); + addMethodHook(new PkgMethodProxy("onApplicationActive")); + addMethodHook(new PkgMethodProxy("hasShortcutHostPermission")); + addMethodHook(new PkgMethodProxy("removeAllDynamicShortcuts")); + addMethodHook(new PkgMethodProxy("removeDynamicShortcuts")); + addMethodHook(new PkgMethodProxy("removeLongLivedShortcuts")); + addMethodHook(new WrapperShortcutInfo("pushDynamicShortcut", 1, null)); + addMethodHook(new WrapperShortcutInfo("requestPinShortcut", 1, false)); + addMethodHook(new WrapperShortcutInfo("addDynamicShortcuts", 1, false)); + addMethodHook(new WrapperShortcutInfo("setDynamicShortcuts", 1, false)); + addMethodHook(new PkgMethodProxy("getManifestShortcuts") { + + @Override + protected Object hook(Object who, Method method, Object[] args) { + return ParceledListSliceCompat.create(new ArrayList()); + } + }); + } + + static class WrapperShortcutInfo extends MethodHook{ + private int infoIndex; + private Object defValue; + private String MethodName; + + public WrapperShortcutInfo(String name,int infoIndex, Object defValue) { + this.infoIndex = infoIndex; + this.defValue = defValue; + this.MethodName = name; + } + + + @Override + protected String getMethodName() { + return MethodName; + } + + private Object wrapperResult(Method method,Object result) { + if (!method.toString().contains("AndroidFuture")) { + return result; + } + Object ret = AndroidFuture.ctor.newInstance(); + AndroidFuture.complete.call(ret, result); + return ret; + } + + @RequiresApi(api = Build.VERSION_CODES.N_MR1) + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return wrapperResult(method,defValue); + } + } + + + @ProxyMethod("requestPinShortcut") + public static class RequestPinShortcut extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return true; + } + } + + @ProxyMethod("setDynamicShortcuts") + public static class SetDynamicShortcuts extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return true; + } + } + + @ProxyMethod("createShortcutResultIntent") + public static class CreateShortcutResultIntent extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return new Intent(); + } + } + + @ProxyMethod("getMaxShortcutCountPerActivity") + public static class GetMaxShortcutCountPerActivity extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageManagerProxy.java new file mode 100644 index 0000000..441e99b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageManagerProxy.java @@ -0,0 +1,81 @@ +package com.vcore.fake.service; + +import android.os.IInterface; +import android.os.storage.StorageVolume; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.android.os.mount.IMountService; +import black.android.os.storage.IStorageManager; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.compat.BuildCompat; + +public class IStorageManagerProxy extends BinderInvocationStub { + public IStorageManagerProxy() { + super(ServiceManager.getService.call("mount")); + } + + @Override + protected Object getWho() { + IInterface mount; + if (BuildCompat.isOreo()) { + mount = IStorageManager.Stub.asInterface.call(ServiceManager.getService.call("mount")); + } else { + mount = IMountService.Stub.asInterface.call(ServiceManager.getService.call("mount")); + } + return mount; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("mount"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("getVolumeList") + public static class GetVolumeList extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args == null) { + StorageVolume[] volumeList = BlackBoxCore.getBStorageManager().getVolumeList(BActivityThread.getBUid(), null, 0, BActivityThread.getUserId()); + if (volumeList == null) { + return method.invoke(who, args); + } + return volumeList; + } + + try { + int uid = (int) args[0]; + String packageName = (String) args[1]; + int flags = (int) args[2]; + + StorageVolume[] volumeList = BlackBoxCore.getBStorageManager().getVolumeList(uid, packageName, flags, BActivityThread.getUserId()); + if (volumeList == null) { + return method.invoke(who, args); + } + return volumeList; + } catch (Throwable t) { + return method.invoke(who, args); + } + } + } + + @ProxyMethod("mkdirs") + public static class MkDirs extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageStatsManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageStatsManagerProxy.java new file mode 100644 index 0000000..d16568c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IStorageStatsManagerProxy.java @@ -0,0 +1,38 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.app.usage.IStorageStatsManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.utils.MethodParameterUtils; + +public class IStorageStatsManagerProxy extends BinderInvocationStub { + public IStorageStatsManagerProxy() { + super(ServiceManager.getService.call(Context.STORAGE_STATS_SERVICE)); + } + + @Override + protected Object getWho() { + return IStorageStatsManager.Stub.asInterface.call(ServiceManager.getService.call(Context.STORAGE_STATS_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.STORAGE_STATS_SERVICE); + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + MethodParameterUtils.replaceLastUid(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISubProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISubProxy.java new file mode 100644 index 0000000..e5f4a66 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISubProxy.java @@ -0,0 +1,47 @@ +package com.vcore.fake.service; + +import black.android.os.ServiceManager; +import black.com.android.internal.telephony.ISub; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.ValueMethodProxy; + +public class ISubProxy extends BinderInvocationStub { + public static final String TAG = "ISubProxy"; + + public ISubProxy() { + super(ServiceManager.getService.call("isub")); + } + + @Override + protected Object getWho() { + return ISub.Stub.asInterface.call(ServiceManager.getService.call("isub")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("isub"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + super.onBindMethod(); + addMethodHook(new ValueMethodProxy("getAllSubInfoList", null)); + addMethodHook(new ValueMethodProxy("getAllSubInfoCount", -1)); + addMethodHook(new ValueMethodProxy("getActiveSubscriptionInfo", null)); + addMethodHook(new ValueMethodProxy("getActiveSubscriptionInfoForIccId", null)); + addMethodHook(new ValueMethodProxy("getActiveSubscriptionInfoForSimSlotIndex", null)); + addMethodHook(new ValueMethodProxy("getActiveSubscriptionInfoList", null)); + addMethodHook(new ValueMethodProxy("getActiveSubInfoCount", -1)); + addMethodHook(new ValueMethodProxy("getActiveSubInfoCountMax", -1)); + addMethodHook(new ValueMethodProxy("getAvailableSubscriptionInfoList", null)); + addMethodHook(new ValueMethodProxy("getAccessibleSubscriptionInfoList", null)); + addMethodHook(new ValueMethodProxy("addSubInfoRecord", -1)); + addMethodHook(new ValueMethodProxy("addSubInfo", -1)); + addMethodHook(new ValueMethodProxy("removeSubInfo", -1)); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISuperResolutionManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISuperResolutionManagerProxy.java new file mode 100644 index 0000000..174e114 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISuperResolutionManagerProxy.java @@ -0,0 +1,49 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IBinder; + +import black.android.os.ServiceManager; +import black.oem.vivo.ISuperResolutionManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:26 + **/ +public class ISuperResolutionManagerProxy extends BinderInvocationStub { + + public ISuperResolutionManagerProxy() { + super(ServiceManager.getService.call("SuperResolutionManager")); + } + + @Override + protected Object getWho() { + return ISuperResolutionManager.Stub.asInterface.call(ServiceManager.getService.call("SuperResolutionManager")); + } + + + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("SuperResolutionManager"); + } + + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("registerPackageSettingStateChangeListener")); + addMethodHook(new PkgMethodProxy("unRegisterPackageSettingStateChangeListener")); + addMethodHook(new PkgMethodProxy("registerSuperResolutionStateChange")); + addMethodHook(new PkgMethodProxy("unRegisterSuperResolutionStateChange")); + addMethodHook(new PkgMethodProxy("getPackageSettingState")); + addMethodHook(new PkgMethodProxy("putPackageSettingState")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemDefenceManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemDefenceManagerProxy.java new file mode 100644 index 0000000..ab30e02 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemDefenceManagerProxy.java @@ -0,0 +1,45 @@ +package com.vcore.fake.service; + +import android.os.IBinder; + +import black.android.os.ServiceManager; +import black.oem.vivo.ISystemDefenceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:30 + **/ +public class ISystemDefenceManagerProxy extends BinderInvocationStub { + public ISystemDefenceManagerProxy() { + super(ServiceManager.getService.call("system_defence_service")); + } + + @Override + protected Object getWho() { + return ISystemDefenceManager.Stub.asInterface.call(ServiceManager.getService.call("system_defence_service")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("system_defence_service"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("checkTransitionTimoutErrorDefence")); + addMethodHook(new PkgMethodProxy("checkSkipKilledByRemoveTask")); + addMethodHook(new PkgMethodProxy("checkSmallIconNULLPackage")); + addMethodHook(new PkgMethodProxy("checkDelayUpdate")); + addMethodHook(new PkgMethodProxy("onSetActivityResumed")); + addMethodHook(new PkgMethodProxy("checkReinstallPacakge")); + addMethodHook(new PkgMethodProxy("reportFgCrashData")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemUpdateProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemUpdateProxy.java new file mode 100644 index 0000000..1de4e21 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ISystemUpdateProxy.java @@ -0,0 +1,26 @@ +package com.vcore.fake.service; + +import black.android.os.ServiceManager; +import black.android.view.IAutoFillManager; +import com.vcore.fake.hook.BinderInvocationStub; + +public class ISystemUpdateProxy extends BinderInvocationStub { + public ISystemUpdateProxy() { + super(ServiceManager.getService.call("system_update")); + } + + @Override + protected Object getWho() { + return IAutoFillManager.Stub.asInterface.call(ServiceManager.getService.call("system_update")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("system_update"); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyManagerProxy.java new file mode 100644 index 0000000..afdbe82 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyManagerProxy.java @@ -0,0 +1,177 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.util.Log; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.com.android.internal.telephony.ITelephony; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.entity.location.BCell; +import com.vcore.fake.frameworks.BLocationManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.Md5Utils; + +public class ITelephonyManagerProxy extends BinderInvocationStub { + public static final String TAG = "ITelephonyManagerProxy"; + + public ITelephonyManagerProxy() { + super(ServiceManager.getService.call(Context.TELEPHONY_SERVICE)); + } + + @Override + protected Object getWho() { + return ITelephony.Stub.asInterface.call(ServiceManager.getService.call(Context.TELEPHONY_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.TELEPHONY_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("getDeviceId") + public static class GetDeviceId extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("getImeiForSlot") + public static class GetImeiForSlot extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("getMeidForSlot") + public static class GetMeidForSlot extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("isUserDataEnabled") + public static class IsUserDataEnabled extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return true; + } + } + + @ProxyMethod("getLine1NumberForDisplay") + public static class GetLine1NumberForDisplay extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return null; + } + } + + @ProxyMethod("getSubscriberId") + public static class GetSubscriberId extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("getDeviceIdWithFeature") + public static class GetDeviceIdWithFeature extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return Md5Utils.md5(BlackBoxCore.getHostPkg()); + } + } + + @ProxyMethod("getCellLocation") + public static class GetCellLocation extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "getCellLocation"); + if (BLocationManager.isFakeLocationEnable()) { + BCell cell = BLocationManager.get().getCell(BActivityThread.getUserId(), BActivityThread.getAppPackageName()); + if (cell != null) { + // TODO: Transfer BCell to CdmaCellLocation/GsmCellLocation + return null; + } + } + return method.invoke(who, args); + } + } + + @ProxyMethod("getAllCellInfo") + public static class GetAllCellInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "GetAllCellInfo"); + if (BLocationManager.isFakeLocationEnable()) { + // TODO: Transfer BCell to CdmaCellLocation/GsmCellLocation + return BLocationManager.get().getAllCell(BActivityThread.getUserId(), BActivityThread.getAppPackageName()); + } + + try { + return method.invoke(who, args); + } catch (Throwable e) { + return null; + } + } + } + + @ProxyMethod("getNetworkOperator") + public static class GetNetworkOperator extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "getNetworkOperator"); + return method.invoke(who, args); + } + } + + @ProxyMethod("getNetworkTypeForSubscriber") + public static class GetNetworkTypeForSubscriber extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + try { + return method.invoke(who, args); + } catch (Throwable e) { + return 0; + } + } + } + + @ProxyMethod("getNeighboringCellInfo") + public static class GetNeighboringCellInfo extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "getNeighboringCellInfo"); + if (BLocationManager.isFakeLocationEnable()) { + // TODO: Transfer BCell to CdmaCellLocation/GsmCellLocation + return BLocationManager.get().getNeighboringCell(BActivityThread.getUserId(), BActivityThread.getAppPackageName()); + } + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyRegistryProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyRegistryProxy.java new file mode 100644 index 0000000..fecca85 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/ITelephonyRegistryProxy.java @@ -0,0 +1,51 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; + +import black.android.os.ServiceManager; +import black.com.android.internal.telephony.ITelephonyRegistry; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.utils.MethodParameterUtils; + +public class ITelephonyRegistryProxy extends BinderInvocationStub { + public ITelephonyRegistryProxy() { + super(ServiceManager.getService.call("telephony.registry")); + } + + @Override + protected Object getWho() { + return ITelephonyRegistry.Stub.asInterface.call(ServiceManager.getService.call("telephony.registry")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("telephony.registry"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("listenForSubscriber") + public static class ListenForSubscriber extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("listen") + public static class Listen extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IUserManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IUserManagerProxy.java new file mode 100644 index 0000000..ea6e276 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IUserManagerProxy.java @@ -0,0 +1,77 @@ +package com.vcore.fake.service; + +import android.content.Context; + +import java.lang.reflect.Method; +import java.util.ArrayList; + +import black.android.content.pm.UserInfo; +import black.android.os.IUserManager; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.service.base.PkgMethodProxy; +import com.vcore.fake.service.base.ValueMethodProxy; + +public class IUserManagerProxy extends BinderInvocationStub { + public IUserManagerProxy() { + super(ServiceManager.getService.call(Context.USER_SERVICE)); + } + + @Override + protected Object getWho() { + return IUserManager.Stub.asInterface.call(ServiceManager.getService.call(Context.USER_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.USER_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new ValueMethodProxy("getProfileParent",null)); + addMethodHook(new ValueMethodProxy("getUserIcon",null)); + addMethodHook(new ValueMethodProxy("getDefaultGuestRestrictions",null)); + addMethodHook(new ValueMethodProxy("setDefaultGuestRestrictions",null)); + addMethodHook(new ValueMethodProxy("removeRestrictions",null)); + addMethodHook(new ValueMethodProxy("createUser",null)); + addMethodHook(new ValueMethodProxy("createProfileForUser",null)); + } + + @ProxyMethod("getApplicationRestrictions") + public static class GetApplicationRestrictions extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + args[0] = BlackBoxCore.getHostPkg(); + return method.invoke(who, args); + } + } + + @ProxyMethod("getProfileParent") + public static class GetProfileParent extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return UserInfo._new.newInstance(BActivityThread.getUserId(), "BlackBox", UserInfo.FLAG_PRIMARY); + } + } + + @ProxyMethod("getUsers") + public static class GetUsers extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return new ArrayList<>(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVibratorServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVibratorServiceProxy.java new file mode 100644 index 0000000..d2a75c3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVibratorServiceProxy.java @@ -0,0 +1,55 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IBinder; + +import java.lang.reflect.Method; + +import black.android.os.IVibratorManagerService; +import black.android.os.ServiceManager; +import black.com.android.internal.os.IVibratorService; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.utils.MethodParameterUtils; +import com.vcore.utils.compat.BuildCompat; + +public class IVibratorServiceProxy extends BinderInvocationStub { + private static final String NAME; + + static { + if (BuildCompat.isS()) { + NAME = "vibrator_manager"; + } else { + NAME = Context.VIBRATOR_SERVICE; + } + } + + public IVibratorServiceProxy() { + super(ServiceManager.getService.call(NAME)); + } + + @Override + protected Object getWho() { + IBinder service = ServiceManager.getService.call(NAME); + if (BuildCompat.isS()) { + return IVibratorManagerService.Stub.asInterface.call(service); + } + return IVibratorService.Stub.asInterface.call(service); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(NAME); + } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstUid(args); + MethodParameterUtils.replaceFirstAppPkg(args); + return super.invoke(proxy, method, args); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVivoPermissionServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVivoPermissionServiceProxy.java new file mode 100644 index 0000000..80e72f8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVivoPermissionServiceProxy.java @@ -0,0 +1,46 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IBinder; + +import black.android.os.ServiceManager; +import black.oem.vivo.IVivoPermissonService; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.service.base.PkgMethodProxy; + +/** + * @author Findger + * @function + * @date :2023/10/8 20:36 + **/ +public class IVivoPermissionServiceProxy extends BinderInvocationStub { + public IVivoPermissionServiceProxy() { + super(ServiceManager.getService.call("vivo_permission_service")); + } + + @Override + protected Object getWho() { + return IVivoPermissonService.Stub.asInterface.call(ServiceManager.getService.call("vivo_permission_service")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("vivo_permission_service"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new PkgMethodProxy("checkPermission")); + addMethodHook(new PkgMethodProxy("getAppPermission")); + addMethodHook(new PkgMethodProxy("setAppPermission")); + addMethodHook(new PkgMethodProxy("setWhiteListApp")); + addMethodHook(new PkgMethodProxy("setBlackListApp")); + addMethodHook(new PkgMethodProxy("noteStartActivityProcess")); + addMethodHook(new PkgMethodProxy("isBuildInThirdPartApp")); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVpnManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVpnManagerProxy.java new file mode 100644 index 0000000..e7cf354 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IVpnManagerProxy.java @@ -0,0 +1,30 @@ +package com.vcore.fake.service; + +import black.android.net.IVpnManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.ScanClass; + +@ScanClass(VpnCommonProxy.class) +public class IVpnManagerProxy extends BinderInvocationStub { + public static final String TAG = "IVpnManagerProxy"; + + public IVpnManagerProxy() { + super(ServiceManager.getService.call("vpn_management")); + } + + @Override + protected Object getWho() { + return IVpnManager.Stub.asInterface.call(ServiceManager.getService.call("vpn_management")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("vpn_management"); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiManagerProxy.java new file mode 100644 index 0000000..6163a6c --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiManagerProxy.java @@ -0,0 +1,76 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.net.wifi.ScanResult; +import android.net.wifi.WifiInfo; +import android.util.Log; + +import java.lang.reflect.Method; +import java.util.ArrayList; + +import black.android.net.wifi.IWifiManager; +import black.android.net.wifi.WifiSsid; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IWifiManagerProxy extends BinderInvocationStub { + public static final String TAG = "IWifiManagerProxy"; + + public IWifiManagerProxy() { + super(ServiceManager.getService.call(Context.WIFI_SERVICE)); + } + + @Override + protected Object getWho() { + return IWifiManager.Stub.asInterface.call(ServiceManager.getService.call(Context.WIFI_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.WIFI_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @Override + protected void onBindMethod() { + addMethodHook(new GetConnectionInfo()); + addMethodHook(new GetScanResults()); + } + + @ProxyMethod("getConnectionInfo") + public static class GetConnectionInfo extends MethodHook { + /* + * It doesn't have public method to set BSSID and SSID fields in WifiInfo class, + * So the reflection framework invocation appeared. + * commented by BlackBoxing at 2022/03/08 + */ + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + WifiInfo wifiInfo = (WifiInfo) method.invoke(who, args); + black.android.net.wifi.WifiInfo.mBSSID.set(wifiInfo, "ac:62:5a:82:65:c4"); + black.android.net.wifi.WifiInfo.mMacAddress.set(wifiInfo, "ac:62:5a:82:65:c4"); + black.android.net.wifi.WifiInfo.mWifiSsid.set(wifiInfo, WifiSsid.createFromAsciiEncoded.call("BlackBox_Wifi")); + return wifiInfo; + } + } + + @ProxyMethod("getScanResults") + public static class GetScanResults extends MethodHook { + /* + * It doesn't have public method to set BSSID and SSID fields in WifiInfo class, + * So the reflection framework invocation appeared. + * commented by BlackBoxing at 2022/03/08 + */ + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Log.d(TAG, "GetScanResults"); + return new ArrayList(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiScannerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiScannerProxy.java new file mode 100644 index 0000000..0eea6dc --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWifiScannerProxy.java @@ -0,0 +1,26 @@ +package com.vcore.fake.service; + +import black.android.net.wifi.IWifiManager; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; + +public class IWifiScannerProxy extends BinderInvocationStub { + public IWifiScannerProxy() { + super(ServiceManager.getService.call("wifiscanner")); + } + + @Override + protected Object getWho() { + return IWifiManager.Stub.asInterface.call(ServiceManager.getService.call("wifiscanner")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("wifiscanner"); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowManagerProxy.java new file mode 100644 index 0000000..b904ef9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowManagerProxy.java @@ -0,0 +1,51 @@ +package com.vcore.fake.service; + +import android.content.Context; +import android.os.IInterface; + +import java.lang.reflect.Method; +import java.util.Objects; + +import black.android.os.ServiceManager; +import black.android.view.IWindowManager; +import black.android.view.WindowManagerGlobal; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IWindowManagerProxy extends BinderInvocationStub { + public static final String TAG = "WindowManagerStub"; + + public IWindowManagerProxy() { + super(ServiceManager.getService.call(Context.WINDOW_SERVICE)); + } + + @Override + protected Object getWho() { + return IWindowManager.Stub.asInterface.call(ServiceManager.getService.call(Context.WINDOW_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.WINDOW_SERVICE); + WindowManagerGlobal.sWindowManagerService.set(null); + } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("openSession") + public static class OpenSession extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + IInterface session = (IInterface) method.invoke(who, args); + IWindowSessionProxy IWindowSessionProxy = new IWindowSessionProxy(Objects.requireNonNull(session)); + IWindowSessionProxy.injectHook(); + return IWindowSessionProxy.getProxyInvocation(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowSessionProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowSessionProxy.java new file mode 100644 index 0000000..2c9e6f4 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/IWindowSessionProxy.java @@ -0,0 +1,55 @@ +package com.vcore.fake.service; + +import android.os.IInterface; +import android.view.WindowManager; + +import java.lang.reflect.Method; + +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class IWindowSessionProxy extends BinderInvocationStub { + public static final String TAG = "WindowSessionStub"; + private final IInterface mSession; + + public IWindowSessionProxy(IInterface session) { + super(session.asBinder()); + this.mSession = session; + } + + @Override + protected Object getWho() { + return mSession; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { } + + @Override + public boolean isBadEnv() { + return false; + } + + + @ProxyMethod("addToDisplay") + public static class AddToDisplay extends MethodHook { + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + for (Object arg : args) { + if (arg == null) { + continue; + } + + if (arg instanceof WindowManager.LayoutParams) { + ((WindowManager.LayoutParams) arg).packageName = BlackBoxCore.getHostPkg(); + } + } + return method.invoke(who, args); + } + } + + @ProxyMethod("addToDisplayAsUser") + public static class AddToDisplayAsUser extends AddToDisplay { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/VpnCommonProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/VpnCommonProxy.java new file mode 100644 index 0000000..91857c0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/VpnCommonProxy.java @@ -0,0 +1,57 @@ +package com.vcore.fake.service; + +import java.lang.reflect.Method; +import java.util.List; + +import black.com.android.internal.net.VpnConfig; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.proxy.ProxyVpnService; +import com.vcore.utils.MethodParameterUtils; + +public class VpnCommonProxy { + @ProxyMethod("setVpnPackageAuthorization") + public static class SetVpnPackageAuthorization extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("prepareVpn") + public static class PrepareVpn extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } + } + + @ProxyMethod("establishVpn") + public static class EstablishVpn extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + VpnConfig.user.set(args[0], ProxyVpnService.class.getName()); + + handlePackage(VpnConfig.allowedApplications.get()); + handlePackage(VpnConfig.disallowedApplications.get()); + return method.invoke(who, args); + } + + private void handlePackage(List applications) { + if (applications == null) { + return; + } + + if (applications.contains(BActivityThread.getAppPackageName())) { + applications.add(BlackBoxCore.getHostPkg()); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/PkgMethodProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/PkgMethodProxy.java new file mode 100644 index 0000000..ba53f68 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/PkgMethodProxy.java @@ -0,0 +1,25 @@ +package com.vcore.fake.service.base; + +import java.lang.reflect.Method; + +import com.vcore.fake.hook.MethodHook; +import com.vcore.utils.MethodParameterUtils; + +public class PkgMethodProxy extends MethodHook { + final String mName; + + public PkgMethodProxy(String name) { + this.mName = name; + } + + @Override + protected String getMethodName() { + return mName; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + MethodParameterUtils.replaceFirstAppPkg(args); + return method.invoke(who, args); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/UidMethodProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/UidMethodProxy.java new file mode 100644 index 0000000..cc74a8d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/UidMethodProxy.java @@ -0,0 +1,31 @@ +package com.vcore.fake.service.base; + +import java.lang.reflect.Method; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.MethodHook; + +public class UidMethodProxy extends MethodHook { + private final int index; + private final String name; + + public UidMethodProxy(String name, int index) { + this.index = index; + this.name = name; + } + + @Override + protected String getMethodName() { + return name; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int uid = (int) args[index]; + if (uid == BActivityThread.getBUid()) { + args[index] = BlackBoxCore.getHostUid(); + } + return method.invoke(who, args); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/ValueMethodProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/ValueMethodProxy.java new file mode 100644 index 0000000..293ece2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/base/ValueMethodProxy.java @@ -0,0 +1,25 @@ +package com.vcore.fake.service.base; + +import java.lang.reflect.Method; + +import com.vcore.fake.hook.MethodHook; + +public class ValueMethodProxy extends MethodHook { + final Object mValue; + final String mName; + + public ValueMethodProxy(String name, Object value) { + this.mValue = value; + this.mName = name; + } + + @Override + protected String getMethodName() { + return mName; + } + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return mValue; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/ContentServiceProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/ContentServiceProxy.java new file mode 100644 index 0000000..9900c3f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/ContentServiceProxy.java @@ -0,0 +1,48 @@ +package com.vcore.fake.service.context; + +import java.lang.reflect.Method; + +import black.android.content.IContentService; +import black.android.os.ServiceManager; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class ContentServiceProxy extends BinderInvocationStub { + public ContentServiceProxy() { + super(ServiceManager.getService.call("content")); + } + + @Override + protected Object getWho() { + return IContentService.Stub.asInterface.call(ServiceManager.getService.call("content")); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService("content"); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("registerContentObserver") + public static class RegisterContentObserver extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } + + @ProxyMethod("notifyChange") + public static class NotifyChange extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + return 0; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/LocationListenerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/LocationListenerProxy.java new file mode 100644 index 0000000..b1f09d7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/LocationListenerProxy.java @@ -0,0 +1,53 @@ +package com.vcore.fake.service.context; + +import android.location.Location; + +import java.lang.reflect.Method; +import java.util.List; + +import com.vcore.app.BActivityThread; +import com.vcore.fake.frameworks.BLocationManager; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class LocationListenerProxy extends ClassInvocationStub { + public static final String TAG = "LocationListenerProxy"; + private Object mBase; + + public Object wrapper(final Object locationListenerProxy) { + mBase = locationListenerProxy; + injectHook(); + return getProxyInvocation(); + } + + @Override + protected Object getWho() { + return mBase; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { } + + @ProxyMethod("onLocationChanged") + public static class OnLocationChanged extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + if (args[0] instanceof List) { + List locations = (List) args[0]; + locations.clear(); + locations.add(BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()).convert2SystemLocation()); + args[0] = locations; + } else if (args[0] instanceof Location) { + args[0] = BLocationManager.get().getLocation(BActivityThread.getUserId(), BActivityThread.getAppPackageName()).convert2SystemLocation(); + } + return method.invoke(who, args); + } + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/RestrictionsManagerProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/RestrictionsManagerProxy.java new file mode 100644 index 0000000..2ebf5ba --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/RestrictionsManagerProxy.java @@ -0,0 +1,42 @@ +package com.vcore.fake.service.context; + +import android.content.Context; + +import java.lang.reflect.Method; + +import black.android.content.IRestrictionsManager; +import black.android.os.ServiceManager; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.BinderInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; + +public class RestrictionsManagerProxy extends BinderInvocationStub { + public RestrictionsManagerProxy() { + super(ServiceManager.getService.call(Context.RESTRICTIONS_SERVICE)); + } + + @Override + protected Object getWho() { + return IRestrictionsManager.Stub.asInterface.call(ServiceManager.getService.call(Context.RESTRICTIONS_SERVICE)); + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + replaceSystemService(Context.RESTRICTIONS_SERVICE); + } + + @Override + public boolean isBadEnv() { + return false; + } + + @ProxyMethod("getApplicationRestrictions") + public static class GetApplicationRestrictions extends MethodHook { + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + args[0] = BlackBoxCore.getHostPkg(); + return method.invoke(who, args); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/BContentProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/BContentProvider.java new file mode 100644 index 0000000..280e515 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/BContentProvider.java @@ -0,0 +1,7 @@ +package com.vcore.fake.service.context.providers; + +import android.os.IInterface; + +public interface BContentProvider { + IInterface wrapper(final IInterface contentProviderProxy, final String appPkg); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/ContentProviderStub.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/ContentProviderStub.java new file mode 100644 index 0000000..d39cecf --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/ContentProviderStub.java @@ -0,0 +1,69 @@ +package com.vcore.fake.service.context.providers; + +import android.os.Build; +import android.os.Bundle; +import android.os.IInterface; + +import java.lang.reflect.Method; + +import black.android.content.AttributionSource; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.utils.compat.ContextCompat; + +public class ContentProviderStub extends ClassInvocationStub implements BContentProvider { + public static final String TAG = "ContentProviderStub"; + private IInterface mBase; + private String mAppPkg; + + public IInterface wrapper(final IInterface contentProviderProxy, final String appPkg) { + mBase = contentProviderProxy; + mAppPkg = appPkg; + + injectHook(); + return (IInterface) getProxyInvocation(); + } + + private Bundle wrapBundle(String name, String value) { + Bundle bundle = new Bundle(); + if (Build.VERSION.SDK_INT >= 24) { + bundle.putString("name", name); + bundle.putString("value", value); + } else { + bundle.putString(name, value); + } + return bundle; + } + + @Override + protected Object getWho() { + return mBase; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + if ("asBinder".equals(method.getName())) { + return method.invoke(mBase, args); + } + if (args != null && args.length > 0) { + Object arg = args[0]; + if (arg instanceof String) { + args[0] = mAppPkg; + if ("android_id".equals(arg)) { + return wrapBundle("android_id", ""); + } + } else if (arg.getClass().getName().equals(AttributionSource.REF.getClazz().getName())) { + ContextCompat.fixAttributionSourceState(arg, BActivityThread.getBUid()); + } + } + return method.invoke(mBase, args); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/SystemProviderStub.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/SystemProviderStub.java new file mode 100644 index 0000000..ffb69cb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/context/providers/SystemProviderStub.java @@ -0,0 +1,56 @@ +package com.vcore.fake.service.context.providers; + +import android.os.IInterface; + +import java.lang.reflect.Method; + +import black.android.content.AttributionSource; +import com.vcore.BlackBoxCore; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.utils.compat.ContextCompat; + +public class SystemProviderStub extends ClassInvocationStub implements BContentProvider { + public static final String TAG = "SystemProviderStub"; + private IInterface mBase; + private String mAppPkg; + + @Override + public IInterface wrapper(IInterface contentProviderProxy, String appPkg) { + mBase = contentProviderProxy; + mAppPkg = appPkg; + + injectHook(); + return (IInterface) getProxyInvocation(); + } + + + @Override + protected Object getWho() { + return mBase; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { } + + @Override + public Object invoke(Object proxy, Method method, Object[] args) throws Throwable { + if ("asBinder".equals(method.getName())) { + return method.invoke(mBase, args); + } + + if (args != null && args.length > 0) { + Object arg = args[0]; + if (arg instanceof String) { + args[0] = mAppPkg; + } else if (arg.getClass().getName().equals(AttributionSource.REF.getClazz().getName())) { + ContextCompat.fixAttributionSourceState(arg, BlackBoxCore.getHostUid()); + } + } + return method.invoke(mBase, args); + } + + @Override + public boolean isBadEnv() { + return false; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/libcore/OsProxy.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/libcore/OsProxy.java new file mode 100644 index 0000000..cfa07fb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/fake/service/libcore/OsProxy.java @@ -0,0 +1,78 @@ +package com.vcore.fake.service.libcore; + +import android.os.Process; + +import java.lang.reflect.Method; +import java.util.Objects; + +import black.Reflector; +import black.libcore.io.Libcore; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.ClassInvocationStub; +import com.vcore.fake.hook.MethodHook; +import com.vcore.fake.hook.ProxyMethod; +import com.vcore.fake.hook.ProxyMethods; + +public class OsProxy extends ClassInvocationStub { + public static final String TAG = "OsProxy"; + private final Object mBase; + + public OsProxy() { + this.mBase = Libcore.os.get(); + } + + @Override + protected Object getWho() { + return mBase; + } + + @Override + protected void inject(Object baseInvocation, Object proxyInvocation) { + Libcore.os.set(proxyInvocation); + } + + @Override + public boolean isBadEnv() { + return Libcore.os.get() != getProxyInvocation(); + } + + @ProxyMethod("getuid") + public static class GetUID extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + int callUid = (int) method.invoke(who, args); + return getFakeUid(callUid); + } + } + + @ProxyMethods({"lstat", "stat"}) + public static class Stat extends MethodHook { + + @Override + protected Object hook(Object who, Method method, Object[] args) throws Throwable { + Object invoke; + try { + invoke = method.invoke(who, args); + } catch (Throwable e) { + throw Objects.requireNonNull(e.getCause()); + } + + Reflector.on("android.system.StructStat") + .field("st_uid").set(invoke, getFakeUid(-1)); + return invoke; + } + } + + private static int getFakeUid(int callUid) { + if (callUid > 0 && callUid <= Process.FIRST_APPLICATION_UID) { + return callUid; + } + + if (BActivityThread.isThreadInit() && BActivityThread.currentActivityThread().isInit()) { + return BActivityThread.getBAppId(); + } + return BlackBoxCore.getHostUid(); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/JniHook.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/JniHook.java new file mode 100644 index 0000000..2e2ee1a --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/JniHook.java @@ -0,0 +1,11 @@ +package com.vcore.jnihook; + +public final class JniHook { + public static final int NATIVE_OFFSET = 0; + + public static final int NATIVE_OFFSET_2 = 0; + + public static native void nativeOffset(); + + public static native void nativeOffset2(); +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/MethodUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/MethodUtils.java new file mode 100644 index 0000000..d94693f --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/jnihook/MethodUtils.java @@ -0,0 +1,96 @@ +package com.vcore.jnihook; + +import androidx.annotation.Keep; + +import java.lang.reflect.Method; +import java.util.Objects; + +@Keep +public class MethodUtils { + // native call + public static String getDeclaringClass(final Method method) { + return method.getDeclaringClass().getName().replace(".", "/"); + } + + // native call + public static String getMethodName(final Method method) { + return method.getName(); + } + + // native call + public static String getDesc(final Method method) { + final StringBuilder buf = new StringBuilder(); + buf.append("("); + + final Class[] types = method.getParameterTypes(); + for (Class type : types) { + buf.append(getDesc(type)); + } + + buf.append(")"); + buf.append(getDesc(method.getReturnType())); + return buf.toString(); + } + + private static String getDesc(final Class returnType) { + if (returnType.isPrimitive()) { + return getPrimitiveLetter(returnType); + } + + if (returnType.isArray()) { + return "[" + getDesc(Objects.requireNonNull(returnType.getComponentType())); + } + return "L" + getType(returnType) + ";"; + } + + private static String getType(final Class parameterType) { + if (parameterType.isArray()) { + return "[" + getDesc(Objects.requireNonNull(parameterType.getComponentType())); + } + + if (!parameterType.isPrimitive()) { + final String clsName = parameterType.getName(); + return clsName.replaceAll("\\.", "/"); + } + return getPrimitiveLetter(parameterType); + } + + private static String getPrimitiveLetter(final Class type) { + if (Integer.TYPE.equals(type)) { + return "I"; + } + + if (Void.TYPE.equals(type)) { + return "V"; + } + + if (Boolean.TYPE.equals(type)) { + return "Z"; + } + + if (Character.TYPE.equals(type)) { + return "C"; + } + + if (Byte.TYPE.equals(type)) { + return "B"; + } + + if (Short.TYPE.equals(type)) { + return "S"; + } + + if (Float.TYPE.equals(type)) { + return "F"; + } + + if (Long.TYPE.equals(type)) { + return "J"; + } + + if (Double.TYPE.equals(type)) { + return "D"; + } + throw new IllegalStateException("Type: " + type.getCanonicalName() + " is not a primitive type"); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyActivity.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyActivity.java new file mode 100644 index 0000000..332858d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyActivity.java @@ -0,0 +1,130 @@ +package com.vcore.proxy; + +import android.app.Activity; +import android.os.Bundle; +import android.util.Log; + +import androidx.annotation.Nullable; + +import com.vcore.app.BActivityThread; +import com.vcore.fake.hook.HookManager; +import com.vcore.fake.service.HCallbackProxy; +import com.vcore.proxy.record.ProxyActivityRecord; + +public class ProxyActivity extends Activity { + public static final String TAG = "ProxyActivity"; + + @Override + protected void onCreate(@Nullable Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + Log.d(TAG, "onCreate"); + finish(); + + HookManager.get().checkEnv(HCallbackProxy.class); + ProxyActivityRecord record = ProxyActivityRecord.create(getIntent()); + if (record.mTarget != null) { + record.mTarget.setExtrasClassLoader(BActivityThread.getApplication().getClassLoader()); + startActivity(record.mTarget); + } + } + + public static class P0 extends ProxyActivity { } + + public static class P1 extends ProxyActivity { } + + public static class P2 extends ProxyActivity { } + + public static class P3 extends ProxyActivity { } + + public static class P4 extends ProxyActivity { } + + public static class P5 extends ProxyActivity { } + + public static class P6 extends ProxyActivity { } + + public static class P7 extends ProxyActivity { } + + public static class P8 extends ProxyActivity { } + + public static class P9 extends ProxyActivity { } + + public static class P10 extends ProxyActivity { } + + public static class P11 extends ProxyActivity { } + + public static class P12 extends ProxyActivity { } + + public static class P13 extends ProxyActivity { } + + public static class P14 extends ProxyActivity { } + + public static class P15 extends ProxyActivity { } + + public static class P16 extends ProxyActivity { } + + public static class P17 extends ProxyActivity { } + + public static class P18 extends ProxyActivity { } + + public static class P19 extends ProxyActivity { } + + public static class P20 extends ProxyActivity { } + + public static class P21 extends ProxyActivity { } + + public static class P22 extends ProxyActivity { } + + public static class P23 extends ProxyActivity { } + + public static class P24 extends ProxyActivity { } + + public static class P25 extends ProxyActivity { } + + public static class P26 extends ProxyActivity { } + + public static class P27 extends ProxyActivity { } + + public static class P28 extends ProxyActivity { } + + public static class P29 extends ProxyActivity { } + + public static class P30 extends ProxyActivity { } + + public static class P31 extends ProxyActivity { } + + public static class P32 extends ProxyActivity { } + + public static class P33 extends ProxyActivity { } + + public static class P34 extends ProxyActivity { } + + public static class P35 extends ProxyActivity { } + + public static class P36 extends ProxyActivity { } + + public static class P37 extends ProxyActivity { } + + public static class P38 extends ProxyActivity { } + + public static class P39 extends ProxyActivity { } + + public static class P40 extends ProxyActivity { } + + public static class P41 extends ProxyActivity { } + + public static class P42 extends ProxyActivity { } + + public static class P43 extends ProxyActivity { } + + public static class P44 extends ProxyActivity { } + + public static class P45 extends ProxyActivity { } + + public static class P46 extends ProxyActivity { } + + public static class P47 extends ProxyActivity { } + + public static class P48 extends ProxyActivity { } + + public static class P49 extends ProxyActivity { } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/proxy/ProxyBroadcastReceiver.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyBroadcastReceiver.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/proxy/ProxyBroadcastReceiver.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyBroadcastReceiver.java index aa681b7..80fef9f 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/proxy/ProxyBroadcastReceiver.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyBroadcastReceiver.java @@ -1,17 +1,14 @@ -package top.niunaijun.blackbox.proxy; +package com.vcore.proxy; import android.content.BroadcastReceiver; import android.content.Context; import android.content.Intent; import android.os.RemoteException; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.entity.am.PendingResultData; -import top.niunaijun.blackbox.proxy.record.ProxyBroadcastRecord; +import com.vcore.BlackBoxCore; +import com.vcore.entity.am.PendingResultData; +import com.vcore.proxy.record.ProxyBroadcastRecord; -/** - * Created by BlackBox on 2022/2/25. - */ public class ProxyBroadcastReceiver extends BroadcastReceiver { public static final String TAG = "ProxyBroadcastReceiver"; @@ -22,6 +19,7 @@ public void onReceive(Context context, Intent intent) { if (record.mIntent == null) { return; } + PendingResult pendingResult = goAsync(); try { BlackBoxCore.getBActivityManager().scheduleBroadcastReceiver(record.mIntent, new PendingResultData(pendingResult), record.mUserId); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyContentProvider.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyContentProvider.java new file mode 100644 index 0000000..556294b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyContentProvider.java @@ -0,0 +1,173 @@ +package com.vcore.proxy; + +import android.content.ContentProvider; +import android.content.ContentValues; +import android.database.Cursor; +import android.net.Uri; +import android.os.Bundle; +import android.util.Log; + +import androidx.annotation.NonNull; +import androidx.annotation.Nullable; + +import com.vcore.app.BActivityThread; +import com.vcore.entity.AppConfig; +import com.vcore.utils.compat.BundleCompat; + +public class ProxyContentProvider extends ContentProvider { + public static final String TAG = "ProxyContentProvider"; + + @Override + public boolean onCreate() { + return false; + } + + @Nullable + @Override + public Bundle call(@NonNull String method, @Nullable String arg, @Nullable Bundle extras) { + if (method.equals("_Black_|_init_process_")) { + assert extras != null; + extras.setClassLoader(AppConfig.class.getClassLoader()); + AppConfig appConfig = extras.getParcelable(AppConfig.KEY); + BActivityThread.currentActivityThread().initProcess(appConfig); + + Bundle bundle = new Bundle(); + BundleCompat.putBinder(bundle, "_Black_|_client_", BActivityThread.currentActivityThread()); + return bundle; + } + return super.call(method, arg, extras); + } + + @Nullable + @Override + public Cursor query(@NonNull Uri uri, @Nullable String[] projection, @Nullable String selection, @Nullable String[] selectionArgs, @Nullable String sortOrder) { + Log.d(TAG, uri.toString()); + return null; + } + + @Nullable + @Override + public String getType(@NonNull Uri uri) { + Log.d(TAG, uri.toString()); + return null; + } + + @Nullable + @Override + public Uri insert(@NonNull Uri uri, @Nullable ContentValues values) { + Log.d(TAG, uri.toString()); + return null; + } + + @Override + public int delete(@NonNull Uri uri, @Nullable String selection, @Nullable String[] selectionArgs) { + Log.d(TAG, uri.toString()); + return 0; + } + + @Override + public int update(@NonNull Uri uri, @Nullable ContentValues values, @Nullable String selection, @Nullable String[] selectionArgs) { + Log.d(TAG, uri.toString()); + return 0; + } + + public static class P0 extends ProxyContentProvider { } + + public static class P1 extends ProxyContentProvider { } + + public static class P2 extends ProxyContentProvider { } + + public static class P3 extends ProxyContentProvider { } + + public static class P4 extends ProxyContentProvider { } + + public static class P5 extends ProxyContentProvider { } + + public static class P6 extends ProxyContentProvider { } + + public static class P7 extends ProxyContentProvider { } + + public static class P8 extends ProxyContentProvider { } + + public static class P9 extends ProxyContentProvider { } + + public static class P10 extends ProxyContentProvider { } + + public static class P11 extends ProxyContentProvider { } + + public static class P12 extends ProxyContentProvider { } + + public static class P13 extends ProxyContentProvider { } + + public static class P14 extends ProxyContentProvider { } + + public static class P15 extends ProxyContentProvider { } + + public static class P16 extends ProxyContentProvider { } + + public static class P17 extends ProxyContentProvider { } + + public static class P18 extends ProxyContentProvider { } + + public static class P19 extends ProxyContentProvider { } + + public static class P20 extends ProxyContentProvider { } + + public static class P21 extends ProxyContentProvider { } + + public static class P22 extends ProxyContentProvider { } + + public static class P23 extends ProxyContentProvider { } + + public static class P24 extends ProxyContentProvider { } + + public static class P25 extends ProxyContentProvider { } + + public static class P26 extends ProxyContentProvider { } + + public static class P27 extends ProxyContentProvider { } + + public static class P28 extends ProxyContentProvider { } + + public static class P29 extends ProxyContentProvider { } + + public static class P30 extends ProxyContentProvider { } + + public static class P31 extends ProxyContentProvider { } + + public static class P32 extends ProxyContentProvider { } + + public static class P33 extends ProxyContentProvider { } + + public static class P34 extends ProxyContentProvider { } + + public static class P35 extends ProxyContentProvider { } + + public static class P36 extends ProxyContentProvider { } + + public static class P37 extends ProxyContentProvider { } + + public static class P38 extends ProxyContentProvider { } + + public static class P39 extends ProxyContentProvider { } + + public static class P40 extends ProxyContentProvider { } + + public static class P41 extends ProxyContentProvider { } + + public static class P42 extends ProxyContentProvider { } + + public static class P43 extends ProxyContentProvider { } + + public static class P44 extends ProxyContentProvider { } + + public static class P45 extends ProxyContentProvider { } + + public static class P46 extends ProxyContentProvider { } + + public static class P47 extends ProxyContentProvider { } + + public static class P48 extends ProxyContentProvider { } + + public static class P49 extends ProxyContentProvider { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyJobService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyJobService.java new file mode 100644 index 0000000..50043ca --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyJobService.java @@ -0,0 +1,151 @@ +package com.vcore.proxy; + +import android.app.job.JobParameters; +import android.app.job.JobService; +import android.content.Intent; +import android.content.res.Configuration; + +import com.vcore.app.dispatcher.AppJobServiceDispatcher; + +public class ProxyJobService extends JobService { + public static final String TAG = "StubJobService"; + + @Override + public boolean onStartJob(JobParameters params) { + return AppJobServiceDispatcher.get().onStartJob(params); + } + + @Override + public boolean onStopJob(JobParameters params) { + return AppJobServiceDispatcher.get().onStopJob(params); + } + + @Override + public int onStartCommand(Intent intent, int flags, int startId) { + return START_NOT_STICKY; + } + + @Override + public void onDestroy() { + super.onDestroy(); + AppJobServiceDispatcher.get().onDestroy(); + } + + @Override + public void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + AppJobServiceDispatcher.get().onConfigurationChanged(newConfig); + } + + @Override + public void onLowMemory() { + super.onLowMemory(); + AppJobServiceDispatcher.get().onLowMemory(); + } + + @Override + public void onTrimMemory(int level) { + super.onTrimMemory(level); + AppJobServiceDispatcher.get().onTrimMemory(level); + } + + public static class P0 extends ProxyJobService { } + + public static class P1 extends ProxyJobService { } + + public static class P2 extends ProxyJobService { } + + public static class P3 extends ProxyJobService { } + + public static class P4 extends ProxyJobService { } + + public static class P5 extends ProxyJobService { } + + public static class P6 extends ProxyJobService { } + + public static class P7 extends ProxyJobService { } + + public static class P8 extends ProxyJobService { } + + public static class P9 extends ProxyJobService { } + + public static class P10 extends ProxyJobService { } + + public static class P11 extends ProxyJobService { } + + public static class P12 extends ProxyJobService { } + + public static class P13 extends ProxyJobService { } + + public static class P14 extends ProxyJobService { } + + public static class P15 extends ProxyJobService { } + + public static class P16 extends ProxyJobService { } + + public static class P17 extends ProxyJobService { } + + public static class P18 extends ProxyJobService { } + + public static class P19 extends ProxyJobService { } + + public static class P20 extends ProxyJobService { } + + public static class P21 extends ProxyJobService { } + + public static class P22 extends ProxyJobService { } + + public static class P23 extends ProxyJobService { } + + public static class P24 extends ProxyJobService { } + + public static class P25 extends ProxyJobService { } + + public static class P26 extends ProxyJobService { } + + public static class P27 extends ProxyJobService { } + + public static class P28 extends ProxyJobService { } + + public static class P29 extends ProxyJobService { } + + public static class P30 extends ProxyJobService { } + + public static class P31 extends ProxyJobService { } + + public static class P32 extends ProxyJobService { } + + public static class P33 extends ProxyJobService { } + + public static class P34 extends ProxyJobService { } + + public static class P35 extends ProxyJobService { } + + public static class P36 extends ProxyJobService { } + + public static class P37 extends ProxyJobService { } + + public static class P38 extends ProxyJobService { } + + public static class P39 extends ProxyJobService { } + + public static class P40 extends ProxyJobService { } + + public static class P41 extends ProxyJobService { } + + public static class P42 extends ProxyJobService { } + + public static class P43 extends ProxyJobService { } + + public static class P44 extends ProxyJobService { } + + public static class P45 extends ProxyJobService { } + + public static class P46 extends ProxyJobService { } + + public static class P47 extends ProxyJobService { } + + public static class P48 extends ProxyJobService { } + + public static class P49 extends ProxyJobService { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyManifest.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyManifest.java new file mode 100644 index 0000000..3381da3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyManifest.java @@ -0,0 +1,49 @@ +package com.vcore.proxy; + +import java.util.Locale; + +import com.vcore.BlackBoxCore; + +public class ProxyManifest { + public static final int FREE_COUNT = 50; + + public static boolean isProxy(String msg) { + return getBindProvider().equals(msg) || msg.contains("proxy_content_provider_"); + } + + public static String getBindProvider() { + return BlackBoxCore.getHostPkg() + ".blackbox.SystemCallProvider"; + } + + public static String getProxyAuthorities(int index) { + return String.format(Locale.CHINA, "%s.proxy_content_provider_%d", BlackBoxCore.getHostPkg(), index); + } + + public static String getProxyPendingActivity(int index) { + return String.format(Locale.CHINA, "com.vcore.proxy.ProxyPendingActivity$P%d", index); + } + + public static String getProxyActivity(int index) { + return String.format(Locale.CHINA, "com.vcore.proxy.ProxyActivity$P%d", index); + } + + public static String TransparentProxyActivity(int index) { + return String.format(Locale.CHINA, "com.vcore.proxy.TransparentProxyActivity$P%d", index); + } + + public static String getProxyService(int index) { + return String.format(Locale.CHINA, "com.vcore.proxy.ProxyService$P%d", index); + } + + public static String getProxyJobService(int index) { + return String.format(Locale.CHINA, "com.vcore.proxy.ProxyJobService$P%d", index); + } + + public static String getProxyFileProvider() { + return BlackBoxCore.getHostPkg() + ".blackbox.FileProvider"; + } + + public static String getProcessName(int bPid) { + return BlackBoxCore.getHostPkg() + ":p" + bPid; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyPendingActivity.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyPendingActivity.java new file mode 100644 index 0000000..56baabb --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyPendingActivity.java @@ -0,0 +1,131 @@ +package com.vcore.proxy; + +import android.app.Activity; +import android.content.Intent; +import android.os.Bundle; + +import androidx.annotation.Nullable; + +import com.vcore.app.BActivityThread; +import com.vcore.proxy.record.ProxyPendingRecord; +import com.vcore.utils.Slog; + +public class ProxyPendingActivity extends Activity { + public static final String TAG = "ProxyPendingActivity"; + + @Override + protected void onCreate(@Nullable Bundle savedInstanceState) { + super.onCreate(savedInstanceState); + finish(); + + ProxyPendingRecord pendingActivityRecord = ProxyPendingRecord.create(getIntent()); + Slog.d(TAG, "ProxyPendingActivity: " + pendingActivityRecord); + if (pendingActivityRecord.mTarget == null) { + return; + } + + pendingActivityRecord.mTarget.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); + pendingActivityRecord.mTarget.setExtrasClassLoader(BActivityThread.getApplication().getClassLoader()); + startActivity(pendingActivityRecord.mTarget); + } + + public static class P0 extends ProxyPendingActivity { } + + public static class P1 extends ProxyPendingActivity { } + + public static class P2 extends ProxyPendingActivity { } + + public static class P3 extends ProxyPendingActivity { } + + public static class P4 extends ProxyPendingActivity { } + + public static class P5 extends ProxyPendingActivity { } + + public static class P6 extends ProxyPendingActivity { } + + public static class P7 extends ProxyPendingActivity { } + + public static class P8 extends ProxyPendingActivity { } + + public static class P9 extends ProxyPendingActivity { } + + public static class P10 extends ProxyPendingActivity { } + + public static class P11 extends ProxyPendingActivity { } + + public static class P12 extends ProxyPendingActivity { } + + public static class P13 extends ProxyPendingActivity { } + + public static class P14 extends ProxyPendingActivity { } + + public static class P15 extends ProxyPendingActivity { } + + public static class P16 extends ProxyPendingActivity { } + + public static class P17 extends ProxyPendingActivity { } + + public static class P18 extends ProxyPendingActivity { } + + public static class P19 extends ProxyPendingActivity { } + + public static class P20 extends ProxyPendingActivity { } + + public static class P21 extends ProxyPendingActivity { } + + public static class P22 extends ProxyPendingActivity { } + + public static class P23 extends ProxyPendingActivity { } + + public static class P24 extends ProxyPendingActivity { } + + public static class P25 extends ProxyPendingActivity { } + + public static class P26 extends ProxyPendingActivity { } + + public static class P27 extends ProxyPendingActivity { } + + public static class P28 extends ProxyPendingActivity { } + + public static class P29 extends ProxyPendingActivity { } + + public static class P30 extends ProxyPendingActivity { } + + public static class P31 extends ProxyPendingActivity { } + + public static class P32 extends ProxyPendingActivity { } + + public static class P33 extends ProxyPendingActivity { } + + public static class P34 extends ProxyPendingActivity { } + + public static class P35 extends ProxyPendingActivity { } + + public static class P36 extends ProxyPendingActivity { } + + public static class P37 extends ProxyPendingActivity { } + + public static class P38 extends ProxyPendingActivity { } + + public static class P39 extends ProxyPendingActivity { } + + public static class P40 extends ProxyPendingActivity { } + + public static class P41 extends ProxyPendingActivity { } + + public static class P42 extends ProxyPendingActivity { } + + public static class P43 extends ProxyPendingActivity { } + + public static class P44 extends ProxyPendingActivity { } + + public static class P45 extends ProxyPendingActivity { } + + public static class P46 extends ProxyPendingActivity { } + + public static class P47 extends ProxyPendingActivity { } + + public static class P48 extends ProxyPendingActivity { } + + public static class P49 extends ProxyPendingActivity { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyService.java new file mode 100644 index 0000000..5fc19f1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyService.java @@ -0,0 +1,156 @@ +package com.vcore.proxy; + +import android.app.Service; +import android.content.Intent; +import android.content.res.Configuration; +import android.os.IBinder; + +import androidx.annotation.Nullable; + +import com.vcore.app.dispatcher.AppServiceDispatcher; + +public class ProxyService extends Service { + public static final String TAG = "StubService"; + + @Nullable + @Override + public IBinder onBind(Intent intent) { + return AppServiceDispatcher.get().onBind(intent); + } + + @Override + public int onStartCommand(Intent intent, int flags, int startId) { + AppServiceDispatcher.get().onStartCommand(intent); + return START_NOT_STICKY; + } + + @Override + public void onDestroy() { + super.onDestroy(); + AppServiceDispatcher.get().onDestroy(); + } + + @Override + public void onConfigurationChanged(Configuration newConfig) { + super.onConfigurationChanged(newConfig); + AppServiceDispatcher.get().onConfigurationChanged(newConfig); + } + + @Override + public void onLowMemory() { + super.onLowMemory(); + AppServiceDispatcher.get().onLowMemory(); + } + + @Override + public void onTrimMemory(int level) { + super.onTrimMemory(level); + AppServiceDispatcher.get().onTrimMemory(level); + } + + @Override + public boolean onUnbind(Intent intent) { + AppServiceDispatcher.get().onUnbind(intent); + return false; + } + + public static class P0 extends ProxyService { } + + public static class P1 extends ProxyService { } + + public static class P2 extends ProxyService { } + + public static class P3 extends ProxyService { } + + public static class P4 extends ProxyService { } + + public static class P5 extends ProxyService { } + + public static class P6 extends ProxyService { } + + public static class P7 extends ProxyService { } + + public static class P8 extends ProxyService { } + + public static class P9 extends ProxyService { } + + public static class P10 extends ProxyService { } + + public static class P11 extends ProxyService { } + + public static class P12 extends ProxyService { } + + public static class P13 extends ProxyService { } + + public static class P14 extends ProxyService { } + + public static class P15 extends ProxyService { } + + public static class P16 extends ProxyService { } + + public static class P17 extends ProxyService { } + + public static class P18 extends ProxyService { } + + public static class P19 extends ProxyService { } + + public static class P20 extends ProxyService { } + + public static class P21 extends ProxyService { } + + public static class P22 extends ProxyService { } + + public static class P23 extends ProxyService { } + + public static class P24 extends ProxyService { } + + public static class P25 extends ProxyService { } + + public static class P26 extends ProxyService { } + + public static class P27 extends ProxyService { } + + public static class P28 extends ProxyService { } + + public static class P29 extends ProxyService { } + + public static class P30 extends ProxyService { } + + public static class P31 extends ProxyService { } + + public static class P32 extends ProxyService { } + + public static class P33 extends ProxyService { } + + public static class P34 extends ProxyService { } + + public static class P35 extends ProxyService { } + + public static class P36 extends ProxyService { } + + public static class P37 extends ProxyService { } + + public static class P38 extends ProxyService { } + + public static class P39 extends ProxyService { } + + public static class P40 extends ProxyService { } + + public static class P41 extends ProxyService { } + + public static class P42 extends ProxyService { } + + public static class P43 extends ProxyService { } + + public static class P44 extends ProxyService { } + + public static class P45 extends ProxyService { } + + public static class P46 extends ProxyService { } + + public static class P47 extends ProxyService { } + + public static class P48 extends ProxyService { } + + public static class P49 extends ProxyService { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyVpnService.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyVpnService.java new file mode 100644 index 0000000..271eb85 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/ProxyVpnService.java @@ -0,0 +1,5 @@ +package com.vcore.proxy; + +import android.net.VpnService; + +public class ProxyVpnService extends VpnService { } diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/TransparentProxyActivity.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/TransparentProxyActivity.java new file mode 100644 index 0000000..1a821ba --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/TransparentProxyActivity.java @@ -0,0 +1,103 @@ +package com.vcore.proxy; + +public class TransparentProxyActivity extends ProxyActivity { + public static class P0 extends TransparentProxyActivity { } + + public static class P1 extends TransparentProxyActivity { } + + public static class P2 extends TransparentProxyActivity { } + + public static class P3 extends TransparentProxyActivity { } + + public static class P4 extends TransparentProxyActivity { } + + public static class P5 extends TransparentProxyActivity { } + + public static class P6 extends TransparentProxyActivity { } + + public static class P7 extends TransparentProxyActivity { } + + public static class P8 extends TransparentProxyActivity { } + + public static class P9 extends TransparentProxyActivity { } + + public static class P10 extends TransparentProxyActivity { } + + public static class P11 extends TransparentProxyActivity { } + + public static class P12 extends TransparentProxyActivity { } + + public static class P13 extends TransparentProxyActivity { } + + public static class P14 extends TransparentProxyActivity { } + + public static class P15 extends TransparentProxyActivity { } + + public static class P16 extends TransparentProxyActivity { } + + public static class P17 extends TransparentProxyActivity { } + + public static class P18 extends TransparentProxyActivity { } + + public static class P19 extends TransparentProxyActivity { } + + public static class P20 extends TransparentProxyActivity { } + + public static class P21 extends TransparentProxyActivity { } + + public static class P22 extends TransparentProxyActivity { } + + public static class P23 extends TransparentProxyActivity { } + + public static class P24 extends TransparentProxyActivity { } + + public static class P25 extends TransparentProxyActivity { } + + public static class P26 extends TransparentProxyActivity { } + + public static class P27 extends TransparentProxyActivity { } + + public static class P28 extends TransparentProxyActivity { } + + public static class P29 extends TransparentProxyActivity { } + + public static class P30 extends TransparentProxyActivity { } + + public static class P31 extends TransparentProxyActivity { } + + public static class P32 extends TransparentProxyActivity { } + + public static class P33 extends TransparentProxyActivity { } + + public static class P34 extends TransparentProxyActivity { } + + public static class P35 extends TransparentProxyActivity { } + + public static class P36 extends TransparentProxyActivity { } + + public static class P37 extends TransparentProxyActivity { } + + public static class P38 extends TransparentProxyActivity { } + + public static class P39 extends TransparentProxyActivity { } + + public static class P40 extends TransparentProxyActivity { } + + public static class P41 extends TransparentProxyActivity { } + + public static class P42 extends TransparentProxyActivity { } + + public static class P43 extends TransparentProxyActivity { } + + public static class P44 extends TransparentProxyActivity { } + + public static class P45 extends TransparentProxyActivity { } + + public static class P46 extends TransparentProxyActivity { } + + public static class P47 extends TransparentProxyActivity { } + + public static class P48 extends TransparentProxyActivity { } + + public static class P49 extends TransparentProxyActivity { } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyActivityRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyActivityRecord.java new file mode 100644 index 0000000..32b0f04 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyActivityRecord.java @@ -0,0 +1,34 @@ +package com.vcore.proxy.record; + +import android.content.Intent; +import android.content.pm.ActivityInfo; + +public class ProxyActivityRecord { + public final int mUserId; + public final ActivityInfo mActivityInfo; + public final Intent mTarget; + public final String mActivityToken; + + public ProxyActivityRecord(int userId, ActivityInfo activityInfo, Intent target, String activityToken) { + this.mUserId = userId; + this.mActivityInfo = activityInfo; + this.mTarget = target; + this.mActivityToken = activityToken; + } + + public static void saveStub(Intent shadow, Intent target, ActivityInfo activityInfo, String activityToken, int userId) { + shadow.putExtra("_B_|_user_id_", userId); + shadow.putExtra("_B_|_activity_info_", activityInfo); + shadow.putExtra("_B_|_target_", target); + shadow.putExtra("_B_|_activity_token_v_", activityToken); + } + + public static ProxyActivityRecord create(Intent intent) { + int userId = intent.getIntExtra("_B_|_user_id_", 0); + ActivityInfo activityInfo = intent.getParcelableExtra("_B_|_activity_info_"); + + Intent target = intent.getParcelableExtra("_B_|_target_"); + String activityToken = intent.getStringExtra("_B_|_activity_token_v_"); + return new ProxyActivityRecord(userId, activityInfo, target, activityToken); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyBroadcastRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyBroadcastRecord.java new file mode 100644 index 0000000..853ac9d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyBroadcastRecord.java @@ -0,0 +1,32 @@ +package com.vcore.proxy.record; + +import android.content.Intent; + +import androidx.annotation.NonNull; + +public class ProxyBroadcastRecord { + public final Intent mIntent; + public final int mUserId; + + public ProxyBroadcastRecord(Intent intent, int userId) { + this.mIntent = intent; + this.mUserId = userId; + } + + public static void saveStub(Intent shadow, Intent target, int userId) { + shadow.putExtra("_B_|_target_", target); + shadow.putExtra("_B_|_user_id_", userId); + } + + public static ProxyBroadcastRecord create(Intent intent) { + Intent target = intent.getParcelableExtra("_B_|_target_"); + int userId = intent.getIntExtra("_B_|_user_id_", 0); + return new ProxyBroadcastRecord(target, userId); + } + + @NonNull + @Override + public String toString() { + return "ProxyBroadcastRecord{" + "mIntent=" + mIntent + ", mUserId=" + mUserId + '}'; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyPendingRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyPendingRecord.java new file mode 100644 index 0000000..35819a7 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyPendingRecord.java @@ -0,0 +1,32 @@ +package com.vcore.proxy.record; + +import android.content.Intent; + +import androidx.annotation.NonNull; + +public class ProxyPendingRecord { + public final int mUserId; + public final Intent mTarget; + + public ProxyPendingRecord(Intent target, int userId) { + this.mUserId = userId; + this.mTarget = target; + } + + public static void saveStub(Intent shadow, Intent target, int userId) { + shadow.putExtra("_B_|_P_user_id_", userId); + shadow.putExtra("_B_|_P_target_", target); + } + + public static ProxyPendingRecord create(Intent intent) { + int userId = intent.getIntExtra("_B_|_P_user_id_", 0); + Intent target = intent.getParcelableExtra("_B_|_P_target_"); + return new ProxyPendingRecord(target, userId); + } + + @NonNull + @Override + public String toString() { + return "ProxyPendingActivityRecord{" + "mUserId=" + mUserId + ", mTarget=" + mTarget + '}'; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyServiceRecord.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyServiceRecord.java new file mode 100644 index 0000000..4c21410 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/proxy/record/ProxyServiceRecord.java @@ -0,0 +1,42 @@ +package com.vcore.proxy.record; + +import android.content.Intent; +import android.content.pm.ServiceInfo; +import android.os.IBinder; + +import com.vcore.utils.compat.BundleCompat; + +public class ProxyServiceRecord { + public final Intent mServiceIntent; + public final ServiceInfo mServiceInfo; + public final IBinder mToken; + public final int mUserId; + public final int mStartId; + + public ProxyServiceRecord(Intent serviceIntent, ServiceInfo serviceInfo, IBinder token, int userId, int startId) { + this.mServiceIntent = serviceIntent; + this.mServiceInfo = serviceInfo; + this.mUserId = userId; + this.mStartId = startId; + this.mToken = token; + } + + public static void saveStub(Intent shadow, Intent target, ServiceInfo serviceInfo, IBinder token, int userId, int startId) { + shadow.putExtra("_B_|_target_", target); + shadow.putExtra("_B_|_service_info_", serviceInfo); + shadow.putExtra("_B_|_user_id_", userId); + shadow.putExtra("_B_|_start_id_", startId); + BundleCompat.putBinder(shadow, "_B_|_token_", token); + } + + public static ProxyServiceRecord create(Intent intent) { + Intent target = intent.getParcelableExtra("_B_|_target_"); + ServiceInfo serviceInfo = intent.getParcelableExtra("_B_|_service_info_"); + + int userId = intent.getIntExtra("_B_|_user_id_", 0); + int startId = intent.getIntExtra("_B_|_start_id_", 0); + + IBinder token = BundleCompat.getBinder(intent, "_B_|_token_"); + return new ProxyServiceRecord(target, serviceInfo, token, userId, startId); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/AbiUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/AbiUtils.java similarity index 90% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/AbiUtils.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/AbiUtils.java index 1e3623f..d398995 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/AbiUtils.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/AbiUtils.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.utils; +package com.vcore.utils; import java.io.File; import java.util.Enumeration; @@ -9,16 +9,8 @@ import java.util.zip.ZipEntry; import java.util.zip.ZipFile; -import top.niunaijun.blackbox.BlackBoxCore; +import com.vcore.BlackBoxCore; -/** - * Created by Milk on 3/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class AbiUtils { private final Set mLibs = new HashSet<>(); private static final Map sAbiUtilsMap = new HashMap<>(); @@ -29,6 +21,7 @@ public static boolean isSupport(File apkFile) { abiUtils = new AbiUtils(apkFile); sAbiUtilsMap.put(apkFile, abiUtils); } + if (abiUtils.isEmptyAib()) { return true; } @@ -45,9 +38,11 @@ public AbiUtils(File apkFile) { try { zipFile = new ZipFile(apkFile); Enumeration entries = zipFile.entries(); + while (entries.hasMoreElements()) { ZipEntry zipEntry = entries.nextElement(); String name = zipEntry.getName(); + if (name.startsWith("lib/arm64-v8a")) { mLibs.add("arm64-v8a"); } else if (name.startsWith("lib/armeabi")) { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ArrayUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ArrayUtils.java new file mode 100644 index 0000000..170e2b2 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ArrayUtils.java @@ -0,0 +1,66 @@ +package com.vcore.utils; + +import java.util.Arrays; + +public class ArrayUtils { + public static T[] trimToSize(T[] array, int size) { + if (array == null || size == 0) { + return null; + } else if (array.length == size) { + return array; + } + return Arrays.copyOf(array, size); + } + + public static int indexOfFirst(Object[] array, Class type) { + if (!isEmpty(array)) { + int N = -1; + for (Object one : array) { + N++; + if (one != null && type == one.getClass()) { + return N; + } + } + } + return -1; + } + + public static int indexOfObject(Object[] array, Class type, int sequence) { + if (array == null) { + return -1; + } + + while (sequence < array.length) { + if (type.isInstance(array[sequence])) { + return sequence; + } + sequence++; + } + return -1; + } + + public static int indexOfLast(Object[] array, Class type) { + if (!isEmpty(array)) { + for (int N = array.length; N > 0; N--) { + Object one = array[N - 1]; + if (one != null && one.getClass() == type) { + return N - 1; + } + } + } + return -1; + } + + public static int[] toInt(Integer[] array) { + int[] newArray = new int[array.length]; + + for (int i = 0; i < array.length; i++) { + newArray[i] = array[i]; + } + return newArray; + } + + public static boolean isEmpty(T[] array) { + return array == null || array.length == 0; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/CloseUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/CloseUtils.java new file mode 100644 index 0000000..5e60b00 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/CloseUtils.java @@ -0,0 +1,20 @@ +package com.vcore.utils; + +import java.io.Closeable; +import java.io.IOException; + +public class CloseUtils { + public static void close(Closeable... closeables) { + if (closeables == null) { + return; + } + + for (Closeable closeable : closeables) { + if (closeable != null) { + try { + closeable.close(); + } catch (IOException ignored) { } + } + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/ComponentUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ComponentUtils.java similarity index 75% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/ComponentUtils.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ComponentUtils.java index 006bc11..631e7cc 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/ComponentUtils.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ComponentUtils.java @@ -1,26 +1,26 @@ -package top.niunaijun.blackbox.utils; +package com.vcore.utils; + +import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_INSTANCE; import android.content.ComponentName; import android.content.Intent; import android.content.pm.ActivityInfo; import android.content.pm.ComponentInfo; -import android.content.pm.ProviderInfo; import java.util.Objects; -import top.niunaijun.blackbox.app.BActivityThread; - -import static android.content.pm.ActivityInfo.LAUNCH_SINGLE_INSTANCE; +import com.vcore.app.BActivityThread; public class ComponentUtils { - public static boolean isRequestInstall(Intent intent) { return "application/vnd.android.package-archive".equals(intent.getType()); } public static boolean isSelf(Intent intent) { ComponentName component = intent.getComponent(); - if (component == null || BActivityThread.getAppPackageName() == null) return false; + if (component == null || BActivityThread.getAppPackageName() == null) { + return false; + } return component.getPackageName().equals(BActivityThread.getAppPackageName()); } @@ -44,42 +44,38 @@ public static String getTaskAffinity(ActivityInfo info) { return info.applicationInfo.taskAffinity; } - public static String getFirstAuthority(ProviderInfo info) { - if (info == null) { - return null; - } - String[] authorities = info.authority.split(";"); - return authorities.length == 0 ? info.authority : authorities[0]; - } - public static boolean intentFilterEquals(Intent a, Intent b) { if (a != null && b != null) { if (!Objects.equals(a.getAction(), b.getAction())) { return false; } + if (!Objects.equals(a.getData(), b.getData())) { return false; } + if (!Objects.equals(a.getType(), b.getType())) { return false; } + Object pkgA = a.getPackage(); if (pkgA == null && a.getComponent() != null) { pkgA = a.getComponent().getPackageName(); } + String pkgB = b.getPackage(); if (pkgB == null && b.getComponent() != null) { pkgB = b.getComponent().getPackageName(); } + if (!Objects.equals(pkgA, pkgB)) { return false; } + if (!Objects.equals(a.getComponent(), b.getComponent())) { return false; } - if (!Objects.equals(a.getCategories(), b.getCategories())) { - return false; - } + return Objects.equals(a.getCategories(), b.getCategories()); } return true; } @@ -93,18 +89,6 @@ public static String getProcessName(ComponentInfo componentInfo) { return processName; } - public static boolean isSameComponent(ComponentInfo first, ComponentInfo second) { - - if (first != null && second != null) { - String pkg1 = first.packageName + ""; - String pkg2 = second.packageName + ""; - String name1 = first.name + ""; - String name2 = second.name + ""; - return pkg1.equals(pkg2) && name1.equals(name2); - } - return false; - } - public static ComponentName toComponentName(ComponentInfo componentInfo) { return new ComponentName(componentInfo.packageName, componentInfo.name); } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/DrawableUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/DrawableUtils.java similarity index 77% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/DrawableUtils.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/DrawableUtils.java index bb700e1..29641b3 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/DrawableUtils.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/DrawableUtils.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.utils; +package com.vcore.utils; import android.graphics.Bitmap; import android.graphics.Canvas; @@ -8,16 +8,17 @@ public class DrawableUtils { public static Bitmap drawableToBitmap(Drawable drawable, int width, int height) { - if (drawable == null) + if (drawable == null) { return null; + } - if (drawable instanceof BitmapDrawable) + if (drawable instanceof BitmapDrawable) { return ((BitmapDrawable) drawable).getBitmap(); + } - Bitmap.Config config = drawable.getOpacity() != PixelFormat.OPAQUE ? - Bitmap.Config.ARGB_8888 : Bitmap.Config.RGB_565; - + Bitmap.Config config = drawable.getOpacity() != PixelFormat.OPAQUE ? Bitmap.Config.ARGB_8888 : Bitmap.Config.RGB_565; Bitmap bitmap = Bitmap.createBitmap(width, height, config); + Canvas canvas = new Canvas(bitmap); drawable.setBounds(0, 0, width, height); drawable.draw(canvas); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/FileUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/FileUtils.java new file mode 100644 index 0000000..057d3e1 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/FileUtils.java @@ -0,0 +1,186 @@ +package com.vcore.utils; + +import android.os.Parcel; + +import java.io.ByteArrayInputStream; +import java.io.ByteArrayOutputStream; +import java.io.Closeable; +import java.io.File; +import java.io.FileInputStream; +import java.io.FileOutputStream; +import java.io.IOException; +import java.io.InputStream; +import java.nio.ByteBuffer; +import java.nio.channels.Channels; +import java.nio.channels.FileChannel; +import java.nio.channels.ReadableByteChannel; + +public class FileUtils { + public static int count(File file) { + if (!file.exists()) { + return -1; + } + + if (file.isFile()) { + return 1; + } + + if (file.isDirectory()) { + String[] fs = file.list(); + return fs == null ? 0 : fs.length; + } + return 0; + } + + public static boolean renameTo(File origFile, File newFile) { + return origFile.renameTo(newFile); + } + + public static Parcel readToParcel(File file) throws IOException { + Parcel in = Parcel.obtain(); + byte[] bytes = toByteArray(file); + + in.unmarshall(bytes, 0, bytes.length); + in.setDataPosition(0); + return in; + } + + public static boolean isSymlink(File file) throws IOException { + if (file == null) { + throw new NullPointerException("File must not be null"); + } + + File canon; + if (file.getParent() == null) { + canon = file; + } else { + File canonDir = file.getParentFile().getCanonicalFile(); + canon = new File(canonDir, file.getName()); + } + return !canon.getCanonicalFile().equals(canon.getAbsoluteFile()); + } + + public static void writeParcelToOutput(Parcel p, FileOutputStream fos) throws IOException { + fos.write(p.marshall()); + } + + public static byte[] toByteArray(File file) throws IOException { + FileInputStream fileInputStream = new FileInputStream(file); + try { + return toByteArray(fileInputStream); + } finally { + closeQuietly(fileInputStream); + } + } + + public static byte[] toByteArray(InputStream inStream) throws IOException { + ByteArrayOutputStream swapStream = new ByteArrayOutputStream(); + byte[] buff = new byte[100]; + int rc; + while ((rc = inStream.read(buff, 0, 100)) > 0) { + swapStream.write(buff, 0, rc); + } + return swapStream.toByteArray(); + } + + public static int deleteDir(File dir) { + int count = 0; + if (dir.isDirectory()) { + boolean link = false; + try { + link = isSymlink(dir); + } catch (Exception ignored) { } + + if (!link) { + String[] children = dir.list(); + for (String file : children) { + count += deleteDir(new File(dir, file)); + } + } + } + + if (dir.delete()) { + count++; + } + return count; + } + + public static int deleteDir(String dir) { + return deleteDir(new File(dir)); + } + + public static void writeToFile(byte[] data, File target) throws IOException { + try (ReadableByteChannel src = Channels.newChannel(new ByteArrayInputStream(data)); + FileOutputStream fo = new FileOutputStream(target); + FileChannel out = fo.getChannel()) { + out.transferFrom(src, 0, data.length); + } + } + + public static void copyFile(InputStream inputStream, File target) { + FileOutputStream outputStream = null; + try { + outputStream = new FileOutputStream(target); + byte[] data = new byte[4096]; + int len; + while ((len = inputStream.read(data)) != -1) { + outputStream.write(data, 0, len); + } + outputStream.flush(); + } catch (Throwable e) { + // Ignore + } finally { + closeQuietly(inputStream); + closeQuietly(outputStream); + } + } + + public static void copyFile(File source, File target) throws IOException { + FileInputStream inputStream = null; + FileOutputStream outputStream = null; + try { + inputStream = new FileInputStream(source); + outputStream = new FileOutputStream(target); + FileChannel iChannel = inputStream.getChannel(); + FileChannel oChannel = outputStream.getChannel(); + + ByteBuffer buffer = ByteBuffer.allocate(1024); + while (true) { + buffer.clear(); + int r = iChannel.read(buffer); + if (r == -1) { + break; + } + + buffer.limit(buffer.position()); + buffer.position(0); + oChannel.write(buffer); + } + } finally { + closeQuietly(inputStream); + closeQuietly(outputStream); + } + } + + public static void closeQuietly(Closeable closeable) { + if (closeable != null) { + try { + closeable.close(); + } catch (Exception ignored) { } + } + } + + public static void mkdirs(File path) { + if (!path.exists()) { + path.mkdirs(); + } + } + + public static void mkdirs(String path) { + mkdirs(new File(path)); + } + + public static boolean isExist(String path) { + return new File(path).exists(); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Md5Utils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Md5Utils.java new file mode 100644 index 0000000..41cd468 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Md5Utils.java @@ -0,0 +1,36 @@ +package com.vcore.utils; + +import java.nio.charset.StandardCharsets; +import java.security.MessageDigest; + +public class Md5Utils { + private static final char[] hexDigits = {'0', '1', '2', '3', '4', '5', '6', '7', '8', '9', 'a', 'b', 'c', 'd', 'e', 'f'}; + + public static String md5(String input) { + if (input == null) { + return null; + } + + try { + MessageDigest messageDigest = MessageDigest.getInstance("MD5"); + byte[] inputByteArray = input.getBytes(StandardCharsets.UTF_8); + messageDigest.update(inputByteArray); + + byte[] resultByteArray = messageDigest.digest(); + return byteArrayToHex(resultByteArray); + } catch (Exception e) { + return null; + } + } + + private static String byteArrayToHex(byte[] byteArray) { + char[] resultCharArray = new char[byteArray.length * 2]; + int index = 0; + + for (byte b : byteArray) { + resultCharArray[index++] = hexDigits[b >>> 4 & 0xf]; + resultCharArray[index++] = hexDigits[b & 0xf]; + } + return new String(resultCharArray); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/MethodParameterUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/MethodParameterUtils.java new file mode 100644 index 0000000..874130b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/MethodParameterUtils.java @@ -0,0 +1,125 @@ +package com.vcore.utils; + +import java.util.Arrays; +import java.util.HashSet; +import java.util.Objects; + +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; + +public class MethodParameterUtils { + public static T getFirstParam(Object[] args, Class tClass) { + if (args == null) { + return null; + } + + int index = ArrayUtils.indexOfFirst(args, tClass); + if (index != -1) { + return (T) args[index]; + } + return null; + } + + public static T getFirstParamByInstance(Object[] args, Class tClass) { + if (args == null) { + return null; + } + + int index = ArrayUtils.indexOfObject(args, tClass, 0); + if (index != -1) { + return (T) args[index]; + } + return null; + } + + public static String replaceFirstAppPkg(Object[] args) { + if (args == null) { + return null; + } + + for (int i = 0; i < args.length; i++) { + if (args[i] instanceof String) { + String value = (String) args[i]; + if (BlackBoxCore.get().isInstalled(value, BActivityThread.getUserId())) { + args[i] = BlackBoxCore.getHostPkg(); + return value; + } + } + } + return null; + } + + public static void replaceAllAppPkg(Object[] args) { + if (args == null) { + return; + } + + for (int i = 0; i < args.length; i++) { + if (args[i] == null) { + continue; + } + + if (args[i] instanceof String) { + String value = (String) args[i]; + if (BlackBoxCore.get().isInstalled(value, BActivityThread.getUserId())) { + args[i] = BlackBoxCore.getHostPkg(); + } + } + } + } + + public static void replaceFirstUid(Object[] args) { + if (args == null) { + return; + } + + for (int i = 0; i < args.length; i++) { + if (args[i] instanceof Integer) { + int uid = (int) args[i]; + if (uid == BActivityThread.getBUid()) { + args[i] = BlackBoxCore.getHostUid(); + } + } + } + } + + public static void replaceLastUid(Object[] args) { + int index = ArrayUtils.indexOfLast(args, Integer.class); + if (index != -1) { + int uid = (int) args[index]; + if (uid == BActivityThread.getBUid()) { + args[index] = BlackBoxCore.getHostUid(); + } + } + } + + public static void replaceLastAppPkg(Object[] args) { + int index = ArrayUtils.indexOfLast(args, String.class); + if (index != -1) { + String pkg = (String) args[index]; + if (BlackBoxCore.get().isInstalled(pkg, BActivityThread.getUserId())) { + args[index] = BlackBoxCore.getHostPkg(); + } + } + } + + public static Class[] getAllInterface(Class clazz) { + HashSet> classes = new HashSet<>(); + getAllInterfaces(clazz, classes); + + Class[] result = new Class[classes.size()]; + classes.toArray(result); + return result; + } + + public static void getAllInterfaces(Class clazz, HashSet> interfaceCollection) { + Class[] classes = clazz.getInterfaces(); + if (classes.length != 0) { + interfaceCollection.addAll(Arrays.asList(classes)); + } + + if (clazz.getSuperclass() != Object.class) { + getAllInterfaces(Objects.requireNonNull(clazz.getSuperclass()), interfaceCollection); + } + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/NativeUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/NativeUtils.java similarity index 88% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/NativeUtils.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/NativeUtils.java index b8f3164..a86fba4 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/NativeUtils.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/NativeUtils.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.utils; +package com.vcore.utils; import android.os.Build; import android.util.Log; @@ -14,23 +14,15 @@ import java.util.zip.ZipEntry; import java.util.zip.ZipFile; - -/** - * Created by Milk on 2/24/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class NativeUtils { - public static final String TAG = "VirtualM"; + public static final String TAG = "NativeUtils"; public static void copyNativeLib(File apk, File nativeLibDir) throws Exception { long startTime = System.currentTimeMillis(); if (!nativeLibDir.exists()) { nativeLibDir.mkdirs(); } + try (ZipFile zipfile = new ZipFile(apk.getAbsolutePath())) { if (findAndCopyNativeLib(zipfile, Build.CPU_ABI, nativeLibDir)) { return; @@ -42,15 +34,15 @@ public static void copyNativeLib(File apk, File nativeLibDir) throws Exception { } } - private static boolean findAndCopyNativeLib(ZipFile zipfile, String cpuArch, File nativeLibDir) throws Exception { Log.d(TAG, "Try to copy plugin's cup arch: " + cpuArch); boolean findLib = false; boolean findSo = false; - byte buffer[] = null; + byte[] buffer = null; + String libPrefix = "lib/" + cpuArch + "/"; ZipEntry entry; - Enumeration e = zipfile.entries(); + Enumeration e = zipfile.entries(); while (e.hasMoreElements()) { entry = (ZipEntry) e.nextElement(); @@ -58,6 +50,7 @@ private static boolean findAndCopyNativeLib(ZipFile zipfile, String cpuArch, Fil if (!findLib && !entryName.startsWith("lib/")) { continue; } + findLib = true; if (!entryName.endsWith(".so") || !entryName.startsWith(libPrefix)) { continue; @@ -71,16 +64,13 @@ private static boolean findAndCopyNativeLib(ZipFile zipfile, String cpuArch, Fil String libName = entryName.substring(entryName.lastIndexOf('/') + 1); Log.d(TAG, "verify so " + libName); -// File abiDir = new File(nativeLibDir, cpuArch); -// if (!abiDir.exists()) { -// abiDir.mkdirs(); -// } File libFile = new File(nativeLibDir, libName); if (libFile.exists() && libFile.length() == entry.getSize()) { Log.d(TAG, libName + " skip copy"); continue; } + FileOutputStream fos = new FileOutputStream(libFile); Log.d(TAG, "copy so " + entry.getName() + " of " + cpuArch); copySo(buffer, zipfile.getInputStream(entry), fos); @@ -90,7 +80,6 @@ private static boolean findAndCopyNativeLib(ZipFile zipfile, String cpuArch, Fil Log.d(TAG, "Fast skip all!"); return true; } - return findSo; } @@ -102,6 +91,7 @@ private static void copySo(byte[] buffer, InputStream input, OutputStream output while ((count = bufferedInput.read(buffer)) > 0) { bufferedOutput.write(buffer, 0, count); } + bufferedOutput.flush(); bufferedOutput.close(); output.close(); diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ShellUtils.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ShellUtils.java new file mode 100644 index 0000000..89022d9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/ShellUtils.java @@ -0,0 +1,125 @@ +package com.vcore.utils; + +import java.io.BufferedReader; +import java.io.DataOutputStream; +import java.io.IOException; +import java.io.InputStreamReader; + +public class ShellUtils { + public static final String COMMAND_SU = "su"; + public static final String COMMAND_SH = "sh"; + public static final String COMMAND_EXIT = "exit\n"; + public static final String COMMAND_LINE_END = "\n"; + + private ShellUtils() { + throw new AssertionError(); + } + + /** + * Execute shell command, default return result msg + * + * @param command command + * @param isRoot whether need to run with root + * @see ShellUtils#execCommand(String[], boolean, boolean) + */ + public static void execCommand(String command, boolean isRoot) { + execCommand(new String[]{command}, isRoot, true); + } + + /** + * Execute shell commands + * + * @param commands command array + * @param isRoot whether need to run with root + * @param isNeedResultMsg whether need result msg + * @return
    + *
  • if isNeedResultMsg is false, {@link CommandResult#successMsg} is null and + *
  • if {@link CommandResult#result} is -1, there maybe some exception.
  • + *
+ */ + public static CommandResult execCommand(String[] commands, boolean isRoot, boolean isNeedResultMsg) { + int result = -1; + if (commands == null || commands.length == 0) { + return new CommandResult(result, null); + } + + Process process = null; + BufferedReader successResult = null; + StringBuilder successMsg = null; + DataOutputStream os = null; + + try { + process = Runtime.getRuntime().exec(isRoot ? COMMAND_SU : COMMAND_SH); + os = new DataOutputStream(process.getOutputStream()); + + for (String command : commands) { + if (command == null) { + continue; + } + + os.write(command.getBytes()); + os.writeBytes(COMMAND_LINE_END); + os.flush(); + } + + os.writeBytes(COMMAND_EXIT); + os.flush(); + + result = process.waitFor(); + if (isNeedResultMsg) { + successMsg = new StringBuilder(); + successResult = new BufferedReader(new InputStreamReader(process.getInputStream())); + String s; + + while ((s = successResult.readLine()) != null) { + successMsg.append(s).append("\n"); + } + } + } catch (Exception e) { + e.printStackTrace(); + } finally { + try { + if (os != null) { + os.close(); + } + + if (successResult != null) { + successResult.close(); + } + } catch (IOException e) { + e.printStackTrace(); + } + + if (process != null) { + process.destroy(); + } + } + return new CommandResult(result, successMsg == null ? null : successMsg.toString()); + } + + /** + * Result of command + *
    + *
  • {@link CommandResult#result} means result of command, 0 means normal, else means error, same to execute in + * linux shell
  • + *
  • {@link CommandResult#successMsg} means success message of command result
  • + *
+ * + * @author Trinea 2013-5-16 + */ + public static class CommandResult { + /** + * result of command + **/ + public final int result; + /** + * success message of command result + **/ + public final String successMsg; + + public CommandResult(int result, String successMsg) { + this.result = result; + this.successMsg = successMsg; + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Slog.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Slog.java new file mode 100644 index 0000000..9f50253 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/Slog.java @@ -0,0 +1,59 @@ +package com.vcore.utils; + +import android.util.Log; + +/** + * @hide + */ +public final class Slog { + private Slog() { } + + public static void v(String tag, String msg) { + println(Log.VERBOSE, tag, msg); + } + + public static void v(String tag, String msg, Throwable tr) { + println(Log.VERBOSE, tag, msg + '\n' + Log.getStackTraceString(tr)); + } + + public static void d(String tag, String msg) { + println(Log.DEBUG, tag, msg); + } + + public static void d(String tag, String msg, Throwable tr) { + println(Log.DEBUG, tag, msg + '\n' + Log.getStackTraceString(tr)); + } + + public static void i(String tag, String msg) { + println(Log.INFO, tag, msg); + } + + public static void i(String tag, String msg, Throwable tr) { + println(Log.INFO, tag, msg + '\n' + Log.getStackTraceString(tr)); + } + + public static void w(String tag, String msg) { + println(Log.WARN, tag, msg); + } + + public static void w(String tag, String msg, Throwable tr) { + println(Log.WARN, tag, msg + '\n' + Log.getStackTraceString(tr)); + } + + public static void w(String tag, Throwable tr) { + println(Log.WARN, tag, Log.getStackTraceString(tr)); + } + + public static void e(String tag, String msg) { + println(Log.ERROR, tag, msg); + } + + public static void e(String tag, String msg, Throwable tr) { + println(Log.ERROR, tag, msg + '\n' + Log.getStackTraceString(tr)); + } + + public static void println(int priority, String tag, String msg) { + Log.println(priority, tag, msg); + } +} + diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/TrieTree.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/TrieTree.java new file mode 100644 index 0000000..340afa5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/TrieTree.java @@ -0,0 +1,81 @@ +package com.vcore.utils; + +import java.util.LinkedList; +import java.util.List; +import java.util.Objects; + +public class TrieTree { + private final TrieNode root = new TrieNode(); + + private static class TrieNode { + char content; + String word; + boolean isEnd = false; + final List children = new LinkedList<>(); + + public TrieNode() { } + + public TrieNode(char content, String word) { + this.content = content; + this.word = word; + } + + @Override + public boolean equals(Object object) { + if (object instanceof TrieNode) { + return ((TrieNode) object).content == content; + } + return false; + } + + public TrieNode nextNode(char content) { + for (TrieNode childNode : children) { + if (childNode.content == content) { + return childNode; + } + } + return null; + } + } + + public void add(String word) { + TrieNode current = root; + StringBuilder wordBuilder = new StringBuilder(); + + for (int index = 0; index < word.length(); ++index) { + char content = word.charAt(index); + wordBuilder.append(content); + + TrieNode node = new TrieNode(content, wordBuilder.toString()); + if (Objects.requireNonNull(current).children.contains(node)) { + current = current.nextNode(content); + } else { + current.children.add(node); + current = node; + } + + if (index == (word.length() - 1)) { + Objects.requireNonNull(current).isEnd = true; + } + } + } + + public String search(String word) { + TrieNode current = root; + for (int index = 0; index < word.length(); ++index) { + char content = word.charAt(index); + + TrieNode node = new TrieNode(content, null); + if (current.children.contains(node)) { + current = current.nextNode(content); + } else { + return null; + } + + if (Objects.requireNonNull(current).isEnd) { + return current.word; + } + } + return null; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/AccountManagerCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/AccountManagerCompat.java new file mode 100644 index 0000000..fbc929b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/AccountManagerCompat.java @@ -0,0 +1,9 @@ +package com.vcore.utils.compat; + +public class AccountManagerCompat { + /** + * Boolean, if set and 'customTokens' the authenticator is responsible for + * notifications. + */ + public static final String KEY_NOTIFY_ON_FAILURE = "notifyOnAuthFailure"; +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityCompat.java new file mode 100644 index 0000000..53dbcb9 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityCompat.java @@ -0,0 +1,77 @@ +package com.vcore.utils.compat; + +import android.app.Activity; +import android.app.ActivityManager; +import android.app.WallpaperManager; +import android.content.Context; +import android.content.Intent; +import android.content.pm.ApplicationInfo; +import android.content.pm.PackageManager; +import android.content.res.TypedArray; +import android.graphics.Bitmap; +import android.graphics.drawable.Drawable; +import android.view.WindowManager; + +import com.vcore.app.BActivityThread; +import com.vcore.utils.ArrayUtils; +import com.vcore.utils.DrawableUtils; + +public class ActivityCompat { + public static void fix(Activity activity) { + Context baseContext = activity.getBaseContext(); + try { + TypedArray typedArray = activity.obtainStyledAttributes(ArrayUtils.toInt(black.com.android.internal.R.styleable.Window.get())); + if (typedArray != null) { + boolean isShowWallpaper = typedArray.getBoolean(black.com.android.internal.R.styleable.Window_windowShowWallpaper.get(), false); + if (isShowWallpaper) { + activity.getWindow().setBackgroundDrawable(WallpaperManager.getInstance(activity).getDrawable()); + } + + boolean isFullscreen = typedArray.getBoolean(black.com.android.internal.R.styleable.Window_windowFullscreen.get(), false); + if (isFullscreen) { + activity.getWindow().addFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN); + } + typedArray.recycle(); + } + } catch (Throwable e) { + e.printStackTrace(); + } + + if (BuildCompat.isL()) { + Intent intent = activity.getIntent(); + ApplicationInfo applicationInfo = baseContext.getApplicationInfo(); + PackageManager packageManager = activity.getPackageManager(); + + if (intent != null && activity.isTaskRoot()) { + try { + String taskDescriptionLabel = TaskDescriptionCompat.getTaskDescriptionLabel(BActivityThread.getUserId(), applicationInfo.loadLabel(packageManager)); + + Bitmap icon = null; + Drawable activityIcon = getActivityIcon(activity); + if (activityIcon != null) { + ActivityManager activityManager = (ActivityManager) baseContext.getSystemService(Context.ACTIVITY_SERVICE); + + int iconSize = activityManager.getLauncherLargeIconSize(); + icon = DrawableUtils.drawableToBitmap(activityIcon, iconSize, iconSize); + } + activity.setTaskDescription(new ActivityManager.TaskDescription(taskDescriptionLabel, icon)); + } catch (Throwable e) { + e.printStackTrace(); + } + } + } + } + + private static Drawable getActivityIcon(Activity activity) { + PackageManager packageManager = activity.getPackageManager(); + try { + Drawable icon = packageManager.getActivityIcon(activity.getComponentName()); + if (icon != null) { + return icon; + } + } catch (PackageManager.NameNotFoundException ignore) { } + + ApplicationInfo applicationInfo = activity.getApplicationInfo(); + return applicationInfo.loadIcon(packageManager); + } +} \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityManagerCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityManagerCompat.java new file mode 100644 index 0000000..f59b601 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ActivityManagerCompat.java @@ -0,0 +1,55 @@ +package com.vcore.utils.compat; + +import android.app.Activity; +import android.content.Intent; +import android.os.IBinder; + +import black.android.app.ActivityManagerNative; +import black.android.app.IActivityManager; +import black.android.app.IActivityManagerL; +import black.android.app.IActivityManagerN; + +public class ActivityManagerCompat { + /** + * Type for IActivityManager.getIntentSender: this PendingIntent is + * for a startActivity operation. + */ + public static final int INTENT_SENDER_ACTIVITY = 2; + + public static final int START_FLAG_DEBUG = 1<<1; + public static final int START_FLAG_TRACK_ALLOCATION = 1<<2; + public static final int START_FLAG_NATIVE_DEBUGGING = 1<<3; + + public static void finishActivity(IBinder token, int code, Intent data) { + if (BuildCompat.isN()) { + IActivityManagerN.finishActivity.call(ActivityManagerNative.getDefault.call(), token, code, data, 0); + } else if (BuildCompat.isL()) { + IActivityManagerL.finishActivity.call(ActivityManagerNative.getDefault.call(), token, code, data, false); + } + } + + public static void setActivityOrientation(Activity activity, int orientation) { + try { + activity.setRequestedOrientation(orientation); + } catch (Throwable e) { + e.printStackTrace(); + // Samsung is WindowManager.setRequestedOrientation + Activity parent = black.android.app.Activity.mParent.get(activity); + while (true) { + Activity tmp = black.android.app.Activity.mParent.get(parent); + if (tmp != null) { + parent = tmp; + } else { + break; + } + } + + IBinder token = black.android.app.Activity.mToken.get(parent); + try { + IActivityManager.setRequestedOrientation.call(ActivityManagerNative.getDefault.call(), token, orientation); + } catch (Throwable ex) { + ex.printStackTrace(); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ApplicationThreadCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ApplicationThreadCompat.java new file mode 100644 index 0000000..d020e7d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ApplicationThreadCompat.java @@ -0,0 +1,16 @@ +package com.vcore.utils.compat; + +import android.os.IBinder; +import android.os.IInterface; + +import black.android.app.ApplicationThreadNative; +import black.android.app.IApplicationThread; + +public class ApplicationThreadCompat { + public static IInterface asInterface(IBinder binder) { + if (BuildCompat.isOreo()) { + return IApplicationThread.Stub.asInterface.call(binder); + } + return ApplicationThreadNative.asInterface.call(binder); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BuildCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BuildCompat.java new file mode 100644 index 0000000..41a1367 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BuildCompat.java @@ -0,0 +1,132 @@ +package com.vcore.utils.compat; + +import android.os.Build; + +public class BuildCompat { + + // 14 + public static boolean isU() { + return Build.VERSION.SDK_INT >= 34 || (Build.VERSION.SDK_INT >= 33 && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 13 + public static boolean isT() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.S && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 12 + public static boolean isS() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.S || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 11 + public static boolean isR() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.R || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 10 + public static boolean isQ() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 9 + public static boolean isPie() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.P || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 8 + public static boolean isOreo() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.O || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 7 + public static boolean isN() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.N || (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M && Build.VERSION.PREVIEW_SDK_INT == 1); + } + + // 6 + public static boolean isM() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.M; + } + + // 5 + public static boolean isL() { + return Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP; + } + + public static boolean isSamsung() { + return "samsung".equalsIgnoreCase(Build.BRAND) || "samsung".equalsIgnoreCase(Build.MANUFACTURER); + } + + public static boolean isEMUI() { + if (Build.DISPLAY.toUpperCase().startsWith("EMUI")) { + return true; + } + + String property = SystemPropertiesCompat.get("ro.build.version.emui"); + return property != null && property.contains("EmotionUI"); + } + + public static boolean isMIUI() { + return SystemPropertiesCompat.getInt("ro.miui.ui.version.code", 0) > 0; + } + + public static boolean isFlyme() { + return Build.DISPLAY.toLowerCase().contains("flyme"); + } + + public static boolean isColorOS() { + return SystemPropertiesCompat.isExist("ro.build.version.opporom") || SystemPropertiesCompat.isExist("ro.rom.different.version"); + } + + public static boolean is360UI() { + String property = SystemPropertiesCompat.get("ro.build.uiversion"); + return property != null && property.toUpperCase().contains("360UI"); + } + + public static boolean isLetv() { + return Build.MANUFACTURER.equalsIgnoreCase("Letv"); + } + + public static boolean isVivo() { + return SystemPropertiesCompat.isExist("ro.vivo.os.build.display.id"); + } + + private static ROMType sRomType; + public static ROMType getROMType() { + if (sRomType == null) { + if (isEMUI()) { + sRomType = ROMType.EMUI; + } else if (isMIUI()) { + sRomType = ROMType.MIUI; + } else if (isFlyme()) { + sRomType = ROMType.FLYME; + } else if (isColorOS()) { + sRomType = ROMType.COLOR_OS; + } else if (is360UI()) { + sRomType = ROMType._360; + } else if (isLetv()) { + sRomType = ROMType.LETV; + } else if (isVivo()) { + sRomType = ROMType.VIVO; + } else if (isSamsung()) { + sRomType = ROMType.SAMSUNG; + } else { + sRomType = ROMType.OTHER; + } + } + return sRomType; + } + + public enum ROMType { + EMUI, + MIUI, + FLYME, + COLOR_OS, + LETV, + VIVO, + _360, + SAMSUNG, + OTHER + } +} \ No newline at end of file diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BundleCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BundleCompat.java new file mode 100644 index 0000000..a496bb3 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/BundleCompat.java @@ -0,0 +1,36 @@ +package com.vcore.utils.compat; + +import android.content.Intent; +import android.os.Build; +import android.os.Bundle; +import android.os.IBinder; + +public class BundleCompat { + public static IBinder getBinder(Bundle bundle, String key) { + if (Build.VERSION.SDK_INT >= 18) { + return bundle.getBinder(key); + } + return black.android.os.Bundle.getIBinder.call(bundle, key); + } + + public static void putBinder(Bundle bundle, String key, IBinder value) { + if (Build.VERSION.SDK_INT >= 18) { + bundle.putBinder(key, value); + } + black.android.os.Bundle.putIBinder.call(bundle, key, value); + } + + public static void putBinder(Intent intent, String key, IBinder value) { + Bundle bundle = new Bundle(); + putBinder(bundle, "binder", value); + intent.putExtra(key, bundle); + } + + public static IBinder getBinder(Intent intent, String key) { + Bundle bundle = intent.getBundleExtra(key); + if (bundle != null) { + return getBinder(bundle, "binder"); + } + return null; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContentProviderCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContentProviderCompat.java new file mode 100644 index 0000000..24095b8 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContentProviderCompat.java @@ -0,0 +1,67 @@ +package com.vcore.utils.compat; + +import android.content.ContentProviderClient; +import android.content.Context; +import android.net.Uri; +import android.os.Build; +import android.os.Build.VERSION; +import android.os.Bundle; +import android.os.RemoteException; +import android.os.SystemClock; + +public class ContentProviderCompat { + public static Bundle call(Context context, Uri uri, String method, String arg, Bundle extras, int retryCount) throws IllegalAccessException { + if (VERSION.SDK_INT < Build.VERSION_CODES.JELLY_BEAN_MR1) { + return context.getContentResolver().call(uri, method, arg, extras); + } + + ContentProviderClient client = acquireContentProviderClientRetry(context, uri, retryCount); + try { + if (client == null) { + throw new IllegalAccessException(); + } + return client.call(method, arg, extras); + } catch (RemoteException e) { + throw new IllegalAccessException(e.getMessage()); + } finally { + releaseQuietly(client); + } + } + + private static ContentProviderClient acquireContentProviderClient(Context context, Uri uri) { + try { + if (VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN) { + return context.getContentResolver().acquireUnstableContentProviderClient(uri); + } + return context.getContentResolver().acquireContentProviderClient(uri); + } catch (SecurityException e) { + e.printStackTrace(); + } + return null; + } + + public static ContentProviderClient acquireContentProviderClientRetry(Context context, Uri uri, int retryCount) { + ContentProviderClient client = acquireContentProviderClient(context, uri); + if (client == null) { + int retry = 0; + while (retry < retryCount && client == null) { + SystemClock.sleep(400); + retry++; + client = acquireContentProviderClient(context, uri); + } + } + return client; + } + + private static void releaseQuietly(ContentProviderClient client) { + if (client != null) { + try { + if (VERSION.SDK_INT >= Build.VERSION_CODES.N) { + client.close(); + } else { + client.release(); + } + } catch (Exception ignored) { } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContextCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContextCompat.java new file mode 100644 index 0000000..3ec7823 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ContextCompat.java @@ -0,0 +1,57 @@ +package com.vcore.utils.compat; + +import android.content.Context; +import android.content.ContextWrapper; + +import black.android.app.ContextImpl; +import black.android.app.ContextImplKitkat; +import black.android.content.AttributionSource; +import black.android.content.AttributionSourceState; +import black.android.content.ContentResolver; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; + +public class ContextCompat { + public static final String TAG = "ContextCompat"; + + public static void fixAttributionSourceState(Object obj, int uid) { + Object mAttributionSourceState; + if (obj != null && AttributionSource.mAttributionSourceState != null) { + mAttributionSourceState = AttributionSource.mAttributionSourceState.get(obj); + + AttributionSourceState.packageName.set(mAttributionSourceState, BlackBoxCore.getHostPkg()); + AttributionSourceState.uid.set(mAttributionSourceState, uid); + fixAttributionSourceState(AttributionSource.getNext.call(obj), uid); + } + } + + public static void fix(Context context) { + try { + int deep = 0; + while (context instanceof ContextWrapper) { + context = ((ContextWrapper) context).getBaseContext(); + deep++; + if (deep >= 10) { + return; + } + } + + ContextImpl.mPackageManager.set(context, null); + try { + context.getPackageManager(); + } catch (Throwable e) { + e.printStackTrace(); + } + + ContextImpl.mBasePackageName.set(context, BlackBoxCore.getHostPkg()); + ContextImplKitkat.mOpPackageName.set(context, BlackBoxCore.getHostPkg()); + ContentResolver.mPackageName.set(context.getContentResolver(), BlackBoxCore.getHostPkg()); + + if (BuildCompat.isS()) { + fixAttributionSourceState(ContextImpl.getAttributionSource.call(context), BActivityThread.getBUid()); + } + } catch (Exception e) { + e.printStackTrace(); + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/PackageParserCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/PackageParserCompat.java new file mode 100644 index 0000000..226e00b --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/PackageParserCompat.java @@ -0,0 +1,69 @@ +package com.vcore.utils.compat; + +import static android.os.Build.VERSION_CODES.LOLLIPOP; +import static android.os.Build.VERSION_CODES.LOLLIPOP_MR1; +import static android.os.Build.VERSION_CODES.M; +import static android.os.Build.VERSION_CODES.N; + +import android.content.pm.PackageParser; +import android.content.pm.PackageParser.Package; +import android.os.Build; +import android.util.DisplayMetrics; + +import java.io.File; + +import black.android.content.pm.PackageParserLollipop; +import black.android.content.pm.PackageParserLollipop22; +import black.android.content.pm.PackageParserMarshmallow; +import black.android.content.pm.PackageParserNougat; +import black.android.content.pm.PackageParserPie; +import com.vcore.BlackBoxCore; + +public class PackageParserCompat { + private static final int API_LEVEL = Build.VERSION.SDK_INT; + + public static PackageParser createParser() { + if (BuildCompat.isQ()) { + PackageParser packageParser = PackageParserPie._new.newInstance(); + packageParser.setCallback(new PackageParser.CallbackImpl(BlackBoxCore.getPackageManager())); + return packageParser; + } else if (API_LEVEL >= 28) { + return PackageParserPie._new.newInstance(); + } else if (API_LEVEL >= M) { + return PackageParserMarshmallow._new.newInstance(); + } else if (API_LEVEL >= LOLLIPOP_MR1) { + return PackageParserLollipop22._new.newInstance(); + } else if (API_LEVEL >= LOLLIPOP) { + return PackageParserLollipop._new.newInstance(); + } + return null; + } + + public static Package parsePackage(PackageParser parser, File packageFile, int flags) { + if (BuildCompat.isPie()) { + return PackageParserPie.parsePackage.call(parser, packageFile, flags); + } else if (API_LEVEL >= M) { + return PackageParserMarshmallow.parsePackage.call(parser, packageFile, flags); + } else if (API_LEVEL >= LOLLIPOP_MR1) { + return PackageParserLollipop22.parsePackage.call(parser, packageFile, flags); + } else if (API_LEVEL >= LOLLIPOP) { + return PackageParserLollipop.parsePackage.call(parser, packageFile, flags); + } + return black.android.content.pm.PackageParser.parsePackage.call(parser, packageFile, null, new DisplayMetrics(), flags); + } + + public static void collectCertificates(PackageParser parser, Package p, int flags) { + if (BuildCompat.isPie()) { + PackageParserPie.collectCertificates.call(p, true); + } else if (API_LEVEL >= N) { + PackageParserNougat.collectCertificates.call(p, flags); + } else if (API_LEVEL >= M) { + PackageParserMarshmallow.collectCertificates.call(parser, p, flags); + } else if (API_LEVEL >= LOLLIPOP_MR1) { + PackageParserLollipop22.collectCertificates.call(parser, p, flags); + } else if (API_LEVEL >= LOLLIPOP) { + PackageParserLollipop.collectCertificates.call(parser, p, flags); + } + black.android.content.pm.PackageParser.collectCertificates.call(parser, p, flags); + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ParceledListSliceCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ParceledListSliceCompat.java new file mode 100644 index 0000000..3a30ad0 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/ParceledListSliceCompat.java @@ -0,0 +1,22 @@ +package com.vcore.utils.compat; + +import java.util.List; + +import black.android.content.pm.ParceledListSlice; + +public class ParceledListSliceCompat { + public static Object create(List list) { + Object slice = ParceledListSlice._new1.newInstance(list); + if (slice != null) { + return slice; + } else { + slice = ParceledListSlice._new0.newInstance(); + } + + for (Object item : list) { + ParceledListSlice.append.call(slice, item); + } + ParceledListSlice.setLastSlice.call(slice, true); + return slice; + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/StrictModeCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/StrictModeCompat.java new file mode 100644 index 0000000..cd91a98 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/StrictModeCompat.java @@ -0,0 +1,25 @@ +package com.vcore.utils.compat; + +import black.android.os.StrictMode; + +public class StrictModeCompat { + public static final int DETECT_VM_FILE_URI_EXPOSURE = StrictMode.DETECT_VM_FILE_URI_EXPOSURE.get() == null ? + (0x20 << 8) : StrictMode.DETECT_VM_FILE_URI_EXPOSURE.get(); + + public static final int PENALTY_DEATH_ON_FILE_URI_EXPOSURE = StrictMode.PENALTY_DEATH_ON_FILE_URI_EXPOSURE.get() == null ? + (0x04 << 24) : StrictMode.PENALTY_DEATH_ON_FILE_URI_EXPOSURE.get(); + + public static void disableDeathOnFileUriExposure() { + try { + StrictMode.disableDeathOnFileUriExposure.call(); + } catch (Throwable e) { + try { + int sVmPolicyMask = StrictMode.sVmPolicyMask.get(); + sVmPolicyMask &= ~(DETECT_VM_FILE_URI_EXPOSURE | PENALTY_DEATH_ON_FILE_URI_EXPOSURE); + StrictMode.sVmPolicyMask.set(sVmPolicyMask); + } catch (Throwable e2) { + e2.printStackTrace(); + } + } + } +} diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/SystemPropertiesCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/SystemPropertiesCompat.java new file mode 100644 index 0000000..5ca316d --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/SystemPropertiesCompat.java @@ -0,0 +1,38 @@ +package com.vcore.utils.compat; + +import android.text.TextUtils; + +import black.android.os.SystemProperties; + +public class SystemPropertiesCompat { + public static String get(String key, String def) { + try { + return SystemProperties.get0.call(key, def); + } catch (Exception e) { + e.printStackTrace(); + } + return def; + } + + public static String get(String key) { + try { + return SystemProperties.get1.call(key); + } catch (Exception e) { + e.printStackTrace(); + } + return null; + } + + public static int getInt(String key, int def) { + try { + return SystemProperties.getInt.call(key, def); + } catch (Exception e) { + e.printStackTrace(); + } + return def; + } + + public static boolean isExist(String key) { + return !TextUtils.isEmpty(get(key)); + } +} diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/TaskDescriptionCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/TaskDescriptionCompat.java similarity index 83% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/TaskDescriptionCompat.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/TaskDescriptionCompat.java index 6e00e9e..27adf47 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/TaskDescriptionCompat.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/TaskDescriptionCompat.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.utils.compat; +package com.vcore.utils.compat; import android.app.ActivityManager; import android.content.Context; @@ -8,25 +8,28 @@ import java.util.Locale; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.app.BActivityThread; -import top.niunaijun.blackbox.utils.DrawableUtils; +import com.vcore.BlackBoxCore; +import com.vcore.app.BActivityThread; +import com.vcore.utils.DrawableUtils; public class TaskDescriptionCompat { public static ActivityManager.TaskDescription fix(ActivityManager.TaskDescription td) { String label = td.getLabel(); Bitmap icon = td.getIcon(); - if (label != null && icon != null) + if (label != null && icon != null) { return td; + } label = getTaskDescriptionLabel(BActivityThread.getUserId(), getApplicationLabel()); Drawable drawable = getApplicationIcon(); - if (drawable == null) + if (drawable == null) { return td; + } ActivityManager am = (ActivityManager) BlackBoxCore.getContext().getSystemService(Context.ACTIVITY_SERVICE); int iconSize = am.getLauncherLargeIconSize(); + icon = DrawableUtils.drawableToBitmap(drawable, iconSize, iconSize); td = new ActivityManager.TaskDescription(label, icon, td.getPrimaryColor()); return td; @@ -40,7 +43,7 @@ private static CharSequence getApplicationLabel() { try { PackageManager pm = BlackBoxCore.getPackageManager(); return pm.getApplicationLabel(pm.getApplicationInfo(BActivityThread.getAppPackageName(), 0)); - } catch (PackageManager.NameNotFoundException e) { + } catch (PackageManager.NameNotFoundException ignore) { return null; } } diff --git a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/XposedParserCompat.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/XposedParserCompat.java similarity index 87% rename from 520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/XposedParserCompat.java rename to 520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/XposedParserCompat.java index a50a3f2..1277b97 100644 --- a/520ApkBox/Bcore/src/main/java/top/niunaijun/blackbox/utils/compat/XposedParserCompat.java +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/compat/XposedParserCompat.java @@ -1,4 +1,4 @@ -package top.niunaijun.blackbox.utils.compat; +package com.vcore.utils.compat; import android.content.pm.ApplicationInfo; import android.content.pm.PackageManager; @@ -11,20 +11,11 @@ import java.util.zip.ZipEntry; import java.util.zip.ZipFile; -import top.niunaijun.blackbox.BlackBoxCore; -import top.niunaijun.blackbox.entity.pm.InstalledModule; -import top.niunaijun.blackbox.utils.CloseUtils; +import com.vcore.BlackBoxCore; +import com.vcore.entity.pm.InstalledModule; +import com.vcore.utils.CloseUtils; -/** - * Created by Milk on 5/2/21. - * * ∧_∧ - * (`・ω・∥ - * 丶 つ0 - * しーJ - * 此处无Bug - */ public class XposedParserCompat { - public static InstalledModule parseModule(ApplicationInfo applicationInfo) { try { PackageManager packageManager = BlackBoxCore.getPackageManager(); @@ -71,10 +62,12 @@ private static String getInputStreamContent(InputStream stream) { StringBuilder builder = new StringBuilder(); try { reader = new BufferedReader(new InputStreamReader(stream)); + String line; while ((line = reader.readLine()) != null) { - if (line.startsWith("#")) + if (line.startsWith("#")) { continue; + } builder.append(line).append("\n"); } } catch (Exception e) { diff --git a/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/provider/ProviderCall.java b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/provider/ProviderCall.java new file mode 100644 index 0000000..39993e5 --- /dev/null +++ b/520ApkBox-NewBlackbox/Bcore/src/main/java/com/vcore/utils/provider/ProviderCall.java @@ -0,0 +1,24 @@ +package com.vcore.utils.provider; + +import android.content.Context; +import android.net.Uri; +import android.os.Bundle; + +import com.vcore.BlackBoxCore; +import com.vcore.utils.compat.ContentProviderCompat; + +public class ProviderCall { + public static Bundle callSafely(String authority, String methodName, String arg, Bundle bundle) { + try { + return call(authority, BlackBoxCore.getContext(), methodName, arg, bundle, 5); + } catch (IllegalAccessException e) { + e.printStackTrace(); + } + return null; + } + + public static Bundle call(String authority, Context context, String method, String arg, Bundle bundle, int retryCount) throws IllegalAccessException { + Uri uri = Uri.parse("content://" + authority); + return ContentProviderCompat.call(context, uri, method, arg, bundle, retryCount); + } +} diff --git a/520ApkBox/BCore/src/main/res/drawable/ic_launcher.png b/520ApkBox-NewBlackbox/Bcore/src/main/res/drawable/ic_launcher.png similarity index 100% rename from 520ApkBox/BCore/src/main/res/drawable/ic_launcher.png rename to 520ApkBox-NewBlackbox/Bcore/src/main/res/drawable/ic_launcher.png diff --git a/520ApkBox/BCore/src/main/res/layout/activity_launcher.xml b/520ApkBox-NewBlackbox/Bcore/src/main/res/layout/activity_launcher.xml similarity index 100% rename from 520ApkBox/BCore/src/main/res/layout/activity_launcher.xml rename to 520ApkBox-NewBlackbox/Bcore/src/main/res/layout/activity_launcher.xml diff --git a/520ApkBox/BCore/src/main/res/values/strings.xml b/520ApkBox-NewBlackbox/Bcore/src/main/res/values/strings.xml similarity index 100% rename from 520ApkBox/BCore/src/main/res/values/strings.xml rename to 520ApkBox-NewBlackbox/Bcore/src/main/res/values/strings.xml diff --git a/520ApkBox/BCore/src/main/res/values/styles.xml b/520ApkBox-NewBlackbox/Bcore/src/main/res/values/styles.xml similarity index 88% rename from 520ApkBox/BCore/src/main/res/values/styles.xml rename to 520ApkBox-NewBlackbox/Bcore/src/main/res/values/styles.xml index 4742f90..c7ffa34 100644 --- a/520ApkBox/BCore/src/main/res/values/styles.xml +++ b/520ApkBox-NewBlackbox/Bcore/src/main/res/values/styles.xml @@ -4,6 +4,5 @@ true - - + - \ No newline at end of file diff --git a/520ApkBox/app/src/main/res/values/strings.xml b/520ApkBox/app/src/main/res/values/strings.xml deleted file mode 100644 index e5f8fdc..0000000 --- a/520ApkBox/app/src/main/res/values/strings.xml +++ /dev/null @@ -1,2 +0,0 @@ - - \ No newline at end of file diff --git a/520ApkBox/app/src/main/res/values/themes.xml b/520ApkBox/app/src/main/res/values/themes.xml deleted file mode 100644 index abe3adf..0000000 --- a/520ApkBox/app/src/main/res/values/themes.xml +++ /dev/null @@ -1,4 +0,0 @@ - - - + \ No newline at end of file diff --git a/520apkbox-SpaceCore/app/src/main/res/values/colors.xml b/520apkbox-SpaceCore/app/src/main/res/values/colors.xml new file mode 100644 index 0000000..f8c6127 --- /dev/null +++ b/520apkbox-SpaceCore/app/src/main/res/values/colors.xml @@ -0,0 +1,10 @@ + + + #FFBB86FC + #FF6200EE + #FF3700B3 + #FF03DAC5 + #FF018786 + #FF000000 + #FFFFFFFF + \ No newline at end of file diff --git a/520apkbox-SpaceCore/app/src/main/res/values/strings.xml b/520apkbox-SpaceCore/app/src/main/res/values/strings.xml new file mode 100644 index 0000000..6fc0701 --- /dev/null +++ b/520apkbox-SpaceCore/app/src/main/res/values/strings.xml @@ -0,0 +1,4 @@ + + 520ApkBox + Permission request is denied. Please grant permission manually in settings + \ No newline at end of file diff --git a/520apkbox-SpaceCore/app/src/main/res/values/themes.xml b/520apkbox-SpaceCore/app/src/main/res/values/themes.xml new file mode 100644 index 0000000..5cfaffc --- /dev/null +++ b/520apkbox-SpaceCore/app/src/main/res/values/themes.xml @@ -0,0 +1,4 @@ + + +