diff --git a/app/src/main/java/app/revanced/integrations/shared/Logger.java b/app/src/main/java/app/revanced/integrations/shared/Logger.java
index f8c5c87e..25885050 100644
--- a/app/src/main/java/app/revanced/integrations/shared/Logger.java
+++ b/app/src/main/java/app/revanced/integrations/shared/Logger.java
@@ -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.
+ * For static, inner, or anonymous classes, this returns the simple name of the enclosing class.
*
* For example, each of these classes return 'SomethingView':
*
@@ -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);
}
diff --git a/app/src/main/java/app/revanced/integrations/shared/Utils.java b/app/src/main/java/app/revanced/integrations/shared/Utils.java
index f92c9cfd..a7fbfcbc 100644
--- a/app/src/main/java/app/revanced/integrations/shared/Utils.java
+++ b/app/src/main/java/app/revanced/integrations/shared/Utils.java
@@ -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();
diff --git a/app/src/main/java/app/revanced/integrations/tiktok/spoof/sim/SpoofSimPatch.java b/app/src/main/java/app/revanced/integrations/tiktok/spoof/sim/SpoofSimPatch.java
index 31145347..264bd893 100644
--- a/app/src/main/java/app/revanced/integrations/tiktok/spoof/sim/SpoofSimPatch.java
+++ b/app/src/main/java/app/revanced/integrations/tiktok/spoof/sim/SpoofSimPatch.java
@@ -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;
}
}