From c65f71f7f1e0734bf32136c741e679d87b0b2f86 Mon Sep 17 00:00:00 2001 From: Fox2Code Date: Sat, 5 Feb 2022 16:11:32 +0100 Subject: [PATCH] Rewrite module install script, auto detect if a patch is needed on remote modules. --- .../com/fox2code/mmm/ActionButtonType.java | 5 +--- .../main/java/com/fox2code/mmm/Constants.java | 1 - .../java/com/fox2code/mmm/MainActivity.java | 1 + .../com/fox2code/mmm/NotificationType.java | 4 +-- .../mmm/androidacy/AndroidacyWebAPI.java | 5 ++-- .../mmm/installer/InstallerActivity.java | 29 +++++++++++++++++-- .../com/fox2code/mmm/repo/RepoManager.java | 2 +- .../java/com/fox2code/mmm/utils/Files.java | 12 +++----- .../com/fox2code/mmm/utils/IntentHelper.java | 13 ++------- 9 files changed, 41 insertions(+), 31 deletions(-) diff --git a/app/src/main/java/com/fox2code/mmm/ActionButtonType.java b/app/src/main/java/com/fox2code/mmm/ActionButtonType.java index b96e8c1..03395dc 100644 --- a/app/src/main/java/com/fox2code/mmm/ActionButtonType.java +++ b/app/src/main/java/com/fox2code/mmm/ActionButtonType.java @@ -85,9 +85,6 @@ public enum ActionButtonType { // Re-render each time in cse of config changes desc = markwon.render(markwon.parse(localModuleInfo.updateChangeLog)); } - noPatch = true; - } else { - noPatch = false; } if (desc == null || desc.length() == 0) { @@ -103,7 +100,7 @@ public enum ActionButtonType { R.string.update_module : R.string.install_module, (x, y) -> { String updateZipChecksum = moduleHolder.getUpdateZipChecksum(); IntentHelper.openInstaller(button.getContext(), updateZipUrl, - moduleInfo.name, moduleInfo.config, updateZipChecksum, noPatch); + moduleInfo.name, moduleInfo.config, updateZipChecksum); }); } int dim5dp = CompatDisplay.dpToPixel(5); diff --git a/app/src/main/java/com/fox2code/mmm/Constants.java b/app/src/main/java/com/fox2code/mmm/Constants.java index 071281c..ec829db 100644 --- a/app/src/main/java/com/fox2code/mmm/Constants.java +++ b/app/src/main/java/com/fox2code/mmm/Constants.java @@ -14,7 +14,6 @@ public class Constants { public static final String EXTRA_INSTALL_NAME = "extra_install_name"; public static final String EXTRA_INSTALL_CONFIG = "extra_install_config"; public static final String EXTRA_INSTALL_CHECKSUM = "extra_install_checksum"; - public static final String EXTRA_INSTALL_NO_PATCH = "extra_install_no_patch"; public static final String EXTRA_INSTALL_NO_EXTENSIONS = "extra_install_no_extensions"; public static final String EXTRA_INSTALL_TEST_ROOTLESS = "extra_install_test_rootless"; public static final String EXTRA_ANDROIDACY_ALLOW_INSTALL = "extra_androidacy_allow_install"; diff --git a/app/src/main/java/com/fox2code/mmm/MainActivity.java b/app/src/main/java/com/fox2code/mmm/MainActivity.java index e47153a..96798b5 100644 --- a/app/src/main/java/com/fox2code/mmm/MainActivity.java +++ b/app/src/main/java/com/fox2code/mmm/MainActivity.java @@ -262,6 +262,7 @@ public class MainActivity extends CompatActivity implements SwipeRefreshLayout.O if (!NotificationType.NO_INTERNET.shouldRemove()) { this.moduleViewListBuilder.addNotification(NotificationType.NO_INTERNET); } + RepoManager.getINSTANCE().updateEnabledStates(); this.moduleViewListBuilder.appendRemoteModules(); this.moduleViewListBuilder.applyTo(moduleList, moduleViewAdapter); },"Repo update thread").start(); diff --git a/app/src/main/java/com/fox2code/mmm/NotificationType.java b/app/src/main/java/com/fox2code/mmm/NotificationType.java index abb9fe5..71fc825 100644 --- a/app/src/main/java/com/fox2code/mmm/NotificationType.java +++ b/app/src/main/java/com/fox2code/mmm/NotificationType.java @@ -89,7 +89,7 @@ public enum NotificationType implements NotificationTypeCst { } else { IntentHelper.openInstaller(compatActivity, d.getAbsolutePath(), compatActivity.getString( - R.string.local_install_title), null, null, false, + R.string.local_install_title), null, null, BuildConfig.DEBUG && // Use debug mode if no root InstallerInitializer.peekMagiskPath() == null); } @@ -102,7 +102,7 @@ public enum NotificationType implements NotificationTypeCst { } else if (s == IntentHelper.RESPONSE_URL) { IntentHelper.openInstaller(compatActivity, u.toString(), compatActivity.getString( - R.string.remote_install_title), null, null, false, + R.string.remote_install_title), null, null, BuildConfig.DEBUG && // Use debug mode if no root InstallerInitializer.peekMagiskPath() == null); } diff --git a/app/src/main/java/com/fox2code/mmm/androidacy/AndroidacyWebAPI.java b/app/src/main/java/com/fox2code/mmm/androidacy/AndroidacyWebAPI.java index 1c6e4ab..28cd3ed 100644 --- a/app/src/main/java/com/fox2code/mmm/androidacy/AndroidacyWebAPI.java +++ b/app/src/main/java/com/fox2code/mmm/androidacy/AndroidacyWebAPI.java @@ -88,9 +88,8 @@ public class AndroidacyWebAPI { Uri uri = Uri.parse(moduleUrl); if (uri.getScheme().equals("https") && uri.getHost().endsWith(".androidacy.com")) { this.activity.backOnResume = true; - IntentHelper.openInstaller( - this.activity, moduleUrl, installTitle, - null, checksum, true); + IntentHelper.openInstaller(this.activity, + moduleUrl, installTitle, null, checksum); } else { this.activity.forceBackPressed(); } diff --git a/app/src/main/java/com/fox2code/mmm/installer/InstallerActivity.java b/app/src/main/java/com/fox2code/mmm/installer/InstallerActivity.java index 5c57e12..7519a79 100644 --- a/app/src/main/java/com/fox2code/mmm/installer/InstallerActivity.java +++ b/app/src/main/java/com/fox2code/mmm/installer/InstallerActivity.java @@ -31,10 +31,13 @@ import com.topjohnwu.superuser.Shell; import com.topjohnwu.superuser.internal.UiThreadHandler; import com.topjohnwu.superuser.io.SuFile; +import java.io.ByteArrayInputStream; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import java.io.OutputStream; +import java.util.zip.ZipEntry; +import java.util.zip.ZipInputStream; public class InstallerActivity extends CompatActivity { private static final String TAG = "InstallerActivity"; @@ -59,7 +62,6 @@ public class InstallerActivity extends CompatActivity { final String target; final String name; final String checksum; - final boolean noPatch; final boolean noExtensions; final boolean rootless; // Should we allow 3rd part app to install modules? @@ -72,7 +74,6 @@ public class InstallerActivity extends CompatActivity { target = intent.getStringExtra(Constants.EXTRA_INSTALL_PATH); name = intent.getStringExtra(Constants.EXTRA_INSTALL_NAME); checksum = intent.getStringExtra(Constants.EXTRA_INSTALL_CHECKSUM); - noPatch = intent.getBooleanExtra(Constants.EXTRA_INSTALL_NO_PATCH, false); noExtensions = intent.getBooleanExtra(// Allow intent to disable extensions Constants.EXTRA_INSTALL_NO_EXTENSIONS, false); rootless = intent.getBooleanExtra(// For debug only @@ -140,7 +141,31 @@ public class InstallerActivity extends CompatActivity { } } if (this.canceled) return; + Files.fixJavaZipHax(rawModule); + boolean noPatch = false; + boolean isModule = false; + errMessage = "File is not a valid zip file"; + try (ZipInputStream zipInputStream = new ZipInputStream( + new ByteArrayInputStream(rawModule))) { + ZipEntry zipEntry; + while ((zipEntry = zipInputStream.getNextEntry()) != null) { + String entryName = zipEntry.getName(); + if (entryName.equals("module.prop")) { + noPatch = true; + isModule = true; + break; + } else if (entryName.endsWith("/module.prop")) { + isModule = true; + } + } + } + if (!isModule) { + this.setInstallStateFinished(false, + "! File is not a valid magisk module", ""); + return; + } if (noPatch) { + errMessage = "Failed to save module zip"; try (OutputStream outputStream = new FileOutputStream(moduleCache)) { outputStream.write(rawModule); outputStream.flush(); diff --git a/app/src/main/java/com/fox2code/mmm/repo/RepoManager.java b/app/src/main/java/com/fox2code/mmm/repo/RepoManager.java index 97d4db3..96917eb 100644 --- a/app/src/main/java/com/fox2code/mmm/repo/RepoManager.java +++ b/app/src/main/java/com/fox2code/mmm/repo/RepoManager.java @@ -69,8 +69,8 @@ public final class RepoManager { this.modules = new HashMap<>(); // We do not have repo list config yet. this.addRepoData(MAGISK_ALT_REPO); - this.addAndroidacyRepoData(); this.addRepoData(MAGISK_REPO); + this.addAndroidacyRepoData(); // Populate default cache for (RepoData repoData:this.repoData.values()) { for (RepoModule repoModule:repoData.moduleHashMap.values()) { diff --git a/app/src/main/java/com/fox2code/mmm/utils/Files.java b/app/src/main/java/com/fox2code/mmm/utils/Files.java index 0a129b8..dea2c20 100644 --- a/app/src/main/java/com/fox2code/mmm/utils/Files.java +++ b/app/src/main/java/com/fox2code/mmm/utils/Files.java @@ -64,17 +64,13 @@ public class Files { return buffer.toByteArray(); } - - public static byte[] patchModuleSimple(byte[] bytes) throws IOException { - ByteArrayOutputStream byteArrayOutputStream = - new ByteArrayOutputStream((int) (bytes.length * 1.2F)); - patchModuleSimple(bytes, byteArrayOutputStream); - return byteArrayOutputStream.toByteArray(); + public static void fixJavaZipHax(byte[] bytes) { + if (bytes.length > 8 && bytes[0x6] == 0x0 && bytes[0x7] == 0x0 && bytes[0x8] == 0x8) + bytes[0x7] = 0x8; // Known hax to prevent java zip file read } public static void patchModuleSimple(byte[] bytes,OutputStream outputStream) throws IOException { - if (bytes[0x6] == 0x0 && bytes[0x7] == 0x0 && bytes[0x8] == 0x8) bytes[0x7] = 0x8; - patchModuleSimple(new ByteArrayInputStream(bytes), outputStream); + fixJavaZipHax(bytes); patchModuleSimple(new ByteArrayInputStream(bytes), outputStream); } public static void patchModuleSimple(InputStream inputStream,OutputStream outputStream) throws IOException { diff --git a/app/src/main/java/com/fox2code/mmm/utils/IntentHelper.java b/app/src/main/java/com/fox2code/mmm/utils/IntentHelper.java index d0678ac..c10d62e 100644 --- a/app/src/main/java/com/fox2code/mmm/utils/IntentHelper.java +++ b/app/src/main/java/com/fox2code/mmm/utils/IntentHelper.java @@ -122,16 +122,11 @@ public class IntentHelper { public static void openInstaller(Context context, String url, String title, String config, String checksum) { - openInstaller(context, url, title, config, checksum, false, false); + openInstaller(context, url, title, config, checksum, false); } public static void openInstaller(Context context, String url, String title, String config, - String checksum, boolean noPatch) { - openInstaller(context, url, title, config, checksum, noPatch, false); - } - - public static void openInstaller(Context context, String url, String title, String config, - String checksum, boolean noPatch,boolean testDebug) { + String checksum,boolean testDebug) { try { Intent intent = new Intent(context, InstallerActivity.class); intent.setAction(Constants.INTENT_INSTALL_INTERNAL); @@ -142,8 +137,6 @@ public class IntentHelper { intent.putExtra(Constants.EXTRA_INSTALL_CONFIG, config); if (checksum != null && !checksum.isEmpty()) intent.putExtra(Constants.EXTRA_INSTALL_CHECKSUM, checksum); - if (noPatch) - intent.putExtra(Constants.EXTRA_INSTALL_NO_PATCH, true); if (testDebug && BuildConfig.DEBUG) intent.putExtra(Constants.EXTRA_INSTALL_TEST_ROOTLESS, true); startActivity(context, intent, true); @@ -234,7 +227,7 @@ public class IntentHelper { callback.onReceived(destination, null, RESPONSE_ERROR); return; } - Log.d("IntentHelper", "FilePicker returned " + uri.toString()); + Log.d("IntentHelper", "FilePicker returned " + uri); if ("http".equals(uri.getScheme()) || "https".equals(uri.getScheme())) { callback.onReceived(destination, uri, RESPONSE_URL);