-
-
Notifications
You must be signed in to change notification settings - Fork 3.7k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
refactor: Config/Tests/misc rework (#3746)
* refactor: Config/Tests/misc rework Config is now propagated to ResValue instead of being a globally accessible instance that gets set each time a new Config is instantiated. The old way violted every principle of an instance and even a singleton. This caused working with Tests extremely error-prone, because the Config had to be carefully reset to default for each Test to get the expected behavior, and ResValue was only aware of the global instance. Now, only Main and BaseTest are calling new Config(). BaseTest provides a fresh Config for every Test which turns the boilerplate into something shorter, predictable and more robust. Config class is now encapsulated to give control over the values passed to it. Having both publically-modifyable fields and setters with the verfications was more of a dirty hack than proper coding principles. General-purpose XML utilities extracted from ResXmlUtils into XmlUtils in the brut.xml library. It contains Document creation, parsing and saving. In addition, it has a generic evaluateXPath method that's now used more widely wherever manual looping over nodes was used, like in some tests. ResXmlUtils reworked and cleaned, now takes advantage of XmlUtils. ResXmlUtils only retains methods relevant specifically to resource XMLs and Android Manifest. Minor tweaks and code cleanup in various classed like ApktoolProperties and the main work classes (Framework, ApkDecoder, ApkBuilder, etc.), as well as utility classes like AaptInvoker and OS. Fixed locks being held by certain ExtFiles to zips with loaded Directory, which prevented proper temp file cleanup during Test stage. ExternalEntityTest resources ("doctype") moved to aapt1 as it's an aapt1-only test. Overall, mainly a code refactor with no end-user changes, to make development less prone to errors. * fix framework parent check * make sure frameworkDirectory is never null * make sure frameworkDirectory is never null * style * retrieve Config only in ResBagValue and misc tweaks We actually don't need to pass Config explicitly to all ResValue subtypes. It's only needed by 3 subtypes of ResBagValue, so we get the Config via ResBagValue's mParent.getPackage().getConfig(). Encapsulate ResConfigFlags. Encapsulate ResID and make it a numeric and comparable type. Sort resource specs by resource ID in generatePublicXml. Duo is redundant, replace with Apache Common's Pair. ResIdValue is redundant, it's never actually instantiated. Tweak equals and hashCode overrides to standard formats. Misc style and variable name tweaks. * redundant explicit toString calls * Objects.hash is safer
- Loading branch information
1 parent
70a99d2
commit f6d568b
Showing
115 changed files
with
2,664 additions
and
3,233 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -23,9 +23,7 @@ | |
import brut.androlib.exceptions.OutDirExistsException; | ||
import brut.androlib.res.Framework; | ||
import brut.common.BrutException; | ||
import brut.directory.DirectoryException; | ||
import brut.directory.ExtFile; | ||
import brut.util.AaptManager; | ||
import brut.util.OSDetection; | ||
import org.apache.commons.cli.*; | ||
|
||
|
@@ -73,8 +71,8 @@ public static void main(String[] args) throws BrutException { | |
try { | ||
commandLine = parser.parse(allOptions, args, false); | ||
|
||
if (! OSDetection.is64Bit()) { | ||
System.err.println("32 bit support is deprecated. Apktool will not support 32bit on v3.0.0."); | ||
if (!OSDetection.is64Bit()) { | ||
System.err.println("32-bit support is deprecated and will be removed in 3.0.0."); | ||
} | ||
} catch (ParseException ex) { | ||
System.err.println(ex.getMessage()); | ||
|
@@ -96,7 +94,7 @@ public static void main(String[] args) throws BrutException { | |
setAdvanceMode(); | ||
} | ||
|
||
Config config = Config.getDefaultConfig(); | ||
Config config = new Config(); | ||
initConfig(commandLine, config); | ||
|
||
boolean cmdFound = false; | ||
|
@@ -145,16 +143,16 @@ public static void main(String[] args) throws BrutException { | |
|
||
private static void initConfig(CommandLine cli, Config config) { | ||
if (cli.hasOption("p") || cli.hasOption("frame-path")) { | ||
config.frameworkDirectory = cli.getOptionValue("p"); | ||
config.setFrameworkDirectory(cli.getOptionValue("p")); | ||
} | ||
if (cli.hasOption("t") || cli.hasOption("tag")) { | ||
config.frameworkTag = cli.getOptionValue("t"); | ||
config.setFrameworkTag(cli.getOptionValue("t")); | ||
} | ||
if (cli.hasOption("api") || cli.hasOption("api-level")) { | ||
config.apiLevel = Integer.parseInt(cli.getOptionValue("api")); | ||
config.setApiLevel(Integer.parseInt(cli.getOptionValue("api"))); | ||
} | ||
if (cli.hasOption("j") || cli.hasOption("jobs")) { | ||
config.jobs = Integer.parseInt(cli.getOptionValue("j")); | ||
config.setJobs(Integer.parseInt(cli.getOptionValue("j"))); | ||
} | ||
} | ||
|
||
|
@@ -166,17 +164,21 @@ private static void cmdDecode(CommandLine cli, Config config) throws AndrolibExc | |
config.setDecodeSources(Config.DECODE_SOURCES_NONE); | ||
} | ||
if (cli.hasOption("only-main-classes")) { | ||
config.setDecodeSources(Config.DECODE_SOURCES_SMALI_ONLY_MAIN_CLASSES); | ||
if (cli.hasOption("s") || cli.hasOption("no-src")) { | ||
System.err.println("--only-main-classes cannot be paired with -s/--no-src. Ignoring."); | ||
} else { | ||
config.setDecodeSources(Config.DECODE_SOURCES_SMALI_ONLY_MAIN_CLASSES); | ||
} | ||
} | ||
if (cli.hasOption("d") || cli.hasOption("debug")) { | ||
System.err.println("SmaliDebugging has been removed in 2.1.0 onward. Please see: https://github.com/iBotPeaches/Apktool/issues/1061"); | ||
System.exit(1); | ||
} | ||
if (cli.hasOption("b") || cli.hasOption("no-debug-info")) { | ||
config.baksmaliDebugMode = false; | ||
config.setBaksmaliDebugMode(false); | ||
} | ||
if (cli.hasOption("f") || cli.hasOption("force")) { | ||
config.forceDelete = true; | ||
config.setForceDelete(true); | ||
} | ||
if (cli.hasOption("r") || cli.hasOption("no-res")) { | ||
config.setDecodeResources(Config.DECODE_RESOURCES_NONE); | ||
|
@@ -188,10 +190,10 @@ private static void cmdDecode(CommandLine cli, Config config) throws AndrolibExc | |
config.setDecodeAssets(Config.DECODE_ASSETS_NONE); | ||
} | ||
if (cli.hasOption("k") || cli.hasOption("keep-broken-res")) { | ||
config.keepBrokenResources = true; | ||
config.setKeepBrokenResources(true); | ||
} | ||
if (cli.hasOption("m") || cli.hasOption("match-original")) { | ||
config.analysisMode = true; | ||
config.setAnalysisMode(true); | ||
} | ||
if (cli.hasOption("resm") || cli.hasOption("res-mode") || cli.hasOption("resolve-resources-mode")) { | ||
String mode = cli.getOptionValue("resm"); | ||
|
@@ -266,16 +268,16 @@ private static void cmdBuild(CommandLine cli, Config config) throws AndrolibExce | |
|
||
// check for build options | ||
if (cli.hasOption("f") || cli.hasOption("force-all")) { | ||
config.forceBuildAll = true; | ||
config.setForceBuildAll(true); | ||
} | ||
if (cli.hasOption("d") || cli.hasOption("debug")) { | ||
config.debugMode = true; | ||
config.setDebugMode(true); | ||
} | ||
if (cli.hasOption("n") || cli.hasOption("net-sec-conf")) { | ||
config.netSecConf = true; | ||
config.setNetSecConf(true); | ||
} | ||
if (cli.hasOption("v") || cli.hasOption("verbose")) { | ||
config.verbose = true; | ||
config.setVerbose(true); | ||
} | ||
if (cli.hasOption("a") || cli.hasOption("aapt")) { | ||
if (cli.hasOption("use-aapt1") || cli.hasOption("use-aapt2")) { | ||
|
@@ -284,8 +286,7 @@ private static void cmdBuild(CommandLine cli, Config config) throws AndrolibExce | |
} | ||
|
||
try { | ||
config.aaptBinary = new File(cli.getOptionValue("a")); | ||
config.aaptVersion = AaptManager.getAaptVersion(config.aaptBinary); | ||
config.setAaptBinary(new File(cli.getOptionValue("a"))); | ||
} catch (BrutException ex) { | ||
System.err.println(ex.getMessage()); | ||
System.exit(1); | ||
|
@@ -296,42 +297,38 @@ private static void cmdBuild(CommandLine cli, Config config) throws AndrolibExce | |
System.exit(1); | ||
} | ||
|
||
config.aaptVersion = 1; | ||
config.setAaptVersion(1); | ||
} | ||
if (cli.hasOption("c") || cli.hasOption("copy-original")) { | ||
config.copyOriginalFiles = true; | ||
config.setCopyOriginalFiles(true); | ||
} | ||
if (cli.hasOption("nc") || cli.hasOption("no-crunch")) { | ||
config.noCrunch = true; | ||
config.setNoCrunch(true); | ||
} | ||
if (cli.hasOption("na") || cli.hasOption("no-apk")) { | ||
config.noApk = true; | ||
config.setNoApk(true); | ||
} | ||
|
||
File outFile; | ||
if (cli.hasOption("o") || cli.hasOption("output")) { | ||
outFile = new File(cli.getOptionValue("o")); | ||
} else { | ||
outFile = null; | ||
} | ||
|
||
if (config.netSecConf && config.aaptVersion == 1) { | ||
if (config.isNetSecConf() && config.getAaptVersion() == 1) { | ||
System.err.println("-n / --net-sec-conf is not supported with legacy aapt."); | ||
System.exit(1); | ||
} | ||
|
||
File outFile = cli.hasOption("o") || cli.hasOption("output") | ||
? new File(cli.getOptionValue("o")) : null; | ||
|
||
ExtFile apkDir = new ExtFile(apkDirName); | ||
ApkBuilder builder = new ApkBuilder(apkDir, config); | ||
builder.build(outFile); | ||
} | ||
|
||
private static void cmdInstallFramework(CommandLine cli, Config config) throws AndrolibException { | ||
String apkName = getLastArg(cli); | ||
new Framework(config).installFramework(new File(apkName)); | ||
new Framework(config).install(new File(apkName)); | ||
} | ||
|
||
private static void cmdListFrameworks(CommandLine cli, Config config) throws AndrolibException { | ||
new Framework(config).listFrameworkDirectory(); | ||
new Framework(config).listDirectory(); | ||
} | ||
|
||
private static void cmdPublicizeResources(CommandLine cli, Config config) throws AndrolibException { | ||
|
@@ -341,9 +338,9 @@ private static void cmdPublicizeResources(CommandLine cli, Config config) throws | |
|
||
private static void cmdEmptyFrameworkDirectory(CommandLine cli, Config config) throws AndrolibException { | ||
if (cli.hasOption("f") || cli.hasOption("force")) { | ||
config.forceDeleteFramework = true; | ||
config.setForceDeleteFramework(true); | ||
} | ||
new Framework(config).emptyFrameworkDirectory(); | ||
new Framework(config).emptyDirectory(); | ||
} | ||
|
||
private static String getLastArg(CommandLine cli) { | ||
|
@@ -638,11 +635,11 @@ private static void usage() { | |
|
||
// print out license info prior to formatter. | ||
System.out.println( | ||
"Apktool " + ApktoolProperties.getVersion() + " - a tool for reengineering Android apk files\n" + | ||
"with smali v" + ApktoolProperties.get("smaliVersion") + | ||
" and baksmali v" + ApktoolProperties.get("baksmaliVersion") + "\n" + | ||
"Copyright 2010 Ryszard Wiśniewski <[email protected]>\n" + | ||
"Copyright 2010 Connor Tumbleson <[email protected]>" ); | ||
"Apktool " + ApktoolProperties.getVersion() + " - a tool for reengineering Android apk files\n" + | ||
"with smali " + ApktoolProperties.getSmaliVersion() + | ||
" and baksmali " + ApktoolProperties.getBaksmaliVersion() + "\n" + | ||
"Copyright 2010 Ryszard Wiśniewski <[email protected]>\n" + | ||
"Copyright 2010 Connor Tumbleson <[email protected]>"); | ||
if (isAdvanceMode()) { | ||
System.out.println("Apache License 2.0 (https://www.apache.org/licenses/LICENSE-2.0)\n"); | ||
}else { | ||
|
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.