fix(TikTok): Hook application context earlier to prevent crash (#588)

This commit is contained in:
LisoUseInAIKyrios 2024-03-18 04:21:16 +04:00 committed by GitHub
parent 74b6ab8712
commit 9ac2d63489
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
3 changed files with 57 additions and 33 deletions

View File

@ -5,14 +5,15 @@ import static app.revanced.integrations.shared.settings.BaseSettings.DEBUG_STACK
import static app.revanced.integrations.shared.settings.BaseSettings.DEBUG_TOAST_ON_ERROR;
import android.util.Log;
import androidx.annotation.NonNull;
import androidx.annotation.Nullable;
import app.revanced.integrations.shared.settings.BaseSettings;
import java.io.PrintWriter;
import java.io.StringWriter;
import app.revanced.integrations.shared.settings.BaseSettings;
public class Logger {
/**
@ -24,7 +25,7 @@ public class Logger {
/**
* @return For outer classes, this returns {@link Class#getSimpleName()}.
* For inner, static, or anonymous classes, this returns the simple name of the enclosing class.<br>
* For static, inner, or anonymous classes, this returns the simple name of the enclosing class.
* <br>
* For example, each of these classes return 'SomethingView':
* <code>
@ -38,13 +39,13 @@ public class Logger {
String fullClassName = selfClass.getName();
final int dollarSignIndex = fullClassName.indexOf('$');
if (dollarSignIndex == -1) {
return selfClass.getSimpleName(); // already an outer class
if (dollarSignIndex < 0) {
return selfClass.getSimpleName(); // Already an outer class.
}
// class is inner, static, or anonymous
// parse the simple name full name
// a class with no package returns index of -1, but incrementing gives index zero which is correct
// Class is inner, static, or anonymous.
// Parse the simple name full name.
// A class with no package returns index of -1, but incrementing gives index zero which is correct.
final int simpleClassNameStartIndex = fullClassName.lastIndexOf('.') + 1;
return fullClassName.substring(simpleClassNameStartIndex, dollarSignIndex);
}
@ -137,11 +138,19 @@ public class Logger {
}
/**
* Logging to use if {@link BaseSettings#DEBUG} or {@link Utils#context} may not be initialized.
* Always logs even if Debugging is not enabled.
* Logging to use if {@link BaseSettings#DEBUG} or {@link Utils#getContext()} may not be initialized.
* Normally this method should not be used.
*/
public static void initializationError(@NonNull Class<?> callingClass, @NonNull String message, @Nullable Exception ex) {
public static void initializationInfo(@NonNull Class<?> callingClass, @NonNull String message) {
Log.i(REVANCED_LOG_PREFIX + callingClass.getSimpleName(), message);
}
/**
* Logging to use if {@link BaseSettings#DEBUG} or {@link Utils#getContext()} may not be initialized.
* Normally this method should not be used.
*/
public static void initializationException(@NonNull Class<?> callingClass, @NonNull String message,
@Nullable Exception ex) {
Log.e(REVANCED_LOG_PREFIX + callingClass.getSimpleName(), message, ex);
}

View File

@ -54,13 +54,14 @@ public class Utils {
try {
final var packageName = Objects.requireNonNull(getContext()).getPackageName();
PackageManager packageManager = context.getPackageManager();
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU)
packageInfo = context.getPackageManager().getPackageInfo(
packageInfo = packageManager.getPackageInfo(
packageName,
PackageManager.PackageInfoFlags.of(0)
);
else
packageInfo = context.getPackageManager().getPackageInfo(
packageInfo = packageManager.getPackageInfo(
packageName,
0
);
@ -228,14 +229,23 @@ public class Utils {
public static Context getContext() {
if (context == null) {
Logger.initializationError(Utils.class, "Context is null, returning null!", null);
Logger.initializationException(Utils.class, "Context is null, returning null!", null);
}
return context;
}
public static void setContext(Context appContext) {
context = appContext;
Logger.printDebug(() -> "Set context: " + appContext); // Cannot log before context is set.
// In some apps like TikTok, the Setting classes can load in weird orders due to cyclic class dependencies.
// Calling the regular printDebug method here can cause a Settings context null pointer exception,
// even though the context is already set before the call.
//
// The initialization logger methods do not directly or indirectly
// reference the Context or any Settings and are unaffected by this problem.
//
// Info level also helps debug if a patch hook is called before
// the context is set since debug logging is off by default.
Logger.initializationInfo(Utils.class, "Set context: " + appContext);
}
public static void setClipboard(@NonNull String text) {
@ -280,7 +290,7 @@ public class Utils {
Objects.requireNonNull(messageToToast);
runOnMainThreadNowOrLater(() -> {
if (context == null) {
Logger.initializationError(Utils.class, "Cannot show toast (context is null): " + messageToToast, null);
Logger.initializationException(Utils.class, "Cannot show toast (context is null): " + messageToToast, null);
} else {
Logger.printDebug(() -> "Showing toast: " + messageToToast);
Toast.makeText(context, messageToToast, toastDuration).show();

View File

@ -1,32 +1,37 @@
package app.revanced.integrations.tiktok.spoof.sim;
import app.revanced.integrations.shared.Logger;
import app.revanced.integrations.tiktok.settings.Settings;
@SuppressWarnings("unused")
public class SpoofSimPatch {
public static boolean isEnable() {
return Settings.SIM_SPOOF.get();
}
public static String getCountryIso(String value) {
if (isEnable()) {
return Settings.SIM_SPOOF_ISO.get();
} else {
return value;
}
private static final Boolean ENABLED = Settings.SIM_SPOOF.get();
public static String getCountryIso(String value) {
if (ENABLED) {
String iso = Settings.SIM_SPOOF_ISO.get();
Logger.printDebug(() -> "Spoofing sim ISO from: " + value + " to: " + iso);
return iso;
}
return value;
}
public static String getOperator(String value) {
if (isEnable()) {
return Settings.SIMSPOOF_MCCMNC.get();
} else {
return value;
if (ENABLED) {
String mcc_mnc = Settings.SIMSPOOF_MCCMNC.get();
Logger.printDebug(() -> "Spoofing sim MCC-MNC from: " + value + " to: " + mcc_mnc);
return mcc_mnc;
}
return value;
}
public static String getOperatorName(String value) {
if (isEnable()) {
return Settings.SIMSPOOF_OP_NAME.get();
} else {
return value;
if (ENABLED) {
String operator = Settings.SIMSPOOF_OP_NAME.get();
Logger.printDebug(() -> "Spoofing sim operator from: " + value + " to: " + operator);
return operator;
}
return value;
}
}