summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md1
-rw-r--r--build.gradle1
-rw-r--r--enigma-cli/src/main/java/cuchaz/enigma/command/Command.java3
-rw-r--r--enigma-server/src/main/java/cuchaz/enigma/network/DedicatedEnigmaServer.java3
-rw-r--r--enigma-server/src/main/java/cuchaz/enigma/network/ServerAddress.java4
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/EditableType.java2
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/Gui.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/GuiController.java6
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/Main.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/config/OldConfigImporter.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/config/Themes.java13
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/config/legacy/Config.java18
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/dialog/JavadocDialog.java5
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/elements/AbstractInheritanceTree.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/elements/EditorTabbedPane.java9
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ImplementationsTree.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/elements/InheritanceTree.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ValidatableUi.java2
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/panels/ClosableTabTitlePane.java3
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/panels/EditorPanel.java2
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/util/GuiUtil.java4
-rw-r--r--enigma-swing/src/main/java/cuchaz/enigma/gui/util/History.java7
-rw-r--r--enigma/build.gradle17
-rw-r--r--enigma/src/main/java/cuchaz/enigma/Enigma.java19
-rw-r--r--enigma/src/main/java/cuchaz/enigma/EnigmaProfile.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/EnigmaProject.java10
-rw-r--r--enigma/src/main/java/cuchaz/enigma/EnigmaServices.java9
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/ClassImplementationsTreeNode.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/ClassInheritanceTreeNode.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/ClassReferenceTreeNode.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/IndexTreeBuilder.java7
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/MethodImplementationsTreeNode.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/MethodReferenceTreeNode.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/index/BridgeMethodIndex.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/index/EntryIndex.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/index/InheritanceIndex.java4
-rw-r--r--enigma/src/main/java/cuchaz/enigma/analysis/index/PackageVisibilityIndex.java14
-rw-r--r--enigma/src/main/java/cuchaz/enigma/bytecode/translators/LocalVariableFixVisitor.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandle.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleError.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleProvider.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/CachingClassProvider.java69
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/ClassProvider.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/ClasspathClassProvider.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/CombiningClassProvider.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/JarClassProvider.java27
-rw-r--r--enigma/src/main/java/cuchaz/enigma/classprovider/ObfuscationFixClassProvider.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/DecompiledClassSource.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/Decompiler.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/SourceIndex.java38
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/bytecode/BytecodeDecompiler.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDecompiler.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDumper.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/cfr/CfrSource.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/procyon/ProcyonDecompiler.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/procyon/index/SourceIndexMethodVisitor.java14
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/procyon/transformers/AddJavadocsAstTransform.java9
-rw-r--r--enigma/src/main/java/cuchaz/enigma/source/vineflower/VineflowerDecompiler.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/MappingTranslator.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/ProposingTranslator.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/SignatureUpdater.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/Translator.java15
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryChange.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMap.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMapping.java6
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryRemapper.java10
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryResolver.java15
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryUtil.java4
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/IndexEntryResolver.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingPair.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingValidator.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingFormat.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingIoConverter.java3
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsReader.java7
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsWriter.java11
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/recaf/RecafMappingsWriter.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/srg/SrgMappingsWriter.java8
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsReader.java5
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsWriter.java9
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tinyv2/TinyV2Writer.java4
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/DeltaTrackingTree.java10
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTree.java4
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTreeNode.java12
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashEntryTree.java14
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashTreeNode.java6
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/MethodDescriptor.java7
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/TypeDescriptor.java9
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassDefEntry.java15
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassEntry.java8
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/Entry.java2
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldDefEntry.java12
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldEntry.java13
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableDefEntry.java9
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableEntry.java13
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodDefEntry.java12
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodEntry.java13
-rw-r--r--enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ParentedEntry.java14
-rw-r--r--enigma/src/main/java/cuchaz/enigma/utils/I18n.java34
-rw-r--r--enigma/src/main/java/cuchaz/enigma/utils/Utils.java11
-rw-r--r--enigma/src/main/java/cuchaz/enigma/utils/validation/ValidationContext.java2
-rw-r--r--enigma/src/test/java/cuchaz/enigma/TokenChecker.java5
-rw-r--r--enigma/src/test/java/cuchaz/enigma/translation/mapping/serde/recaf/TestRecaf.java3
102 files changed, 399 insertions, 360 deletions
diff --git a/README.md b/README.md
index 08cc0c92..0327da11 100644
--- a/README.md
+++ b/README.md
@@ -11,7 +11,6 @@ Enigma includes the following open-source libraries:
11- [Vineflower](https://github.com/Vineflower/vineflower) (Apache-2.0) 11- [Vineflower](https://github.com/Vineflower/vineflower) (Apache-2.0)
12- A [modified version](https://github.com/FabricMC/cfr) of [CFR](https://github.com/leibnitz27/cfr) (MIT) 12- A [modified version](https://github.com/FabricMC/cfr) of [CFR](https://github.com/leibnitz27/cfr) (MIT)
13- A [modified version](https://github.com/FabricMC/procyon) of [Procyon](https://bitbucket.org/mstrobel/procyon) (Apache-2.0) 13- A [modified version](https://github.com/FabricMC/procyon) of [Procyon](https://bitbucket.org/mstrobel/procyon) (Apache-2.0)
14- [Guava](https://github.com/google/guava) (Apache-2.0)
15- [SyntaxPane](https://github.com/Sciss/SyntaxPane) (Apache-2.0) 14- [SyntaxPane](https://github.com/Sciss/SyntaxPane) (Apache-2.0)
16- [FlatLaf](https://github.com/JFormDesigner/FlatLaf) (Apache-2.0) 15- [FlatLaf](https://github.com/JFormDesigner/FlatLaf) (Apache-2.0)
17- [jopt-simple](https://github.com/jopt-simple/jopt-simple) (MIT) 16- [jopt-simple](https://github.com/jopt-simple/jopt-simple) (MIT)
diff --git a/build.gradle b/build.gradle
index 4453ab93..9f311844 100644
--- a/build.gradle
+++ b/build.gradle
@@ -17,7 +17,6 @@ subprojects {
17 } 17 }
18 18
19 dependencies { 19 dependencies {
20 implementation 'com.google.guava:guava:32.1.2-jre'
21 implementation 'com.google.code.gson:gson:2.10.1' 20 implementation 'com.google.code.gson:gson:2.10.1'
22 implementation 'net.fabricmc:mapping-io:0.7.1' 21 implementation 'net.fabricmc:mapping-io:0.7.1'
23 22
diff --git a/enigma-cli/src/main/java/cuchaz/enigma/command/Command.java b/enigma-cli/src/main/java/cuchaz/enigma/command/Command.java
index de06fa6e..06c49162 100644
--- a/enigma-cli/src/main/java/cuchaz/enigma/command/Command.java
+++ b/enigma-cli/src/main/java/cuchaz/enigma/command/Command.java
@@ -6,7 +6,6 @@ import java.nio.file.Files;
6import java.nio.file.Path; 6import java.nio.file.Path;
7import java.nio.file.Paths; 7import java.nio.file.Paths;
8 8
9import com.google.common.io.MoreFiles;
10import net.fabricmc.mappingio.MappingReader; 9import net.fabricmc.mappingio.MappingReader;
11import net.fabricmc.mappingio.tree.MemoryMappingTree; 10import net.fabricmc.mappingio.tree.MemoryMappingTree;
12import net.fabricmc.mappingio.tree.VisitableMappingTree; 11import net.fabricmc.mappingio.tree.VisitableMappingTree;
@@ -57,7 +56,7 @@ public abstract class Command {
57 56
58 protected static EntryTree<EntryMapping> readMappings(Path path, ProgressListener progress, MappingSaveParameters saveParameters) throws IOException, MappingParseException { 57 protected static EntryTree<EntryMapping> readMappings(Path path, ProgressListener progress, MappingSaveParameters saveParameters) throws IOException, MappingParseException {
59 // Legacy 58 // Legacy
60 if ("zip".equalsIgnoreCase(MoreFiles.getFileExtension(path))) { 59 if (path.getFileName().toString().toLowerCase().endsWith(".zip")) {
61 return MappingFormat.ENIGMA_ZIP.read(path, progress, saveParameters, null); 60 return MappingFormat.ENIGMA_ZIP.read(path, progress, saveParameters, null);
62 } 61 }
63 62
diff --git a/enigma-server/src/main/java/cuchaz/enigma/network/DedicatedEnigmaServer.java b/enigma-server/src/main/java/cuchaz/enigma/network/DedicatedEnigmaServer.java
index f20a9d29..af5e34b3 100644
--- a/enigma-server/src/main/java/cuchaz/enigma/network/DedicatedEnigmaServer.java
+++ b/enigma-server/src/main/java/cuchaz/enigma/network/DedicatedEnigmaServer.java
@@ -11,7 +11,6 @@ import java.util.concurrent.Executors;
11import java.util.concurrent.LinkedBlockingDeque; 11import java.util.concurrent.LinkedBlockingDeque;
12import java.util.concurrent.TimeUnit; 12import java.util.concurrent.TimeUnit;
13 13
14import com.google.common.io.MoreFiles;
15import joptsimple.OptionParser; 14import joptsimple.OptionParser;
16import joptsimple.OptionSet; 15import joptsimple.OptionSet;
17import joptsimple.OptionSpec; 16import joptsimple.OptionSpec;
@@ -103,7 +102,7 @@ public class DedicatedEnigmaServer extends EnigmaServer {
103 102
104 if (Files.isDirectory(mappingsFile)) { 103 if (Files.isDirectory(mappingsFile)) {
105 mappingFormat = MappingFormat.ENIGMA_DIRECTORY; 104 mappingFormat = MappingFormat.ENIGMA_DIRECTORY;
106 } else if ("zip".equalsIgnoreCase(MoreFiles.getFileExtension(mappingsFile))) { 105 } else if (mappingsFile.getFileName().toString().toLowerCase().endsWith(".zip")) {
107 mappingFormat = MappingFormat.ENIGMA_ZIP; 106 mappingFormat = MappingFormat.ENIGMA_ZIP;
108 } else { 107 } else {
109 mappingFormat = MappingFormat.ENIGMA_FILE; 108 mappingFormat = MappingFormat.ENIGMA_FILE;
diff --git a/enigma-server/src/main/java/cuchaz/enigma/network/ServerAddress.java b/enigma-server/src/main/java/cuchaz/enigma/network/ServerAddress.java
index a8a10296..09a13ccb 100644
--- a/enigma-server/src/main/java/cuchaz/enigma/network/ServerAddress.java
+++ b/enigma-server/src/main/java/cuchaz/enigma/network/ServerAddress.java
@@ -2,7 +2,7 @@ package cuchaz.enigma.network;
2 2
3import java.util.Objects; 3import java.util.Objects;
4 4
5import javax.annotation.Nullable; 5import org.jetbrains.annotations.Nullable;
6 6
7public class ServerAddress { 7public class ServerAddress {
8 public final String address; 8 public final String address;
@@ -23,7 +23,7 @@ public class ServerAddress {
23 return null; 23 return null;
24 } 24 }
25 25
26 if (address.equals("")) { 26 if (address.isEmpty()) {
27 return null; 27 return null;
28 } 28 }
29 29
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/EditableType.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/EditableType.java
index 6028609f..a70c9b57 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/EditableType.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/EditableType.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.gui; 1package cuchaz.enigma.gui;
2 2
3import javax.annotation.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.translation.representation.entry.ClassEntry; 5import cuchaz.enigma.translation.representation.entry.ClassEntry;
6import cuchaz.enigma.translation.representation.entry.Entry; 6import cuchaz.enigma.translation.representation.entry.Entry;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/Gui.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/Gui.java
index 21120b8a..c85c4044 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/Gui.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/Gui.java
@@ -23,7 +23,6 @@ import java.util.concurrent.CompletableFuture;
23import java.util.function.Consumer; 23import java.util.function.Consumer;
24import java.util.function.Function; 24import java.util.function.Function;
25 25
26import javax.annotation.Nullable;
27import javax.swing.AbstractAction; 26import javax.swing.AbstractAction;
28import javax.swing.DefaultListModel; 27import javax.swing.DefaultListModel;
29import javax.swing.JButton; 28import javax.swing.JButton;
@@ -42,6 +41,8 @@ import javax.swing.SwingUtilities;
42import javax.swing.WindowConstants; 41import javax.swing.WindowConstants;
43import javax.swing.tree.DefaultMutableTreeNode; 42import javax.swing.tree.DefaultMutableTreeNode;
44 43
44import org.jetbrains.annotations.Nullable;
45
45import cuchaz.enigma.Enigma; 46import cuchaz.enigma.Enigma;
46import cuchaz.enigma.EnigmaProfile; 47import cuchaz.enigma.EnigmaProfile;
47import cuchaz.enigma.analysis.EntryReference; 48import cuchaz.enigma.analysis.EntryReference;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/GuiController.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/GuiController.java
index ece11b00..e8e4dbde 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/GuiController.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/GuiController.java
@@ -17,6 +17,7 @@ import java.io.FileWriter;
17import java.io.IOException; 17import java.io.IOException;
18import java.nio.charset.StandardCharsets; 18import java.nio.charset.StandardCharsets;
19import java.nio.file.Path; 19import java.nio.file.Path;
20import java.util.ArrayList;
20import java.util.Collection; 21import java.util.Collection;
21import java.util.List; 22import java.util.List;
22import java.util.Objects; 23import java.util.Objects;
@@ -29,7 +30,6 @@ import java.util.stream.Stream;
29import javax.swing.JOptionPane; 30import javax.swing.JOptionPane;
30import javax.swing.SwingUtilities; 31import javax.swing.SwingUtilities;
31 32
32import com.google.common.collect.Lists;
33import org.jetbrains.annotations.ApiStatus; 33import org.jetbrains.annotations.ApiStatus;
34 34
35import cuchaz.enigma.Enigma; 35import cuchaz.enigma.Enigma;
@@ -414,8 +414,8 @@ public class GuiController implements ClientPacketHandler {
414 return; 414 return;
415 } 415 }
416 416
417 List<ClassEntry> obfClasses = Lists.newArrayList(); 417 List<ClassEntry> obfClasses = new ArrayList<>();
418 List<ClassEntry> deobfClasses = Lists.newArrayList(); 418 List<ClassEntry> deobfClasses = new ArrayList<>();
419 this.addSeparatedClasses(obfClasses, deobfClasses); 419 this.addSeparatedClasses(obfClasses, deobfClasses);
420 this.gui.setObfClasses(obfClasses); 420 this.gui.setObfClasses(obfClasses);
421 this.gui.setDeobfClasses(deobfClasses); 421 this.gui.setDeobfClasses(deobfClasses);
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/Main.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/Main.java
index 43b16cd9..dc58464c 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/Main.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/Main.java
@@ -20,7 +20,6 @@ import java.util.EnumSet;
20import java.util.List; 20import java.util.List;
21import java.util.Set; 21import java.util.Set;
22 22
23import com.google.common.io.MoreFiles;
24import joptsimple.OptionException; 23import joptsimple.OptionException;
25import joptsimple.OptionParser; 24import joptsimple.OptionParser;
26import joptsimple.OptionSet; 25import joptsimple.OptionSet;
@@ -144,7 +143,7 @@ public class Main {
144 143
145 if (Files.isDirectory(mappingsPath)) { 144 if (Files.isDirectory(mappingsPath)) {
146 controller.openMappings(MappingFormat.ENIGMA_DIRECTORY, mappingsPath); 145 controller.openMappings(MappingFormat.ENIGMA_DIRECTORY, mappingsPath);
147 } else if ("zip".equalsIgnoreCase(MoreFiles.getFileExtension(mappingsPath))) { 146 } else if (mappingsPath.getFileName().toString().toLowerCase().endsWith(".zip")) {
148 controller.openMappings(MappingFormat.ENIGMA_ZIP, mappingsPath); 147 controller.openMappings(MappingFormat.ENIGMA_ZIP, mappingsPath);
149 } else { 148 } else {
150 controller.openMappings(MappingFormat.ENIGMA_FILE, mappingsPath); 149 controller.openMappings(MappingFormat.ENIGMA_FILE, mappingsPath);
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/OldConfigImporter.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/OldConfigImporter.java
index 2e84991b..181b2866 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/OldConfigImporter.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/OldConfigImporter.java
@@ -1,6 +1,7 @@
1package cuchaz.enigma.gui.config; 1package cuchaz.enigma.gui.config;
2 2
3import java.awt.Font; 3import java.awt.Font;
4import java.nio.file.Files;
4 5
5import cuchaz.enigma.gui.config.legacy.Config; 6import cuchaz.enigma.gui.config.legacy.Config;
6 7
@@ -10,7 +11,7 @@ public final class OldConfigImporter {
10 11
11 @SuppressWarnings("deprecation") 12 @SuppressWarnings("deprecation")
12 public static void doImport() { 13 public static void doImport() {
13 if (Config.CONFIG_FILE.exists()) { 14 if (Files.exists(Config.CONFIG_FILE)) {
14 Config config = new Config(); 15 Config config = new Config();
15 16
16 if (config.editorFont != null) { 17 if (config.editorFont != null) {
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/Themes.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/Themes.java
index e2db9682..d2a6608c 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/Themes.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/Themes.java
@@ -2,11 +2,11 @@ package cuchaz.enigma.gui.config;
2 2
3import java.awt.Font; 3import java.awt.Font;
4import java.util.HashSet; 4import java.util.HashSet;
5import java.util.Map;
5import java.util.Set; 6import java.util.Set;
6 7
7import javax.swing.UIManager; 8import javax.swing.UIManager;
8 9
9import com.google.common.collect.ImmutableMap;
10import de.sciss.syntaxpane.DefaultSyntaxKit; 10import de.sciss.syntaxpane.DefaultSyntaxKit;
11 11
12import cuchaz.enigma.gui.EnigmaSyntaxKit; 12import cuchaz.enigma.gui.EnigmaSyntaxKit;
@@ -30,7 +30,7 @@ public class Themes {
30 EnigmaSyntaxKit.invalidate(); 30 EnigmaSyntaxKit.invalidate();
31 DefaultSyntaxKit.initKit(); 31 DefaultSyntaxKit.initKit();
32 DefaultSyntaxKit.registerContentType("text/enigma-sources", EnigmaSyntaxKit.class.getName()); 32 DefaultSyntaxKit.registerContentType("text/enigma-sources", EnigmaSyntaxKit.class.getName());
33 ImmutableMap<RenamableTokenType, BoxHighlightPainter> boxHighlightPainters = getBoxHighlightPainters(); 33 Map<RenamableTokenType, BoxHighlightPainter> boxHighlightPainters = getBoxHighlightPainters();
34 listeners.forEach(l -> l.onThemeChanged(laf, boxHighlightPainters)); 34 listeners.forEach(l -> l.onThemeChanged(laf, boxHighlightPainters));
35 ScaleUtil.applyScaling(); 35 ScaleUtil.applyScaling();
36 UiConfig.save(); 36 UiConfig.save();
@@ -85,9 +85,12 @@ public class Themes {
85 } 85 }
86 } 86 }
87 87
88 public static ImmutableMap<RenamableTokenType, BoxHighlightPainter> getBoxHighlightPainters() { 88 public static Map<RenamableTokenType, BoxHighlightPainter> getBoxHighlightPainters() {
89 return ImmutableMap.of(RenamableTokenType.OBFUSCATED, BoxHighlightPainter.create(UiConfig.getObfuscatedColor(), UiConfig.getObfuscatedOutlineColor()), RenamableTokenType.PROPOSED, BoxHighlightPainter.create(UiConfig.getProposedColor(), UiConfig.getProposedOutlineColor()), 89 return Map.of(
90 RenamableTokenType.DEOBFUSCATED, BoxHighlightPainter.create(UiConfig.getDeobfuscatedColor(), UiConfig.getDeobfuscatedOutlineColor())); 90 RenamableTokenType.OBFUSCATED, BoxHighlightPainter.create(UiConfig.getObfuscatedColor(), UiConfig.getObfuscatedOutlineColor()),
91 RenamableTokenType.PROPOSED, BoxHighlightPainter.create(UiConfig.getProposedColor(), UiConfig.getProposedOutlineColor()),
92 RenamableTokenType.DEOBFUSCATED, BoxHighlightPainter.create(UiConfig.getDeobfuscatedColor(), UiConfig.getDeobfuscatedOutlineColor())
93 );
91 } 94 }
92 95
93 public static void addListener(ThemeChangeListener listener) { 96 public static void addListener(ThemeChangeListener listener) {
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/legacy/Config.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/legacy/Config.java
index 2f7cf19b..9955a6b0 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/config/legacy/Config.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/config/legacy/Config.java
@@ -1,11 +1,11 @@
1package cuchaz.enigma.gui.config.legacy; 1package cuchaz.enigma.gui.config.legacy;
2 2
3import java.awt.Color; 3import java.awt.Color;
4import java.io.File; 4import java.io.BufferedReader;
5import java.lang.reflect.Type; 5import java.lang.reflect.Type;
6import java.nio.charset.Charset; 6import java.nio.file.Files;
7import java.nio.file.Path;
7 8
8import com.google.common.io.Files;
9import com.google.gson.Gson; 9import com.google.gson.Gson;
10import com.google.gson.GsonBuilder; 10import com.google.gson.GsonBuilder;
11import com.google.gson.InstanceCreator; 11import com.google.gson.InstanceCreator;
@@ -40,9 +40,9 @@ public class Config {
40 } 40 }
41 } 41 }
42 42
43 private static final File DIR_HOME = new File(System.getProperty("user.home")); 43 private static final Path DIR_HOME = Path.of(System.getProperty("user.home"));
44 private static final File ENIGMA_DIR = new File(DIR_HOME, ".enigma"); 44 private static final Path ENIGMA_DIR = DIR_HOME.resolve(".enigma");
45 public static final File CONFIG_FILE = new File(ENIGMA_DIR, "config.json"); 45 public static final Path CONFIG_FILE = ENIGMA_DIR.resolve("config.json");
46 46
47 private final transient Gson gson; // transient to exclude it from being exposed 47 private final transient Gson gson; // transient to exclude it from being exposed
48 48
@@ -86,9 +86,9 @@ public class Config {
86 } 86 }
87 87
88 public void loadConfig() { 88 public void loadConfig() {
89 if (CONFIG_FILE.exists()) { 89 if (Files.exists(CONFIG_FILE)) {
90 try { 90 try (BufferedReader reader = Files.newBufferedReader(CONFIG_FILE)) {
91 gson.fromJson(Files.asCharSource(CONFIG_FILE, Charset.defaultCharset()).read(), Config.class); 91 gson.fromJson(reader, Config.class);
92 } catch (Exception e) { 92 } catch (Exception e) {
93 e.printStackTrace(); 93 e.printStackTrace();
94 } 94 }
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/dialog/JavadocDialog.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/dialog/JavadocDialog.java
index 0ecec6c0..05b7dfbe 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/dialog/JavadocDialog.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/dialog/JavadocDialog.java
@@ -17,6 +17,7 @@ import java.awt.Dimension;
17import java.awt.FlowLayout; 17import java.awt.FlowLayout;
18import java.awt.event.KeyAdapter; 18import java.awt.event.KeyAdapter;
19import java.awt.event.KeyEvent; 19import java.awt.event.KeyEvent;
20import java.util.Objects;
20 21
21import javax.swing.JButton; 22import javax.swing.JButton;
22import javax.swing.JComboBox; 23import javax.swing.JComboBox;
@@ -29,8 +30,6 @@ import javax.swing.JScrollPane;
29import javax.swing.WindowConstants; 30import javax.swing.WindowConstants;
30import javax.swing.text.html.HTML; 31import javax.swing.text.html.HTML;
31 32
32import com.google.common.base.Strings;
33
34import cuchaz.enigma.analysis.EntryReference; 33import cuchaz.enigma.analysis.EntryReference;
35import cuchaz.enigma.gui.GuiController; 34import cuchaz.enigma.gui.GuiController;
36import cuchaz.enigma.gui.config.UiConfig; 35import cuchaz.enigma.gui.config.UiConfig;
@@ -198,7 +197,7 @@ public class JavadocDialog {
198 public static void show(JFrame parent, GuiController controller, EntryReference<Entry<?>, Entry<?>> entry) { 197 public static void show(JFrame parent, GuiController controller, EntryReference<Entry<?>, Entry<?>> entry) {
199 // Get the existing text through the mapping as it works for all entries, including constructors. 198 // Get the existing text through the mapping as it works for all entries, including constructors.
200 EntryMapping mapping = controller.project.getMapper().getDeobfMapping(entry.entry); 199 EntryMapping mapping = controller.project.getMapper().getDeobfMapping(entry.entry);
201 String text = Strings.nullToEmpty(mapping.javadoc()); 200 String text = Objects.requireNonNullElse(mapping.javadoc(), "");
202 201
203 // Note: entry.entry is used instead of getNameableEntry() to include constructors, 202 // Note: entry.entry is used instead of getNameableEntry() to include constructors,
204 // which can be documented. 203 // which can be documented.
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/AbstractInheritanceTree.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/AbstractInheritanceTree.java
index 8acfcfe6..6194aa56 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/AbstractInheritanceTree.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/AbstractInheritanceTree.java
@@ -3,7 +3,6 @@ package cuchaz.enigma.gui.elements;
3import java.awt.BorderLayout; 3import java.awt.BorderLayout;
4import java.awt.event.MouseEvent; 4import java.awt.event.MouseEvent;
5 5
6import javax.annotation.Nullable;
7import javax.swing.JPanel; 6import javax.swing.JPanel;
8import javax.swing.JScrollPane; 7import javax.swing.JScrollPane;
9import javax.swing.JTree; 8import javax.swing.JTree;
@@ -13,6 +12,8 @@ import javax.swing.tree.TreeCellRenderer;
13import javax.swing.tree.TreeNode; 12import javax.swing.tree.TreeNode;
14import javax.swing.tree.TreePath; 13import javax.swing.tree.TreePath;
15 14
15import org.jetbrains.annotations.Nullable;
16
16import cuchaz.enigma.analysis.ClassTreeNode; 17import cuchaz.enigma.analysis.ClassTreeNode;
17import cuchaz.enigma.analysis.MethodInheritanceTreeNode; 18import cuchaz.enigma.analysis.MethodInheritanceTreeNode;
18import cuchaz.enigma.analysis.MethodTreeNode; 19import cuchaz.enigma.analysis.MethodTreeNode;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/EditorTabbedPane.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/EditorTabbedPane.java
index 7a6290ea..65b57af3 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/EditorTabbedPane.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/EditorTabbedPane.java
@@ -4,13 +4,14 @@ import java.awt.Component;
4import java.awt.event.KeyAdapter; 4import java.awt.event.KeyAdapter;
5import java.awt.event.KeyEvent; 5import java.awt.event.KeyEvent;
6import java.awt.event.MouseEvent; 6import java.awt.event.MouseEvent;
7import java.util.HashMap;
7import java.util.Iterator; 8import java.util.Iterator;
9import java.util.Map;
8 10
9import javax.annotation.Nullable;
10import javax.swing.JTabbedPane; 11import javax.swing.JTabbedPane;
11import javax.swing.SwingUtilities; 12import javax.swing.SwingUtilities;
12 13
13import com.google.common.collect.HashBiMap; 14import org.jetbrains.annotations.Nullable;
14 15
15import cuchaz.enigma.analysis.EntryReference; 16import cuchaz.enigma.analysis.EntryReference;
16import cuchaz.enigma.classhandle.ClassHandle; 17import cuchaz.enigma.classhandle.ClassHandle;
@@ -24,7 +25,7 @@ import cuchaz.enigma.translation.representation.entry.Entry;
24 25
25public class EditorTabbedPane { 26public class EditorTabbedPane {
26 private final JTabbedPane openFiles = new JTabbedPane(JTabbedPane.TOP, JTabbedPane.SCROLL_TAB_LAYOUT); 27 private final JTabbedPane openFiles = new JTabbedPane(JTabbedPane.TOP, JTabbedPane.SCROLL_TAB_LAYOUT);
27 private final HashBiMap<ClassEntry, EditorPanel> editors = HashBiMap.create(); 28 private final Map<ClassEntry, EditorPanel> editors = new HashMap<>();
28 29
29 private final EditorTabPopupMenu editorTabPopupMenu; 30 private final EditorTabPopupMenu editorTabPopupMenu;
30 private final Gui gui; 31 private final Gui gui;
@@ -95,7 +96,7 @@ public class EditorTabbedPane {
95 96
96 public void closeEditor(EditorPanel ed) { 97 public void closeEditor(EditorPanel ed) {
97 this.openFiles.remove(ed.getUi()); 98 this.openFiles.remove(ed.getUi());
98 this.editors.inverse().remove(ed); 99 this.editors.values().remove(ed);
99 this.gui.showStructure(this.getActiveEditor()); 100 this.gui.showStructure(this.getActiveEditor());
100 ed.destroy(); 101 ed.destroy();
101 } 102 }
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ImplementationsTree.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ImplementationsTree.java
index 962cf273..2500ec8d 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ImplementationsTree.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ImplementationsTree.java
@@ -1,8 +1,9 @@
1package cuchaz.enigma.gui.elements; 1package cuchaz.enigma.gui.elements;
2 2
3import javax.annotation.Nullable;
4import javax.swing.tree.DefaultMutableTreeNode; 3import javax.swing.tree.DefaultMutableTreeNode;
5 4
5import org.jetbrains.annotations.Nullable;
6
6import cuchaz.enigma.gui.Gui; 7import cuchaz.enigma.gui.Gui;
7import cuchaz.enigma.gui.renderer.ImplementationsTreeCellRenderer; 8import cuchaz.enigma.gui.renderer.ImplementationsTreeCellRenderer;
8import cuchaz.enigma.translation.representation.entry.ClassEntry; 9import cuchaz.enigma.translation.representation.entry.ClassEntry;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/InheritanceTree.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/InheritanceTree.java
index aeb173ba..513fa1b9 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/InheritanceTree.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/InheritanceTree.java
@@ -1,8 +1,9 @@
1package cuchaz.enigma.gui.elements; 1package cuchaz.enigma.gui.elements;
2 2
3import javax.annotation.Nullable;
4import javax.swing.tree.DefaultMutableTreeNode; 3import javax.swing.tree.DefaultMutableTreeNode;
5 4
5import org.jetbrains.annotations.Nullable;
6
6import cuchaz.enigma.gui.Gui; 7import cuchaz.enigma.gui.Gui;
7import cuchaz.enigma.gui.renderer.InheritanceTreeCellRenderer; 8import cuchaz.enigma.gui.renderer.InheritanceTreeCellRenderer;
8import cuchaz.enigma.translation.representation.entry.ClassEntry; 9import cuchaz.enigma.translation.representation.entry.ClassEntry;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ValidatableUi.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ValidatableUi.java
index b8b8431b..6ef5fbe9 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ValidatableUi.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/elements/ValidatableUi.java
@@ -7,7 +7,7 @@ import java.util.ArrayList;
7import java.util.Arrays; 7import java.util.Arrays;
8import java.util.List; 8import java.util.List;
9 9
10import javax.annotation.Nullable; 10import org.jetbrains.annotations.Nullable;
11 11
12import cuchaz.enigma.gui.util.ScaleUtil; 12import cuchaz.enigma.gui.util.ScaleUtil;
13import cuchaz.enigma.utils.validation.ParameterizedMessage; 13import cuchaz.enigma.utils.validation.ParameterizedMessage;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/ClosableTabTitlePane.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/ClosableTabTitlePane.java
index dca714dd..24ec233d 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/ClosableTabTitlePane.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/ClosableTabTitlePane.java
@@ -8,7 +8,6 @@ import java.awt.event.MouseAdapter;
8import java.awt.event.MouseEvent; 8import java.awt.event.MouseEvent;
9 9
10import javax.accessibility.AccessibleContext; 10import javax.accessibility.AccessibleContext;
11import javax.annotation.Nullable;
12import javax.swing.JButton; 11import javax.swing.JButton;
13import javax.swing.JComponent; 12import javax.swing.JComponent;
14import javax.swing.JLabel; 13import javax.swing.JLabel;
@@ -19,6 +18,8 @@ import javax.swing.UIManager;
19import javax.swing.border.EmptyBorder; 18import javax.swing.border.EmptyBorder;
20import javax.swing.event.ChangeListener; 19import javax.swing.event.ChangeListener;
21 20
21import org.jetbrains.annotations.Nullable;
22
22public class ClosableTabTitlePane { 23public class ClosableTabTitlePane {
23 private final JPanel ui; 24 private final JPanel ui;
24 private final JButton closeButton; 25 private final JButton closeButton;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/EditorPanel.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/EditorPanel.java
index e0a299f5..fb30f87a 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/EditorPanel.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/panels/EditorPanel.java
@@ -18,7 +18,6 @@ import java.util.Collection;
18import java.util.List; 18import java.util.List;
19import java.util.Map; 19import java.util.Map;
20 20
21import javax.annotation.Nullable;
22import javax.swing.JButton; 21import javax.swing.JButton;
23import javax.swing.JComponent; 22import javax.swing.JComponent;
24import javax.swing.JEditorPane; 23import javax.swing.JEditorPane;
@@ -36,6 +35,7 @@ import javax.swing.text.Highlighter.HighlightPainter;
36 35
37import de.sciss.syntaxpane.DefaultSyntaxKit; 36import de.sciss.syntaxpane.DefaultSyntaxKit;
38import de.sciss.syntaxpane.SyntaxDocument; 37import de.sciss.syntaxpane.SyntaxDocument;
38import org.jetbrains.annotations.Nullable;
39 39
40import cuchaz.enigma.EnigmaProject; 40import cuchaz.enigma.EnigmaProject;
41import cuchaz.enigma.analysis.EntryReference; 41import cuchaz.enigma.analysis.EntryReference;
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/util/GuiUtil.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/util/GuiUtil.java
index da1a2474..7cc0bfe1 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/util/GuiUtil.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/util/GuiUtil.java
@@ -18,6 +18,7 @@ import java.awt.font.TextAttribute;
18import java.io.IOException; 18import java.io.IOException;
19import java.net.URI; 19import java.net.URI;
20import java.net.URISyntaxException; 20import java.net.URISyntaxException;
21import java.util.ArrayList;
21import java.util.Collections; 22import java.util.Collections;
22import java.util.List; 23import java.util.List;
23import java.util.Map; 24import java.util.Map;
@@ -36,7 +37,6 @@ import javax.swing.tree.TreeNode;
36import javax.swing.tree.TreePath; 37import javax.swing.tree.TreePath;
37 38
38import com.formdev.flatlaf.extras.FlatSVGIcon; 39import com.formdev.flatlaf.extras.FlatSVGIcon;
39import com.google.common.collect.Lists;
40 40
41import cuchaz.enigma.analysis.index.EntryIndex; 41import cuchaz.enigma.analysis.index.EntryIndex;
42import cuchaz.enigma.gui.Gui; 42import cuchaz.enigma.gui.Gui;
@@ -172,7 +172,7 @@ public class GuiUtil {
172 } 172 }
173 173
174 public static TreePath getPathToRoot(TreeNode node) { 174 public static TreePath getPathToRoot(TreeNode node) {
175 List<TreeNode> nodes = Lists.newArrayList(); 175 List<TreeNode> nodes = new ArrayList<>();
176 TreeNode n = node; 176 TreeNode n = node;
177 177
178 do { 178 do {
diff --git a/enigma-swing/src/main/java/cuchaz/enigma/gui/util/History.java b/enigma-swing/src/main/java/cuchaz/enigma/gui/util/History.java
index f1a8a7a9..6ce8c831 100644
--- a/enigma-swing/src/main/java/cuchaz/enigma/gui/util/History.java
+++ b/enigma-swing/src/main/java/cuchaz/enigma/gui/util/History.java
@@ -1,12 +1,11 @@
1package cuchaz.enigma.gui.util; 1package cuchaz.enigma.gui.util;
2 2
3import java.util.ArrayDeque;
3import java.util.Deque; 4import java.util.Deque;
4 5
5import com.google.common.collect.Queues;
6
7public class History<T> { 6public class History<T> {
8 private final Deque<T> previous = Queues.newArrayDeque(); 7 private final Deque<T> previous = new ArrayDeque<>();
9 private final Deque<T> next = Queues.newArrayDeque(); 8 private final Deque<T> next = new ArrayDeque<>();
10 private T current; 9 private T current;
11 10
12 public History(T initial) { 11 public History(T initial) {
diff --git a/enigma/build.gradle b/enigma/build.gradle
index 17ea805c..6bbb200f 100644
--- a/enigma/build.gradle
+++ b/enigma/build.gradle
@@ -21,15 +21,22 @@ dependencies {
21 21
22ext.genOutputDir = file("$buildDir/generated-resources") 22ext.genOutputDir = file("$buildDir/generated-resources")
23 23
24task generateVersionFile { 24task generateResources {
25 ext.outputFile = file("$genOutputDir/version.txt") 25 ext.versionFile = file("$genOutputDir/version.txt")
26 outputs.file(outputFile) 26 ext.langsFile = file("$genOutputDir/lang/index.txt")
27 outputs.files(versionFile, langsFile)
27 doLast { 28 doLast {
28 outputFile.text = "${project.version}" 29 versionFile.text = "${project.version}"
30 langsFile.text = file("$projectDir/src/main/resources/lang")
31 .listFiles()
32 .collect { it.name }
33 .findAll { it.endsWith(".json") }
34 .collect { it.substring(0, it.length() - 5) }
35 .join("\n")
29 } 36 }
30} 37}
31 38
32sourceSets.main.output.dir genOutputDir, builtBy: generateVersionFile 39sourceSets.main.output.dir genOutputDir, builtBy: generateResources
33 40
34// Generate obfuscated JARs for tests 41// Generate obfuscated JARs for tests
35 42
diff --git a/enigma/src/main/java/cuchaz/enigma/Enigma.java b/enigma/src/main/java/cuchaz/enigma/Enigma.java
index 01967bb6..b98d71fd 100644
--- a/enigma/src/main/java/cuchaz/enigma/Enigma.java
+++ b/enigma/src/main/java/cuchaz/enigma/Enigma.java
@@ -13,17 +13,19 @@ package cuchaz.enigma;
13 13
14import java.io.IOException; 14import java.io.IOException;
15import java.nio.file.Path; 15import java.nio.file.Path;
16import java.util.ArrayList;
16import java.util.Arrays; 17import java.util.Arrays;
18import java.util.Collections;
17import java.util.HashMap; 19import java.util.HashMap;
18import java.util.HashSet; 20import java.util.HashSet;
19import java.util.LinkedHashMap; 21import java.util.LinkedHashMap;
20import java.util.List; 22import java.util.List;
21import java.util.Map; 23import java.util.Map;
24import java.util.Objects;
22import java.util.ServiceLoader; 25import java.util.ServiceLoader;
23import java.util.Set; 26import java.util.Set;
27import java.util.stream.Collectors;
24 28
25import com.google.common.base.Preconditions;
26import com.google.common.collect.ImmutableListMultimap;
27import org.objectweb.asm.Opcodes; 29import org.objectweb.asm.Opcodes;
28 30
29import cuchaz.enigma.analysis.index.JarIndex; 31import cuchaz.enigma.analysis.index.JarIndex;
@@ -108,8 +110,7 @@ public class Enigma {
108 } 110 }
109 111
110 public Builder setProfile(EnigmaProfile profile) { 112 public Builder setProfile(EnigmaProfile profile) {
111 Preconditions.checkNotNull(profile, "profile cannot be null"); 113 this.profile = Objects.requireNonNull(profile, "profile cannot be null");
112 this.profile = profile;
113 return this; 114 return this;
114 } 115 }
115 116
@@ -142,17 +143,21 @@ public class Enigma {
142 } 143 }
143 144
144 EnigmaServices buildServices() { 145 EnigmaServices buildServices() {
145 ImmutableListMultimap.Builder<EnigmaServiceType<?>, EnigmaService> services = ImmutableListMultimap.builder(); 146 Map<EnigmaServiceType<?>, List<EnigmaService>> services = new LinkedHashMap<>();
146 147
147 pendingServices.forEach((serviceType, pending) -> { 148 pendingServices.forEach((serviceType, pending) -> {
148 pending.orderings.keySet().removeAll(pending.disabled); 149 pending.orderings.keySet().removeAll(pending.disabled);
149 List<String> orderedServices = OrderingImpl.sort(serviceType.key, pending.orderings); 150 List<String> orderedServices = OrderingImpl.sort(serviceType.key, pending.orderings);
150 orderedServices.forEach(serviceId -> { 151 orderedServices.forEach(serviceId -> {
151 services.put(serviceType, pending.factories.get(serviceId).create()); 152 services.computeIfAbsent(serviceType, key -> new ArrayList<>())
153 .add(pending.factories.get(serviceId).create());
152 }); 154 });
153 }); 155 });
154 156
155 return new EnigmaServices(services.build()); 157 return new EnigmaServices(services.entrySet().stream().collect(Collectors.toUnmodifiableMap(
158 Map.Entry::getKey,
159 entry -> Collections.unmodifiableList(entry.getValue())
160 )));
156 } 161 }
157 162
158 private record PendingServices<T extends EnigmaService>( 163 private record PendingServices<T extends EnigmaService>(
diff --git a/enigma/src/main/java/cuchaz/enigma/EnigmaProfile.java b/enigma/src/main/java/cuchaz/enigma/EnigmaProfile.java
index 1bcbaa95..f0a8ab0e 100644
--- a/enigma/src/main/java/cuchaz/enigma/EnigmaProfile.java
+++ b/enigma/src/main/java/cuchaz/enigma/EnigmaProfile.java
@@ -7,10 +7,9 @@ import java.nio.file.Files;
7import java.nio.file.Path; 7import java.nio.file.Path;
8import java.util.Set; 8import java.util.Set;
9 9
10import javax.annotation.Nullable;
11
12import com.google.gson.Gson; 10import com.google.gson.Gson;
13import com.google.gson.annotations.SerializedName; 11import com.google.gson.annotations.SerializedName;
12import org.jetbrains.annotations.Nullable;
14 13
15import cuchaz.enigma.translation.mapping.serde.MappingFileNameFormat; 14import cuchaz.enigma.translation.mapping.serde.MappingFileNameFormat;
16import cuchaz.enigma.translation.mapping.serde.MappingSaveParameters; 15import cuchaz.enigma.translation.mapping.serde.MappingSaveParameters;
diff --git a/enigma/src/main/java/cuchaz/enigma/EnigmaProject.java b/enigma/src/main/java/cuchaz/enigma/EnigmaProject.java
index 1051f452..79df2fb7 100644
--- a/enigma/src/main/java/cuchaz/enigma/EnigmaProject.java
+++ b/enigma/src/main/java/cuchaz/enigma/EnigmaProject.java
@@ -11,13 +11,12 @@ import java.util.List;
11import java.util.Map; 11import java.util.Map;
12import java.util.Objects; 12import java.util.Objects;
13import java.util.concurrent.atomic.AtomicInteger; 13import java.util.concurrent.atomic.AtomicInteger;
14import java.util.function.Function;
14import java.util.jar.JarEntry; 15import java.util.jar.JarEntry;
15import java.util.jar.JarOutputStream; 16import java.util.jar.JarOutputStream;
16import java.util.stream.Collectors; 17import java.util.stream.Collectors;
17import java.util.stream.Stream; 18import java.util.stream.Stream;
18 19
19import com.google.common.base.Functions;
20import com.google.common.base.Preconditions;
21import org.objectweb.asm.ClassWriter; 20import org.objectweb.asm.ClassWriter;
22import org.objectweb.asm.tree.ClassNode; 21import org.objectweb.asm.tree.ClassNode;
23 22
@@ -56,7 +55,10 @@ public class EnigmaProject {
56 private EntryRemapper mapper; 55 private EntryRemapper mapper;
57 56
58 public EnigmaProject(Enigma enigma, List<Path> jarPaths, ClassProvider classProvider, JarIndex jarIndex, byte[] jarChecksum) { 57 public EnigmaProject(Enigma enigma, List<Path> jarPaths, ClassProvider classProvider, JarIndex jarIndex, byte[] jarChecksum) {
59 Preconditions.checkArgument(jarChecksum.length == 20); 58 if (jarChecksum.length != 20) {
59 throw new IllegalArgumentException();
60 }
61
60 this.enigma = enigma; 62 this.enigma = enigma;
61 this.jarPaths = List.copyOf(jarPaths); 63 this.jarPaths = List.copyOf(jarPaths);
62 this.classProvider = classProvider; 64 this.classProvider = classProvider;
@@ -228,7 +230,7 @@ public class EnigmaProject {
228 } 230 }
229 231
230 return null; 232 return null;
231 }).filter(Objects::nonNull).collect(Collectors.toMap(n -> n.name, Functions.identity())); 233 }).filter(Objects::nonNull).collect(Collectors.toMap(n -> n.name, Function.identity()));
232 234
233 return new JarExport(mapper, compiled); 235 return new JarExport(mapper, compiled);
234 } 236 }
diff --git a/enigma/src/main/java/cuchaz/enigma/EnigmaServices.java b/enigma/src/main/java/cuchaz/enigma/EnigmaServices.java
index bbdc6846..3681209a 100644
--- a/enigma/src/main/java/cuchaz/enigma/EnigmaServices.java
+++ b/enigma/src/main/java/cuchaz/enigma/EnigmaServices.java
@@ -1,21 +1,20 @@
1package cuchaz.enigma; 1package cuchaz.enigma;
2 2
3import java.util.List; 3import java.util.List;
4 4import java.util.Map;
5import com.google.common.collect.ImmutableListMultimap;
6 5
7import cuchaz.enigma.api.service.EnigmaService; 6import cuchaz.enigma.api.service.EnigmaService;
8import cuchaz.enigma.api.service.EnigmaServiceType; 7import cuchaz.enigma.api.service.EnigmaServiceType;
9 8
10public final class EnigmaServices { 9public final class EnigmaServices {
11 private final ImmutableListMultimap<EnigmaServiceType<?>, EnigmaService> services; 10 private final Map<EnigmaServiceType<?>, List<EnigmaService>> services;
12 11
13 EnigmaServices(ImmutableListMultimap<EnigmaServiceType<?>, EnigmaService> services) { 12 EnigmaServices(Map<EnigmaServiceType<?>, List<EnigmaService>> services) {
14 this.services = services; 13 this.services = services;
15 } 14 }
16 15
17 @SuppressWarnings("unchecked") 16 @SuppressWarnings("unchecked")
18 public <T extends EnigmaService> List<T> get(EnigmaServiceType<T> type) { 17 public <T extends EnigmaService> List<T> get(EnigmaServiceType<T> type) {
19 return (List<T>) services.get(type); 18 return (List<T>) services.getOrDefault(type, List.of());
20 } 19 }
21} 20}
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/ClassImplementationsTreeNode.java b/enigma/src/main/java/cuchaz/enigma/analysis/ClassImplementationsTreeNode.java
index 306451a0..d0d86443 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/ClassImplementationsTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/ClassImplementationsTreeNode.java
@@ -11,11 +11,10 @@
11 11
12package cuchaz.enigma.analysis; 12package cuchaz.enigma.analysis;
13 13
14import java.util.ArrayList;
14import java.util.Collection; 15import java.util.Collection;
15import java.util.List; 16import java.util.List;
16 17
17import com.google.common.collect.Lists;
18
19import cuchaz.enigma.analysis.index.InheritanceIndex; 18import cuchaz.enigma.analysis.index.InheritanceIndex;
20import cuchaz.enigma.analysis.index.JarIndex; 19import cuchaz.enigma.analysis.index.JarIndex;
21import cuchaz.enigma.translation.Translator; 20import cuchaz.enigma.translation.Translator;
@@ -52,7 +51,7 @@ public class ClassImplementationsTreeNode extends ClassTreeNode {
52 51
53 public void load(JarIndex index) { 52 public void load(JarIndex index) {
54 // get all method implementations 53 // get all method implementations
55 List<ClassImplementationsTreeNode> nodes = Lists.newArrayList(); 54 List<ClassImplementationsTreeNode> nodes = new ArrayList<>();
56 InheritanceIndex inheritanceIndex = index.getInheritanceIndex(); 55 InheritanceIndex inheritanceIndex = index.getInheritanceIndex();
57 56
58 Collection<ClassEntry> inheritors = inheritanceIndex.getChildren(this.getClassEntry()); 57 Collection<ClassEntry> inheritors = inheritanceIndex.getChildren(this.getClassEntry());
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/ClassInheritanceTreeNode.java b/enigma/src/main/java/cuchaz/enigma/analysis/ClassInheritanceTreeNode.java
index dfb2af85..bbad239b 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/ClassInheritanceTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/ClassInheritanceTreeNode.java
@@ -11,10 +11,9 @@
11 11
12package cuchaz.enigma.analysis; 12package cuchaz.enigma.analysis;
13 13
14import java.util.ArrayList;
14import java.util.List; 15import java.util.List;
15 16
16import com.google.common.collect.Lists;
17
18import cuchaz.enigma.analysis.index.InheritanceIndex; 17import cuchaz.enigma.analysis.index.InheritanceIndex;
19import cuchaz.enigma.translation.Translator; 18import cuchaz.enigma.translation.Translator;
20import cuchaz.enigma.translation.representation.entry.ClassEntry; 19import cuchaz.enigma.translation.representation.entry.ClassEntry;
@@ -53,7 +52,7 @@ public class ClassInheritanceTreeNode extends ClassTreeNode {
53 52
54 public void load(InheritanceIndex ancestries, boolean recurse) { 53 public void load(InheritanceIndex ancestries, boolean recurse) {
55 // get all the child nodes 54 // get all the child nodes
56 List<ClassInheritanceTreeNode> nodes = Lists.newArrayList(); 55 List<ClassInheritanceTreeNode> nodes = new ArrayList<>();
57 56
58 for (ClassEntry inheritor : ancestries.getChildren(this.getClassEntry())) { 57 for (ClassEntry inheritor : ancestries.getChildren(this.getClassEntry())) {
59 nodes.add(new ClassInheritanceTreeNode(translator, inheritor.getFullName())); 58 nodes.add(new ClassInheritanceTreeNode(translator, inheritor.getFullName()));
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/ClassReferenceTreeNode.java b/enigma/src/main/java/cuchaz/enigma/analysis/ClassReferenceTreeNode.java
index c76dca7b..f312efbb 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/ClassReferenceTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/ClassReferenceTreeNode.java
@@ -11,13 +11,12 @@
11 11
12package cuchaz.enigma.analysis; 12package cuchaz.enigma.analysis;
13 13
14import java.util.HashSet;
14import java.util.Set; 15import java.util.Set;
15 16
16import javax.swing.tree.DefaultMutableTreeNode; 17import javax.swing.tree.DefaultMutableTreeNode;
17import javax.swing.tree.TreeNode; 18import javax.swing.tree.TreeNode;
18 19
19import com.google.common.collect.Sets;
20
21import cuchaz.enigma.analysis.index.JarIndex; 20import cuchaz.enigma.analysis.index.JarIndex;
22import cuchaz.enigma.analysis.index.ReferenceIndex; 21import cuchaz.enigma.analysis.index.ReferenceIndex;
23import cuchaz.enigma.translation.Translator; 22import cuchaz.enigma.translation.Translator;
@@ -73,7 +72,7 @@ public class ClassReferenceTreeNode extends DefaultMutableTreeNode implements Re
73 for (Object child : this.children) { 72 for (Object child : this.children) {
74 if (child instanceof ClassReferenceTreeNode node) { 73 if (child instanceof ClassReferenceTreeNode node) {
75 // don't recurse into ancestor 74 // don't recurse into ancestor
76 Set<Entry<?>> ancestors = Sets.newHashSet(); 75 Set<Entry<?>> ancestors = new HashSet<>();
77 TreeNode n = node; 76 TreeNode n = node;
78 77
79 while (n.getParent() != null) { 78 while (n.getParent() != null) {
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/IndexTreeBuilder.java b/enigma/src/main/java/cuchaz/enigma/analysis/IndexTreeBuilder.java
index 3043577b..e9dcc666 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/IndexTreeBuilder.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/IndexTreeBuilder.java
@@ -1,10 +1,9 @@
1package cuchaz.enigma.analysis; 1package cuchaz.enigma.analysis;
2 2
3import java.util.ArrayList;
3import java.util.Collection; 4import java.util.Collection;
4import java.util.List; 5import java.util.List;
5 6
6import com.google.common.collect.Lists;
7
8import cuchaz.enigma.analysis.index.JarIndex; 7import cuchaz.enigma.analysis.index.JarIndex;
9import cuchaz.enigma.translation.Translator; 8import cuchaz.enigma.translation.Translator;
10import cuchaz.enigma.translation.mapping.EntryResolver; 9import cuchaz.enigma.translation.mapping.EntryResolver;
@@ -21,7 +20,7 @@ public class IndexTreeBuilder {
21 20
22 public ClassInheritanceTreeNode buildClassInheritance(Translator translator, ClassEntry obfClassEntry) { 21 public ClassInheritanceTreeNode buildClassInheritance(Translator translator, ClassEntry obfClassEntry) {
23 // get the root node 22 // get the root node
24 List<String> ancestry = Lists.newArrayList(); 23 List<String> ancestry = new ArrayList<>();
25 ancestry.add(obfClassEntry.getFullName()); 24 ancestry.add(obfClassEntry.getFullName());
26 25
27 for (ClassEntry classEntry : index.getInheritanceIndex().getAncestors(obfClassEntry)) { 26 for (ClassEntry classEntry : index.getInheritanceIndex().getAncestors(obfClassEntry)) {
@@ -62,7 +61,7 @@ public class IndexTreeBuilder {
62 EntryResolver resolver = index.getEntryResolver(); 61 EntryResolver resolver = index.getEntryResolver();
63 Collection<MethodEntry> resolvedEntries = resolver.resolveEntry(obfMethodEntry, ResolutionStrategy.RESOLVE_ROOT); 62 Collection<MethodEntry> resolvedEntries = resolver.resolveEntry(obfMethodEntry, ResolutionStrategy.RESOLVE_ROOT);
64 63
65 List<MethodImplementationsTreeNode> nodes = Lists.newArrayList(); 64 List<MethodImplementationsTreeNode> nodes = new ArrayList<>();
66 65
67 for (MethodEntry resolvedEntry : resolvedEntries) { 66 for (MethodEntry resolvedEntry : resolvedEntries) {
68 MethodImplementationsTreeNode node = new MethodImplementationsTreeNode(translator, resolvedEntry); 67 MethodImplementationsTreeNode node = new MethodImplementationsTreeNode(translator, resolvedEntry);
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/MethodImplementationsTreeNode.java b/enigma/src/main/java/cuchaz/enigma/analysis/MethodImplementationsTreeNode.java
index d5a34cd2..57767af4 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/MethodImplementationsTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/MethodImplementationsTreeNode.java
@@ -11,11 +11,10 @@
11 11
12package cuchaz.enigma.analysis; 12package cuchaz.enigma.analysis;
13 13
14import java.util.ArrayList;
14import java.util.Collection; 15import java.util.Collection;
15import java.util.List; 16import java.util.List;
16 17
17import com.google.common.collect.Lists;
18
19import cuchaz.enigma.analysis.index.EntryIndex; 18import cuchaz.enigma.analysis.index.EntryIndex;
20import cuchaz.enigma.analysis.index.InheritanceIndex; 19import cuchaz.enigma.analysis.index.InheritanceIndex;
21import cuchaz.enigma.analysis.index.JarIndex; 20import cuchaz.enigma.analysis.index.JarIndex;
@@ -59,7 +58,7 @@ public class MethodImplementationsTreeNode extends MethodTreeNode {
59 58
60 public void load(JarIndex index) { 59 public void load(JarIndex index) {
61 // get all method implementations 60 // get all method implementations
62 List<MethodImplementationsTreeNode> nodes = Lists.newArrayList(); 61 List<MethodImplementationsTreeNode> nodes = new ArrayList<>();
63 EntryIndex entryIndex = index.getEntryIndex(); 62 EntryIndex entryIndex = index.getEntryIndex();
64 InheritanceIndex inheritanceIndex = index.getInheritanceIndex(); 63 InheritanceIndex inheritanceIndex = index.getInheritanceIndex();
65 64
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/MethodReferenceTreeNode.java b/enigma/src/main/java/cuchaz/enigma/analysis/MethodReferenceTreeNode.java
index fc58c6d0..6e2b90c6 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/MethodReferenceTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/MethodReferenceTreeNode.java
@@ -13,13 +13,12 @@ package cuchaz.enigma.analysis;
13 13
14import java.util.ArrayList; 14import java.util.ArrayList;
15import java.util.Collection; 15import java.util.Collection;
16import java.util.HashSet;
16import java.util.Set; 17import java.util.Set;
17 18
18import javax.swing.tree.DefaultMutableTreeNode; 19import javax.swing.tree.DefaultMutableTreeNode;
19import javax.swing.tree.TreeNode; 20import javax.swing.tree.TreeNode;
20 21
21import com.google.common.collect.Sets;
22
23import cuchaz.enigma.analysis.index.JarIndex; 22import cuchaz.enigma.analysis.index.JarIndex;
24import cuchaz.enigma.analysis.index.ReferenceIndex; 23import cuchaz.enigma.analysis.index.ReferenceIndex;
25import cuchaz.enigma.translation.Translator; 24import cuchaz.enigma.translation.Translator;
@@ -76,7 +75,7 @@ public class MethodReferenceTreeNode extends DefaultMutableTreeNode implements R
76 for (Object child : this.children) { 75 for (Object child : this.children) {
77 if (child instanceof MethodReferenceTreeNode node) { 76 if (child instanceof MethodReferenceTreeNode node) {
78 // don't recurse into ancestor 77 // don't recurse into ancestor
79 Set<Entry<?>> ancestors = Sets.newHashSet(); 78 Set<Entry<?>> ancestors = new HashSet<>();
80 TreeNode n = node; 79 TreeNode n = node;
81 80
82 while (n.getParent() != null) { 81 while (n.getParent() != null) {
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/index/BridgeMethodIndex.java b/enigma/src/main/java/cuchaz/enigma/analysis/index/BridgeMethodIndex.java
index 4a98c566..adb48bab 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/index/BridgeMethodIndex.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/index/BridgeMethodIndex.java
@@ -8,7 +8,7 @@ import java.util.Map;
8import java.util.concurrent.ConcurrentHashMap; 8import java.util.concurrent.ConcurrentHashMap;
9import java.util.concurrent.ConcurrentMap; 9import java.util.concurrent.ConcurrentMap;
10 10
11import javax.annotation.Nullable; 11import org.jetbrains.annotations.Nullable;
12 12
13import cuchaz.enigma.translation.representation.AccessFlags; 13import cuchaz.enigma.translation.representation.AccessFlags;
14import cuchaz.enigma.translation.representation.MethodDescriptor; 14import cuchaz.enigma.translation.representation.MethodDescriptor;
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/index/EntryIndex.java b/enigma/src/main/java/cuchaz/enigma/analysis/index/EntryIndex.java
index 9e65fc30..f12bfb81 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/index/EntryIndex.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/index/EntryIndex.java
@@ -4,7 +4,7 @@ import java.util.Collection;
4import java.util.concurrent.ConcurrentHashMap; 4import java.util.concurrent.ConcurrentHashMap;
5import java.util.concurrent.ConcurrentMap; 5import java.util.concurrent.ConcurrentMap;
6 6
7import javax.annotation.Nullable; 7import org.jetbrains.annotations.Nullable;
8 8
9import cuchaz.enigma.translation.representation.AccessFlags; 9import cuchaz.enigma.translation.representation.AccessFlags;
10import cuchaz.enigma.translation.representation.entry.ClassDefEntry; 10import cuchaz.enigma.translation.representation.entry.ClassDefEntry;
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/index/InheritanceIndex.java b/enigma/src/main/java/cuchaz/enigma/analysis/index/InheritanceIndex.java
index 9841aa69..2b29edc9 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/index/InheritanceIndex.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/index/InheritanceIndex.java
@@ -21,8 +21,6 @@ import java.util.Set;
21import java.util.concurrent.ConcurrentHashMap; 21import java.util.concurrent.ConcurrentHashMap;
22import java.util.concurrent.ConcurrentMap; 22import java.util.concurrent.ConcurrentMap;
23 23
24import com.google.common.collect.Sets;
25
26import cuchaz.enigma.translation.representation.entry.ClassDefEntry; 24import cuchaz.enigma.translation.representation.entry.ClassDefEntry;
27import cuchaz.enigma.translation.representation.entry.ClassEntry; 25import cuchaz.enigma.translation.representation.entry.ClassEntry;
28 26
@@ -86,7 +84,7 @@ public class InheritanceIndex implements JarIndexer {
86 } 84 }
87 85
88 public Set<ClassEntry> getAncestors(ClassEntry classEntry) { 86 public Set<ClassEntry> getAncestors(ClassEntry classEntry) {
89 Set<ClassEntry> ancestors = Sets.newHashSet(); 87 Set<ClassEntry> ancestors = new HashSet<>();
90 88
91 LinkedList<ClassEntry> ancestorQueue = new LinkedList<>(); 89 LinkedList<ClassEntry> ancestorQueue = new LinkedList<>();
92 ancestorQueue.push(classEntry); 90 ancestorQueue.push(classEntry);
diff --git a/enigma/src/main/java/cuchaz/enigma/analysis/index/PackageVisibilityIndex.java b/enigma/src/main/java/cuchaz/enigma/analysis/index/PackageVisibilityIndex.java
index a2ba0298..b2d6b73d 100644
--- a/enigma/src/main/java/cuchaz/enigma/analysis/index/PackageVisibilityIndex.java
+++ b/enigma/src/main/java/cuchaz/enigma/analysis/index/PackageVisibilityIndex.java
@@ -1,6 +1,8 @@
1package cuchaz.enigma.analysis.index; 1package cuchaz.enigma.analysis.index;
2 2
3import java.util.ArrayList;
3import java.util.Collection; 4import java.util.Collection;
5import java.util.HashMap;
4import java.util.HashSet; 6import java.util.HashSet;
5import java.util.Iterator; 7import java.util.Iterator;
6import java.util.List; 8import java.util.List;
@@ -9,10 +11,6 @@ import java.util.Set;
9import java.util.concurrent.ConcurrentHashMap; 11import java.util.concurrent.ConcurrentHashMap;
10import java.util.concurrent.ConcurrentMap; 12import java.util.concurrent.ConcurrentMap;
11 13
12import com.google.common.collect.Lists;
13import com.google.common.collect.Maps;
14import com.google.common.collect.Sets;
15
16import cuchaz.enigma.analysis.EntryReference; 14import cuchaz.enigma.analysis.EntryReference;
17import cuchaz.enigma.analysis.ReferenceTargetType; 15import cuchaz.enigma.analysis.ReferenceTargetType;
18import cuchaz.enigma.translation.representation.AccessFlags; 16import cuchaz.enigma.translation.representation.AccessFlags;
@@ -48,8 +46,8 @@ public class PackageVisibilityIndex implements JarIndexer {
48 } 46 }
49 47
50 private final ConcurrentMap<ClassEntry, List<ClassEntry>> connections = new ConcurrentHashMap<>(); 48 private final ConcurrentMap<ClassEntry, List<ClassEntry>> connections = new ConcurrentHashMap<>();
51 private final List<Set<ClassEntry>> partitions = Lists.newArrayList(); 49 private final List<Set<ClassEntry>> partitions = new ArrayList<>();
52 private final Map<ClassEntry, Set<ClassEntry>> classPartitions = Maps.newHashMap(); 50 private final Map<ClassEntry, Set<ClassEntry>> classPartitions = new HashMap<>();
53 51
54 private void addConnection(ClassEntry classA, ClassEntry classB) { 52 private void addConnection(ClassEntry classA, ClassEntry classB) {
55 if (classA != classB) { 53 if (classA != classB) {
@@ -132,14 +130,14 @@ public class PackageVisibilityIndex implements JarIndexer {
132 } 130 }
133 131
134 private void addPartitions(EntryIndex entryIndex) { 132 private void addPartitions(EntryIndex entryIndex) {
135 Set<ClassEntry> unassignedClasses = Sets.newHashSet(entryIndex.getClasses()); 133 Set<ClassEntry> unassignedClasses = new HashSet<>(entryIndex.getClasses());
136 134
137 while (!unassignedClasses.isEmpty()) { 135 while (!unassignedClasses.isEmpty()) {
138 Iterator<ClassEntry> iterator = unassignedClasses.iterator(); 136 Iterator<ClassEntry> iterator = unassignedClasses.iterator();
139 ClassEntry initialEntry = iterator.next(); 137 ClassEntry initialEntry = iterator.next();
140 iterator.remove(); 138 iterator.remove();
141 139
142 HashSet<ClassEntry> partition = Sets.newHashSet(); 140 HashSet<ClassEntry> partition = new HashSet<>();
143 partition.add(initialEntry); 141 partition.add(initialEntry);
144 buildPartition(unassignedClasses, partition, initialEntry); 142 buildPartition(unassignedClasses, partition, initialEntry);
145 partitions.add(partition); 143 partitions.add(partition);
diff --git a/enigma/src/main/java/cuchaz/enigma/bytecode/translators/LocalVariableFixVisitor.java b/enigma/src/main/java/cuchaz/enigma/bytecode/translators/LocalVariableFixVisitor.java
index dc399e53..d31adddc 100644
--- a/enigma/src/main/java/cuchaz/enigma/bytecode/translators/LocalVariableFixVisitor.java
+++ b/enigma/src/main/java/cuchaz/enigma/bytecode/translators/LocalVariableFixVisitor.java
@@ -4,7 +4,6 @@ import java.util.HashMap;
4import java.util.List; 4import java.util.List;
5import java.util.Map; 5import java.util.Map;
6 6
7import com.google.common.base.CharMatcher;
8import org.objectweb.asm.ClassVisitor; 7import org.objectweb.asm.ClassVisitor;
9import org.objectweb.asm.Label; 8import org.objectweb.asm.Label;
10import org.objectweb.asm.MethodVisitor; 9import org.objectweb.asm.MethodVisitor;
@@ -76,7 +75,7 @@ public class LocalVariableFixVisitor extends ClassVisitor {
76 } 75 }
77 76
78 private boolean isInvalidName(String name) { 77 private boolean isInvalidName(String name) {
79 return name == null || name.isEmpty() || !CharMatcher.ascii().matchesAllOf(name); 78 return name == null || name.isEmpty() || name.chars().anyMatch(ch -> ch < 0x21 || ch > 0x7E);
80 } 79 }
81 80
82 @Override 81 @Override
diff --git a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandle.java b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandle.java
index 2a1643e9..f2c77a89 100644
--- a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandle.java
+++ b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandle.java
@@ -2,7 +2,7 @@ package cuchaz.enigma.classhandle;
2 2
3import java.util.concurrent.CompletableFuture; 3import java.util.concurrent.CompletableFuture;
4 4
5import javax.annotation.Nullable; 5import org.jetbrains.annotations.Nullable;
6 6
7import cuchaz.enigma.events.ClassHandleListener; 7import cuchaz.enigma.events.ClassHandleListener;
8import cuchaz.enigma.source.DecompiledClassSource; 8import cuchaz.enigma.source.DecompiledClassSource;
diff --git a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleError.java b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleError.java
index ce6b23f8..6ec7c914 100644
--- a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleError.java
+++ b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleError.java
@@ -3,7 +3,7 @@ package cuchaz.enigma.classhandle;
3import java.io.ByteArrayOutputStream; 3import java.io.ByteArrayOutputStream;
4import java.io.PrintStream; 4import java.io.PrintStream;
5 5
6import javax.annotation.Nullable; 6import org.jetbrains.annotations.Nullable;
7 7
8public final class ClassHandleError { 8public final class ClassHandleError {
9 public final Type type; 9 public final Type type;
diff --git a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleProvider.java b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleProvider.java
index f18be672..f4bbb1da 100644
--- a/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classhandle/ClassHandleProvider.java
@@ -18,7 +18,7 @@ import java.util.concurrent.atomic.AtomicInteger;
18import java.util.concurrent.locks.ReadWriteLock; 18import java.util.concurrent.locks.ReadWriteLock;
19import java.util.concurrent.locks.ReentrantReadWriteLock; 19import java.util.concurrent.locks.ReentrantReadWriteLock;
20 20
21import javax.annotation.Nullable; 21import org.jetbrains.annotations.Nullable;
22 22
23import cuchaz.enigma.EnigmaProject; 23import cuchaz.enigma.EnigmaProject;
24import cuchaz.enigma.classprovider.CachingClassProvider; 24import cuchaz.enigma.classprovider.CachingClassProvider;
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/CachingClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/CachingClassProvider.java
index 28a93927..9318813d 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/CachingClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/CachingClassProvider.java
@@ -1,22 +1,23 @@
1package cuchaz.enigma.classprovider; 1package cuchaz.enigma.classprovider;
2 2
3import java.util.Collection; 3import java.util.Collection;
4import java.util.Optional; 4import java.util.Iterator;
5import java.util.concurrent.ExecutionException; 5import java.util.Map;
6import java.util.concurrent.TimeUnit; 6import java.util.Objects;
7import java.util.concurrent.ConcurrentHashMap;
7 8
8import javax.annotation.Nullable; 9import org.jetbrains.annotations.Nullable;
9
10import com.google.common.cache.Cache;
11import com.google.common.cache.CacheBuilder;
12import org.objectweb.asm.tree.ClassNode; 10import org.objectweb.asm.tree.ClassNode;
13 11
14/** 12/**
15 * Wraps a ClassProvider to provide caching and synchronization. 13 * Wraps a ClassProvider to provide caching and synchronization.
16 */ 14 */
17public class CachingClassProvider implements ClassProvider { 15public class CachingClassProvider implements ClassProvider {
16 private static final long EXPIRE_AFTER = 1 * 60 * 1000; // one minute
17 private static final long MAX_SIZE = 128;
18 private final ClassProvider classProvider; 18 private final ClassProvider classProvider;
19 private final Cache<String, Optional<ClassNode>> cache = CacheBuilder.newBuilder().maximumSize(128).expireAfterAccess(1, TimeUnit.MINUTES).concurrencyLevel(1).build(); 19 private long lastPruneTime = 0;
20 private final ConcurrentHashMap<String, CacheEntry> cache = new ConcurrentHashMap<>();
20 21
21 public CachingClassProvider(ClassProvider classProvider) { 22 public CachingClassProvider(ClassProvider classProvider) {
22 this.classProvider = classProvider; 23 this.classProvider = classProvider;
@@ -30,10 +31,54 @@ public class CachingClassProvider implements ClassProvider {
30 @Override 31 @Override
31 @Nullable 32 @Nullable
32 public ClassNode get(String name) { 33 public ClassNode get(String name) {
33 try { 34 final long time = System.currentTimeMillis();
34 return cache.get(name, () -> Optional.ofNullable(classProvider.get(name))).orElse(null); 35 boolean prune = false;
35 } catch (ExecutionException e) { 36
36 throw new RuntimeException(e); 37 if (lastPruneTime + 2 * EXPIRE_AFTER < time) {
38 synchronized (cache) {
39 if (lastPruneTime + 2 * EXPIRE_AFTER < time) {
40 lastPruneTime = time;
41 prune = true;
42 }
43 }
44 }
45
46 if (prune) {
47 cache.values().removeIf(value -> value.addTime + EXPIRE_AFTER < time);
48 }
49
50 if (cache.size() > MAX_SIZE) {
51 synchronized (cache) {
52 if (cache.size() > MAX_SIZE) {
53 Iterator<Map.Entry<String, CacheEntry>> iterator = cache.entrySet().iterator();
54 iterator.next();
55 iterator.remove();
56 }
57 }
58 }
59
60 CacheEntry entry = cache.computeIfAbsent(name, key -> new CacheEntry(time, classProvider.get(key)));
61 entry.addTime = time;
62 return entry.classNode;
63 }
64
65 private static final class CacheEntry {
66 private long addTime;
67 private final @Nullable ClassNode classNode;
68
69 private CacheEntry(long addTime, @Nullable ClassNode classNode) {
70 this.addTime = addTime;
71 this.classNode = classNode;
72 }
73
74 @Override
75 public boolean equals(Object obj) {
76 return obj instanceof CacheEntry ce && Objects.equals(classNode, ce.classNode);
77 }
78
79 @Override
80 public int hashCode() {
81 return Objects.hash(addTime, classNode);
37 } 82 }
38 } 83 }
39} 84}
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/ClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/ClassProvider.java
index 069e0a86..a299c1d3 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/ClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/ClassProvider.java
@@ -2,8 +2,7 @@ package cuchaz.enigma.classprovider;
2 2
3import java.util.Collection; 3import java.util.Collection;
4 4
5import javax.annotation.Nullable; 5import org.jetbrains.annotations.Nullable;
6
7import org.objectweb.asm.tree.ClassNode; 6import org.objectweb.asm.tree.ClassNode;
8 7
9public interface ClassProvider { 8public interface ClassProvider {
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/ClasspathClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/ClasspathClassProvider.java
index b035cee5..19a7d656 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/ClasspathClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/ClasspathClassProvider.java
@@ -5,8 +5,7 @@ import java.io.InputStream;
5import java.util.Collection; 5import java.util.Collection;
6import java.util.Collections; 6import java.util.Collections;
7 7
8import javax.annotation.Nullable; 8import org.jetbrains.annotations.Nullable;
9
10import org.objectweb.asm.ClassReader; 9import org.objectweb.asm.ClassReader;
11import org.objectweb.asm.tree.ClassNode; 10import org.objectweb.asm.tree.ClassNode;
12 11
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/CombiningClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/CombiningClassProvider.java
index 1b20b8f0..72708176 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/CombiningClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/CombiningClassProvider.java
@@ -4,8 +4,7 @@ import java.util.Arrays;
4import java.util.Collection; 4import java.util.Collection;
5import java.util.stream.Collectors; 5import java.util.stream.Collectors;
6 6
7import javax.annotation.Nullable; 7import org.jetbrains.annotations.Nullable;
8
9import org.objectweb.asm.tree.ClassNode; 8import org.objectweb.asm.tree.ClassNode;
10 9
11/** 10/**
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/JarClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/JarClassProvider.java
index 5dec5beb..391d43a9 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/JarClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/JarClassProvider.java
@@ -5,11 +5,12 @@ import java.nio.file.FileSystem;
5import java.nio.file.FileSystems; 5import java.nio.file.FileSystems;
6import java.nio.file.Files; 6import java.nio.file.Files;
7import java.nio.file.Path; 7import java.nio.file.Path;
8import java.util.Collections;
9import java.util.HashSet;
8import java.util.Set; 10import java.util.Set;
11import java.util.stream.Stream;
9 12
10import javax.annotation.Nullable; 13import org.jetbrains.annotations.Nullable;
11
12import com.google.common.collect.ImmutableSet;
13import org.objectweb.asm.tree.ClassNode; 14import org.objectweb.asm.tree.ClassNode;
14 15
15import cuchaz.enigma.utils.AsmUtil; 16import cuchaz.enigma.utils.AsmUtil;
@@ -26,19 +27,21 @@ public class JarClassProvider implements AutoCloseable, ClassProvider {
26 this.classNames = collectClassNames(fileSystem); 27 this.classNames = collectClassNames(fileSystem);
27 } 28 }
28 29
29 private static ImmutableSet<String> collectClassNames(FileSystem fileSystem) throws IOException { 30 private static Set<String> collectClassNames(FileSystem fileSystem) throws IOException {
30 ImmutableSet.Builder<String> classNames = ImmutableSet.builder(); 31 Set<String> classNames = new HashSet<>();
31 32
32 for (Path root : fileSystem.getRootDirectories()) { 33 for (Path root : fileSystem.getRootDirectories()) {
33 Files.walk(root).map(Path::toString).forEach(path -> { 34 try (Stream<Path> stream = Files.walk(root)) {
34 if (path.endsWith(".class")) { 35 stream.map(Path::toString).forEach(path -> {
35 String name = path.substring(1, path.length() - ".class".length()); 36 if (path.endsWith(".class")) {
36 classNames.add(name); 37 String name = path.substring(1, path.length() - ".class".length());
37 } 38 classNames.add(name);
38 }); 39 }
40 });
41 }
39 } 42 }
40 43
41 return classNames.build(); 44 return Collections.unmodifiableSet(classNames);
42 } 45 }
43 46
44 @Override 47 @Override
diff --git a/enigma/src/main/java/cuchaz/enigma/classprovider/ObfuscationFixClassProvider.java b/enigma/src/main/java/cuchaz/enigma/classprovider/ObfuscationFixClassProvider.java
index 543ce48c..b68eaf11 100644
--- a/enigma/src/main/java/cuchaz/enigma/classprovider/ObfuscationFixClassProvider.java
+++ b/enigma/src/main/java/cuchaz/enigma/classprovider/ObfuscationFixClassProvider.java
@@ -2,8 +2,7 @@ package cuchaz.enigma.classprovider;
2 2
3import java.util.Collection; 3import java.util.Collection;
4 4
5import javax.annotation.Nullable; 5import org.jetbrains.annotations.Nullable;
6
7import org.objectweb.asm.ClassVisitor; 6import org.objectweb.asm.ClassVisitor;
8import org.objectweb.asm.Opcodes; 7import org.objectweb.asm.Opcodes;
9import org.objectweb.asm.tree.AbstractInsnNode; 8import org.objectweb.asm.tree.AbstractInsnNode;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/DecompiledClassSource.java b/enigma/src/main/java/cuchaz/enigma/source/DecompiledClassSource.java
index 9475d743..4f78e9ce 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/DecompiledClassSource.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/DecompiledClassSource.java
@@ -6,7 +6,7 @@ import java.util.List;
6import java.util.Map; 6import java.util.Map;
7import java.util.Optional; 7import java.util.Optional;
8 8
9import javax.annotation.Nullable; 9import org.jetbrains.annotations.Nullable;
10 10
11import cuchaz.enigma.EnigmaProject; 11import cuchaz.enigma.EnigmaProject;
12import cuchaz.enigma.EnigmaServices; 12import cuchaz.enigma.EnigmaServices;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/Decompiler.java b/enigma/src/main/java/cuchaz/enigma/source/Decompiler.java
index b31dcc43..9b3fa303 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/Decompiler.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/Decompiler.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.source; 1package cuchaz.enigma.source;
2 2
3import org.checkerframework.checker.nullness.qual.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.translation.mapping.EntryRemapper; 5import cuchaz.enigma.translation.mapping.EntryRemapper;
6 6
diff --git a/enigma/src/main/java/cuchaz/enigma/source/SourceIndex.java b/enigma/src/main/java/cuchaz/enigma/source/SourceIndex.java
index e9d928e9..a38c6f55 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/SourceIndex.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/SourceIndex.java
@@ -1,15 +1,12 @@
1package cuchaz.enigma.source; 1package cuchaz.enigma.source;
2 2
3import java.util.ArrayList;
3import java.util.Collection; 4import java.util.Collection;
5import java.util.HashMap;
4import java.util.List; 6import java.util.List;
5import java.util.Map; 7import java.util.Map;
6import java.util.TreeMap; 8import java.util.TreeMap;
7 9
8import com.google.common.collect.HashMultimap;
9import com.google.common.collect.Lists;
10import com.google.common.collect.Maps;
11import com.google.common.collect.Multimap;
12
13import cuchaz.enigma.analysis.EntryReference; 10import cuchaz.enigma.analysis.EntryReference;
14import cuchaz.enigma.translation.mapping.EntryResolver; 11import cuchaz.enigma.translation.mapping.EntryResolver;
15import cuchaz.enigma.translation.mapping.ResolutionStrategy; 12import cuchaz.enigma.translation.mapping.ResolutionStrategy;
@@ -19,13 +16,13 @@ public class SourceIndex {
19 private String source; 16 private String source;
20 private List<Integer> lineOffsets; 17 private List<Integer> lineOffsets;
21 private final TreeMap<Token, EntryReference<Entry<?>, Entry<?>>> tokenToReference; 18 private final TreeMap<Token, EntryReference<Entry<?>, Entry<?>>> tokenToReference;
22 private final Multimap<EntryReference<Entry<?>, Entry<?>>, Token> referenceToTokens; 19 private final Map<EntryReference<Entry<?>, Entry<?>>, Collection<Token>> referenceToTokens;
23 private final Map<Entry<?>, Token> declarationToToken; 20 private final Map<Entry<?>, Token> declarationToToken;
24 21
25 public SourceIndex() { 22 public SourceIndex() {
26 tokenToReference = new TreeMap<>(); 23 tokenToReference = new TreeMap<>();
27 referenceToTokens = HashMultimap.create(); 24 referenceToTokens = new HashMap<>();
28 declarationToToken = Maps.newHashMap(); 25 declarationToToken = new HashMap<>();
29 } 26 }
30 27
31 public SourceIndex(String source) { 28 public SourceIndex(String source) {
@@ -35,7 +32,7 @@ public class SourceIndex {
35 32
36 public void setSource(String source) { 33 public void setSource(String source) {
37 this.source = source; 34 this.source = source;
38 lineOffsets = Lists.newArrayList(); 35 lineOffsets = new ArrayList<>();
39 lineOffsets.add(0); 36 lineOffsets.add(0);
40 37
41 for (int i = 0; i < this.source.length(); i++) { 38 for (int i = 0; i < this.source.length(); i++) {
@@ -87,8 +84,10 @@ public class SourceIndex {
87 if (token != null) { 84 if (token != null) {
88 EntryReference<Entry<?>, Entry<?>> reference = new EntryReference<>(deobfEntry, token.text); 85 EntryReference<Entry<?>, Entry<?>> reference = new EntryReference<>(deobfEntry, token.text);
89 tokenToReference.put(token, reference); 86 tokenToReference.put(token, reference);
90 referenceToTokens.put(reference, token); 87 referenceToTokens.computeIfAbsent(reference, key -> new ArrayList<>())
91 referenceToTokens.put(EntryReference.declaration(deobfEntry, token.text), token); 88 .add(token);
89 referenceToTokens.computeIfAbsent(EntryReference.declaration(deobfEntry, token.text), key -> new ArrayList<>())
90 .add(token);
92 declarationToToken.put(deobfEntry, token); 91 declarationToToken.put(deobfEntry, token);
93 } 92 }
94 } 93 }
@@ -120,28 +119,30 @@ public class SourceIndex {
120 } 119 }
121 120
122 public Collection<Token> getReferenceTokens(EntryReference<Entry<?>, Entry<?>> deobfReference) { 121 public Collection<Token> getReferenceTokens(EntryReference<Entry<?>, Entry<?>> deobfReference) {
123 return referenceToTokens.get(deobfReference); 122 return referenceToTokens.getOrDefault(deobfReference, List.of());
124 } 123 }
125 124
126 public void addReference(Token token, Entry<?> deobfEntry, Entry<?> deobfContext) { 125 public void addReference(Token token, Entry<?> deobfEntry, Entry<?> deobfContext) {
127 if (token != null) { 126 if (token != null) {
128 EntryReference<Entry<?>, Entry<?>> deobfReference = new EntryReference<>(deobfEntry, token.text, deobfContext); 127 EntryReference<Entry<?>, Entry<?>> deobfReference = new EntryReference<>(deobfEntry, token.text, deobfContext);
129 tokenToReference.put(token, deobfReference); 128 tokenToReference.put(token, deobfReference);
130 referenceToTokens.put(deobfReference, token); 129 referenceToTokens.computeIfAbsent(deobfReference, key -> new ArrayList<>())
130 .add(token);
131 } 131 }
132 } 132 }
133 133
134 public void resolveReferences(EntryResolver resolver) { 134 public void resolveReferences(EntryResolver resolver) {
135 // resolve all the classes in the source references 135 // resolve all the classes in the source references
136 for (Token token : Lists.newArrayList(referenceToTokens.values())) { 136 for (Token token : referenceToTokens.values().stream().flatMap(Collection::stream).toList()) {
137 EntryReference<Entry<?>, Entry<?>> reference = tokenToReference.get(token); 137 EntryReference<Entry<?>, Entry<?>> reference = tokenToReference.get(token);
138 EntryReference<Entry<?>, Entry<?>> resolvedReference = resolver.resolveFirstReference(reference, ResolutionStrategy.RESOLVE_CLOSEST); 138 EntryReference<Entry<?>, Entry<?>> resolvedReference = resolver.resolveFirstReference(reference, ResolutionStrategy.RESOLVE_CLOSEST);
139 139
140 // replace the reference 140 // replace the reference
141 tokenToReference.replace(token, resolvedReference); 141 tokenToReference.replace(token, resolvedReference);
142 142
143 Collection<Token> tokens = referenceToTokens.removeAll(reference); 143 Collection<Token> tokens = referenceToTokens.remove(reference);
144 referenceToTokens.putAll(resolvedReference, tokens); 144 referenceToTokens.computeIfAbsent(resolvedReference, key -> new ArrayList<>())
145 .addAll(tokens);
145 } 146 }
146 } 147 }
147 148
@@ -152,13 +153,14 @@ public class SourceIndex {
152 remapped.declarationToToken.put(entry.getKey(), result.getRemappedToken(entry.getValue())); 153 remapped.declarationToToken.put(entry.getKey(), result.getRemappedToken(entry.getValue()));
153 } 154 }
154 155
155 for (Map.Entry<EntryReference<Entry<?>, Entry<?>>, Collection<Token>> entry : referenceToTokens.asMap().entrySet()) { 156 for (Map.Entry<EntryReference<Entry<?>, Entry<?>>, Collection<Token>> entry : referenceToTokens.entrySet()) {
156 EntryReference<Entry<?>, Entry<?>> reference = entry.getKey(); 157 EntryReference<Entry<?>, Entry<?>> reference = entry.getKey();
157 Collection<Token> oldTokens = entry.getValue(); 158 Collection<Token> oldTokens = entry.getValue();
158 159
159 Collection<Token> newTokens = oldTokens.stream().map(result::getRemappedToken).toList(); 160 Collection<Token> newTokens = oldTokens.stream().map(result::getRemappedToken).toList();
160 161
161 remapped.referenceToTokens.putAll(reference, newTokens); 162 remapped.referenceToTokens.computeIfAbsent(reference, key -> new ArrayList<>())
163 .addAll(newTokens);
162 } 164 }
163 165
164 for (Map.Entry<Token, EntryReference<Entry<?>, Entry<?>>> entry : tokenToReference.entrySet()) { 166 for (Map.Entry<Token, EntryReference<Entry<?>, Entry<?>>> entry : tokenToReference.entrySet()) {
diff --git a/enigma/src/main/java/cuchaz/enigma/source/bytecode/BytecodeDecompiler.java b/enigma/src/main/java/cuchaz/enigma/source/bytecode/BytecodeDecompiler.java
index 6461d20e..e970d3ae 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/bytecode/BytecodeDecompiler.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/bytecode/BytecodeDecompiler.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.source.bytecode; 1package cuchaz.enigma.source.bytecode;
2 2
3import org.checkerframework.checker.nullness.qual.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.classprovider.ClassProvider; 5import cuchaz.enigma.classprovider.ClassProvider;
6import cuchaz.enigma.source.Decompiler; 6import cuchaz.enigma.source.Decompiler;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDecompiler.java b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDecompiler.java
index 2d9784b5..5cd11046 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDecompiler.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDecompiler.java
@@ -9,7 +9,7 @@ import org.benf.cfr.reader.bytecode.analysis.parse.utils.Pair;
9import org.benf.cfr.reader.util.AnalysisType; 9import org.benf.cfr.reader.util.AnalysisType;
10import org.benf.cfr.reader.util.getopt.Options; 10import org.benf.cfr.reader.util.getopt.Options;
11import org.benf.cfr.reader.util.getopt.OptionsImpl; 11import org.benf.cfr.reader.util.getopt.OptionsImpl;
12import org.checkerframework.checker.nullness.qual.Nullable; 12import org.jetbrains.annotations.Nullable;
13import org.objectweb.asm.tree.ClassNode; 13import org.objectweb.asm.tree.ClassNode;
14 14
15import cuchaz.enigma.classprovider.ClassProvider; 15import cuchaz.enigma.classprovider.ClassProvider;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDumper.java b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDumper.java
index 950f518b..d90d7bd6 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDumper.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrDumper.java
@@ -25,7 +25,7 @@ import org.benf.cfr.reader.util.output.IllegalIdentifierDump;
25import org.benf.cfr.reader.util.output.MovableDumperContext; 25import org.benf.cfr.reader.util.output.MovableDumperContext;
26import org.benf.cfr.reader.util.output.StringStreamDumper; 26import org.benf.cfr.reader.util.output.StringStreamDumper;
27import org.benf.cfr.reader.util.output.TypeContext; 27import org.benf.cfr.reader.util.output.TypeContext;
28import org.checkerframework.checker.nullness.qual.Nullable; 28import org.jetbrains.annotations.Nullable;
29 29
30import cuchaz.enigma.source.SourceIndex; 30import cuchaz.enigma.source.SourceIndex;
31import cuchaz.enigma.source.SourceSettings; 31import cuchaz.enigma.source.SourceSettings;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrSource.java b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrSource.java
index cf6c52fd..e5db78a6 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrSource.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/cfr/CfrSource.java
@@ -11,7 +11,7 @@ import org.benf.cfr.reader.util.CannotLoadClassException;
11import org.benf.cfr.reader.util.collections.ListFactory; 11import org.benf.cfr.reader.util.collections.ListFactory;
12import org.benf.cfr.reader.util.getopt.Options; 12import org.benf.cfr.reader.util.getopt.Options;
13import org.benf.cfr.reader.util.getopt.OptionsImpl; 13import org.benf.cfr.reader.util.getopt.OptionsImpl;
14import org.checkerframework.checker.nullness.qual.Nullable; 14import org.jetbrains.annotations.Nullable;
15 15
16import cuchaz.enigma.source.Source; 16import cuchaz.enigma.source.Source;
17import cuchaz.enigma.source.SourceIndex; 17import cuchaz.enigma.source.SourceIndex;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/procyon/ProcyonDecompiler.java b/enigma/src/main/java/cuchaz/enigma/source/procyon/ProcyonDecompiler.java
index 3ba112ff..76b6b488 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/procyon/ProcyonDecompiler.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/procyon/ProcyonDecompiler.java
@@ -11,7 +11,7 @@ import com.strobel.decompiler.languages.java.JavaFormattingOptions;
11import com.strobel.decompiler.languages.java.ast.AstBuilder; 11import com.strobel.decompiler.languages.java.ast.AstBuilder;
12import com.strobel.decompiler.languages.java.ast.CompilationUnit; 12import com.strobel.decompiler.languages.java.ast.CompilationUnit;
13import com.strobel.decompiler.languages.java.ast.InsertParenthesesVisitor; 13import com.strobel.decompiler.languages.java.ast.InsertParenthesesVisitor;
14import org.checkerframework.checker.nullness.qual.Nullable; 14import org.jetbrains.annotations.Nullable;
15import org.objectweb.asm.tree.ClassNode; 15import org.objectweb.asm.tree.ClassNode;
16 16
17import cuchaz.enigma.classprovider.ClassProvider; 17import cuchaz.enigma.classprovider.ClassProvider;
diff --git a/enigma/src/main/java/cuchaz/enigma/source/procyon/index/SourceIndexMethodVisitor.java b/enigma/src/main/java/cuchaz/enigma/source/procyon/index/SourceIndexMethodVisitor.java
index 12dca73e..493499ff 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/procyon/index/SourceIndexMethodVisitor.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/procyon/index/SourceIndexMethodVisitor.java
@@ -11,11 +11,12 @@
11 11
12package cuchaz.enigma.source.procyon.index; 12package cuchaz.enigma.source.procyon.index;
13 13
14import java.util.ArrayList;
15import java.util.Collection;
14import java.util.HashMap; 16import java.util.HashMap;
17import java.util.List;
15import java.util.Map; 18import java.util.Map;
16 19
17import com.google.common.collect.HashMultimap;
18import com.google.common.collect.Multimap;
19import com.strobel.assembler.metadata.FieldReference; 20import com.strobel.assembler.metadata.FieldReference;
20import com.strobel.assembler.metadata.MemberReference; 21import com.strobel.assembler.metadata.MemberReference;
21import com.strobel.assembler.metadata.MethodDefinition; 22import com.strobel.assembler.metadata.MethodDefinition;
@@ -55,7 +56,7 @@ import cuchaz.enigma.translation.representation.entry.MethodEntry;
55public class SourceIndexMethodVisitor extends SourceIndexVisitor { 56public class SourceIndexMethodVisitor extends SourceIndexVisitor {
56 private final MethodDefEntry methodEntry; 57 private final MethodDefEntry methodEntry;
57 58
58 private Multimap<String, Identifier> unmatchedIdentifier = HashMultimap.create(); 59 private Map<String, Collection<Identifier>> unmatchedIdentifier = new HashMap<>();
59 private Map<String, Entry<?>> identifierEntryCache = new HashMap<>(); 60 private Map<String, Entry<?>> identifierEntryCache = new HashMap<>();
60 61
61 public SourceIndexMethodVisitor(MethodDefEntry methodEntry) { 62 public SourceIndexMethodVisitor(MethodDefEntry methodEntry) {
@@ -173,7 +174,8 @@ public class SourceIndexMethodVisitor extends SourceIndexVisitor {
173 // If it's in the argument cache, create a token! 174 // If it's in the argument cache, create a token!
174 index.addDeclaration(TokenFactory.createToken(index, node.getIdentifierToken()), identifierEntryCache.get(node.getIdentifier())); 175 index.addDeclaration(TokenFactory.createToken(index, node.getIdentifierToken()), identifierEntryCache.get(node.getIdentifier()));
175 } else { 176 } else {
176 unmatchedIdentifier.put(node.getIdentifier(), node.getIdentifierToken()); // Not matched actually, put it! 177 unmatchedIdentifier.computeIfAbsent(node.getIdentifier(), key -> new ArrayList<>())
178 .add(node.getIdentifierToken()); // Not matched actually, put it!
177 } 179 }
178 } 180 }
179 181
@@ -185,11 +187,11 @@ public class SourceIndexMethodVisitor extends SourceIndexVisitor {
185 return; 187 return;
186 } 188 }
187 189
188 for (Identifier identifier : unmatchedIdentifier.get(key)) { 190 for (Identifier identifier : unmatchedIdentifier.getOrDefault(key, List.of())) {
189 index.addDeclaration(TokenFactory.createToken(index, identifier), entry); 191 index.addDeclaration(TokenFactory.createToken(index, identifier), entry);
190 } 192 }
191 193
192 unmatchedIdentifier.removeAll(key); 194 unmatchedIdentifier.remove(key);
193 } 195 }
194 196
195 @Override 197 @Override
diff --git a/enigma/src/main/java/cuchaz/enigma/source/procyon/transformers/AddJavadocsAstTransform.java b/enigma/src/main/java/cuchaz/enigma/source/procyon/transformers/AddJavadocsAstTransform.java
index c48aba5b..4155da35 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/procyon/transformers/AddJavadocsAstTransform.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/procyon/transformers/AddJavadocsAstTransform.java
@@ -4,10 +4,9 @@ import java.util.ArrayList;
4import java.util.Collections; 4import java.util.Collections;
5import java.util.List; 5import java.util.List;
6import java.util.Objects; 6import java.util.Objects;
7import java.util.function.Function;
7import java.util.stream.Stream; 8import java.util.stream.Stream;
8 9
9import com.google.common.base.Function;
10import com.google.common.base.Strings;
11import com.strobel.assembler.metadata.ParameterDefinition; 10import com.strobel.assembler.metadata.ParameterDefinition;
12import com.strobel.decompiler.languages.java.ast.AstNode; 11import com.strobel.decompiler.languages.java.ast.AstNode;
13import com.strobel.decompiler.languages.java.ast.Comment; 12import com.strobel.decompiler.languages.java.ast.Comment;
@@ -60,8 +59,8 @@ public final class AddJavadocsAstTransform implements IAstTransform {
60 59
61 private <T extends AstNode> Comment[] getComments(T node, Function<T, Entry<?>> retriever) { 60 private <T extends AstNode> Comment[] getComments(T node, Function<T, Entry<?>> retriever) {
62 final EntryMapping mapping = remapper.getDeobfMapping(retriever.apply(node)); 61 final EntryMapping mapping = remapper.getDeobfMapping(retriever.apply(node));
63 final String docs = Strings.emptyToNull(mapping.javadoc()); 62 final String docs = mapping.javadoc();
64 return docs == null ? null : Stream.of(docs.split("\\R")).map(st -> new Comment(st, CommentType.Documentation)).toArray(Comment[]::new); 63 return docs == null || docs.isEmpty() ? null : Stream.of(docs.split("\\R")).map(st -> new Comment(st, CommentType.Documentation)).toArray(Comment[]::new);
65 } 64 }
66 65
67 private Comment[] getParameterComments(ParameterDeclaration node, Function<ParameterDeclaration, Entry<?>> retriever) { 66 private Comment[] getParameterComments(ParameterDeclaration node, Function<ParameterDeclaration, Entry<?>> retriever) {
@@ -71,7 +70,7 @@ public final class AddJavadocsAstTransform implements IAstTransform {
71 70
72 if (ret != null) { 71 if (ret != null) {
73 final String paramPrefix = "@param " + (mapping.targetName() != null ? mapping.targetName() : entry.getName()) + " "; 72 final String paramPrefix = "@param " + (mapping.targetName() != null ? mapping.targetName() : entry.getName()) + " ";
74 final String indent = Strings.repeat(" ", paramPrefix.length()); 73 final String indent = " ".repeat(paramPrefix.length());
75 ret[0].setContent(paramPrefix + ret[0].getContent()); 74 ret[0].setContent(paramPrefix + ret[0].getContent());
76 75
77 for (int i = 1; i < ret.length; i++) { 76 for (int i = 1; i < ret.length; i++) {
diff --git a/enigma/src/main/java/cuchaz/enigma/source/vineflower/VineflowerDecompiler.java b/enigma/src/main/java/cuchaz/enigma/source/vineflower/VineflowerDecompiler.java
index 56fd0b91..485fc3fc 100644
--- a/enigma/src/main/java/cuchaz/enigma/source/vineflower/VineflowerDecompiler.java
+++ b/enigma/src/main/java/cuchaz/enigma/source/vineflower/VineflowerDecompiler.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.source.vineflower; 1package cuchaz.enigma.source.vineflower;
2 2
3import org.checkerframework.checker.nullness.qual.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.classprovider.ClassProvider; 5import cuchaz.enigma.classprovider.ClassProvider;
6import cuchaz.enigma.source.Decompiler; 6import cuchaz.enigma.source.Decompiler;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/MappingTranslator.java b/enigma/src/main/java/cuchaz/enigma/translation/MappingTranslator.java
index 833ea294..4cf161c4 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/MappingTranslator.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/MappingTranslator.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.translation; 1package cuchaz.enigma.translation;
2 2
3import javax.annotation.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.translation.mapping.EntryMap; 5import cuchaz.enigma.translation.mapping.EntryMap;
6import cuchaz.enigma.translation.mapping.EntryMapping; 6import cuchaz.enigma.translation.mapping.EntryMapping;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/ProposingTranslator.java b/enigma/src/main/java/cuchaz/enigma/translation/ProposingTranslator.java
index 33a38fee..301cc809 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/ProposingTranslator.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/ProposingTranslator.java
@@ -3,7 +3,7 @@ package cuchaz.enigma.translation;
3import java.util.Arrays; 3import java.util.Arrays;
4import java.util.Optional; 4import java.util.Optional;
5 5
6import javax.annotation.Nullable; 6import org.jetbrains.annotations.Nullable;
7 7
8import cuchaz.enigma.api.service.NameProposalService; 8import cuchaz.enigma.api.service.NameProposalService;
9import cuchaz.enigma.translation.mapping.EntryRemapper; 9import cuchaz.enigma.translation.mapping.EntryRemapper;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/SignatureUpdater.java b/enigma/src/main/java/cuchaz/enigma/translation/SignatureUpdater.java
index 99660141..d6c6142a 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/SignatureUpdater.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/SignatureUpdater.java
@@ -13,10 +13,9 @@ package cuchaz.enigma.translation;
13 13
14import java.io.IOException; 14import java.io.IOException;
15import java.io.StringReader; 15import java.io.StringReader;
16import java.util.ArrayList;
16import java.util.List; 17import java.util.List;
17 18
18import com.google.common.collect.Lists;
19
20public class SignatureUpdater { 19public class SignatureUpdater {
21 public static String update(String signature, ClassNameUpdater updater) { 20 public static String update(String signature, ClassNameUpdater updater) {
22 try { 21 try {
@@ -81,7 +80,7 @@ public class SignatureUpdater {
81 } 80 }
82 81
83 public static List<String> getClasses(String signature) { 82 public static List<String> getClasses(String signature) {
84 final List<String> classNames = Lists.newArrayList(); 83 final List<String> classNames = new ArrayList<>();
85 update(signature, className -> { 84 update(signature, className -> {
86 classNames.add(className); 85 classNames.add(className);
87 return className; 86 return className;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/Translator.java b/enigma/src/main/java/cuchaz/enigma/translation/Translator.java
index ed581972..56889908 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/Translator.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/Translator.java
@@ -11,16 +11,14 @@
11 11
12package cuchaz.enigma.translation; 12package cuchaz.enigma.translation;
13 13
14import java.util.ArrayList;
14import java.util.Collection; 15import java.util.Collection;
15import java.util.HashMap; 16import java.util.HashMap;
16import java.util.Map; 17import java.util.Map;
17import java.util.Set; 18import java.util.Set;
18import java.util.stream.Collectors; 19import java.util.stream.Collectors;
19 20
20import javax.annotation.Nullable; 21import org.jetbrains.annotations.Nullable;
21
22import com.google.common.collect.HashMultimap;
23import com.google.common.collect.Multimap;
24 22
25public interface Translator { 23public interface Translator {
26 @Nullable 24 @Nullable
@@ -61,11 +59,12 @@ public interface Translator {
61 return result; 59 return result;
62 } 60 }
63 61
64 default <K extends Translatable, V extends Translatable> Multimap<K, V> translate(Multimap<K, V> translatable) { 62 default <K extends Translatable, V extends Translatable> Map<K, Collection<V>> translateMulti(Map<K, ? extends Collection<V>> translatable) {
65 Multimap<K, V> result = HashMultimap.create(translatable.size(), 1); 63 Map<K, Collection<V>> result = new HashMap<>(translatable.size());
66 64
67 for (Map.Entry<K, Collection<V>> entry : translatable.asMap().entrySet()) { 65 for (Map.Entry<K, ? extends Collection<V>> entry : translatable.entrySet()) {
68 result.putAll(translate(entry.getKey()), translate(entry.getValue())); 66 result.computeIfAbsent(entry.getKey(), key -> new ArrayList<>())
67 .addAll(translate(entry.getValue()));
69 } 68 }
70 69
71 return result; 70 return result;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryChange.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryChange.java
index 4cd79b94..ad7c33a4 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryChange.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryChange.java
@@ -3,7 +3,7 @@ package cuchaz.enigma.translation.mapping;
3import java.util.Objects; 3import java.util.Objects;
4import java.util.Optional; 4import java.util.Optional;
5 5
6import javax.annotation.Nullable; 6import org.jetbrains.annotations.Nullable;
7 7
8import cuchaz.enigma.EnigmaProject; 8import cuchaz.enigma.EnigmaProject;
9import cuchaz.enigma.source.DecompiledClassSource; 9import cuchaz.enigma.source.DecompiledClassSource;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMap.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMap.java
index b398d412..fa5e1d8a 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMap.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMap.java
@@ -2,7 +2,7 @@ package cuchaz.enigma.translation.mapping;
2 2
3import java.util.stream.Stream; 3import java.util.stream.Stream;
4 4
5import javax.annotation.Nullable; 5import org.jetbrains.annotations.Nullable;
6 6
7import cuchaz.enigma.translation.representation.entry.Entry; 7import cuchaz.enigma.translation.representation.entry.Entry;
8 8
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMapping.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMapping.java
index 72a8fd48..5a1b806c 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMapping.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryMapping.java
@@ -2,10 +2,10 @@ package cuchaz.enigma.translation.mapping;
2 2
3import java.util.Arrays; 3import java.util.Arrays;
4 4
5import javax.annotation.Nonnull; 5import org.jetbrains.annotations.NotNull;
6import javax.annotation.Nullable; 6import org.jetbrains.annotations.Nullable;
7 7
8public record EntryMapping(@Nullable String targetName, @Nonnull AccessModifier accessModifier, @Nullable String javadoc) { 8public record EntryMapping(@Nullable String targetName, @NotNull AccessModifier accessModifier, @Nullable String javadoc) {
9 public static final EntryMapping DEFAULT = new EntryMapping(null, AccessModifier.UNCHANGED, null); 9 public static final EntryMapping DEFAULT = new EntryMapping(null, AccessModifier.UNCHANGED, null);
10 10
11 public EntryMapping { 11 public EntryMapping {
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryRemapper.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryRemapper.java
index ed5dba59..12ed7b1d 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryRemapper.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryRemapper.java
@@ -5,7 +5,7 @@ import java.util.List;
5import java.util.Objects; 5import java.util.Objects;
6import java.util.stream.Stream; 6import java.util.stream.Stream;
7 7
8import javax.annotation.Nonnull; 8import org.jetbrains.annotations.NotNull;
9 9
10import cuchaz.enigma.analysis.index.JarIndex; 10import cuchaz.enigma.analysis.index.JarIndex;
11import cuchaz.enigma.translation.MappingTranslator; 11import cuchaz.enigma.translation.MappingTranslator;
@@ -50,15 +50,15 @@ public class EntryRemapper {
50 return new EntryRemapper(index, new HashEntryTree<>()); 50 return new EntryRemapper(index, new HashEntryTree<>());
51 } 51 }
52 52
53 public void validatePutMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @Nonnull EntryMapping deobfMapping) { 53 public void validatePutMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @NotNull EntryMapping deobfMapping) {
54 doPutMapping(vc, obfuscatedEntry, deobfMapping, true); 54 doPutMapping(vc, obfuscatedEntry, deobfMapping, true);
55 } 55 }
56 56
57 public void putMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @Nonnull EntryMapping deobfMapping) { 57 public void putMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @NotNull EntryMapping deobfMapping) {
58 doPutMapping(vc, obfuscatedEntry, deobfMapping, false); 58 doPutMapping(vc, obfuscatedEntry, deobfMapping, false);
59 } 59 }
60 60
61 private void doPutMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @Nonnull EntryMapping deobfMapping, boolean validateOnly) { 61 private void doPutMapping(ValidationContext vc, Entry<?> obfuscatedEntry, @NotNull EntryMapping deobfMapping, boolean validateOnly) {
62 if (obfuscatedEntry instanceof FieldEntry) { 62 if (obfuscatedEntry instanceof FieldEntry) {
63 FieldEntry fieldEntry = (FieldEntry) obfuscatedEntry; 63 FieldEntry fieldEntry = (FieldEntry) obfuscatedEntry;
64 ClassEntry classEntry = fieldEntry.getParent(); 64 ClassEntry classEntry = fieldEntry.getParent();
@@ -117,7 +117,7 @@ public class EntryRemapper {
117 doPutMapping(vc, methodEntry, new EntryMapping(fieldMapping.targetName()), false); 117 doPutMapping(vc, methodEntry, new EntryMapping(fieldMapping.targetName()), false);
118 } 118 }
119 119
120 @Nonnull 120 @NotNull
121 public EntryMapping getDeobfMapping(Entry<?> entry) { 121 public EntryMapping getDeobfMapping(Entry<?> entry) {
122 EntryMapping entryMapping = obfToDeobf.get(entry); 122 EntryMapping entryMapping = obfToDeobf.get(entry);
123 return entryMapping == null ? EntryMapping.DEFAULT : entryMapping; 123 return entryMapping == null ? EntryMapping.DEFAULT : entryMapping;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryResolver.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryResolver.java
index 39e68259..2274c6e8 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryResolver.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryResolver.java
@@ -1,10 +1,11 @@
1package cuchaz.enigma.translation.mapping; 1package cuchaz.enigma.translation.mapping;
2 2
3import java.util.ArrayList;
3import java.util.Collection; 4import java.util.Collection;
5import java.util.Iterator;
6import java.util.List;
4import java.util.Set; 7import java.util.Set;
5 8
6import com.google.common.collect.Streams;
7
8import cuchaz.enigma.analysis.EntryReference; 9import cuchaz.enigma.analysis.EntryReference;
9import cuchaz.enigma.translation.representation.entry.Entry; 10import cuchaz.enigma.translation.representation.entry.Entry;
10import cuchaz.enigma.translation.representation.entry.MethodEntry; 11import cuchaz.enigma.translation.representation.entry.MethodEntry;
@@ -21,7 +22,15 @@ public interface EntryResolver {
21 22
22 if (reference.context != null) { 23 if (reference.context != null) {
23 Collection<C> context = resolveEntry(reference.context, strategy); 24 Collection<C> context = resolveEntry(reference.context, strategy);
24 return Streams.zip(entry.stream(), context.stream(), (e, c) -> new EntryReference<>(e, c, reference)).toList(); 25 List<EntryReference<E, C>> result = new ArrayList<>(entry.size());
26 Iterator<E> entryIterator = entry.iterator();
27 Iterator<C> contextIterator = context.iterator();
28
29 while (entryIterator.hasNext() && contextIterator.hasNext()) {
30 result.add(new EntryReference<>(entryIterator.next(), contextIterator.next(), reference));
31 }
32
33 return result;
25 } else { 34 } else {
26 return entry.stream().map(e -> new EntryReference<>(e, null, reference)).toList(); 35 return entry.stream().map(e -> new EntryReference<>(e, null, reference)).toList();
27 } 36 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryUtil.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryUtil.java
index f9a10600..fb8ab631 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryUtil.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/EntryUtil.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.translation.mapping; 1package cuchaz.enigma.translation.mapping;
2 2
3import javax.annotation.Nonnull; 3import org.jetbrains.annotations.NotNull;
4 4
5import cuchaz.enigma.translation.representation.entry.Entry; 5import cuchaz.enigma.translation.representation.entry.Entry;
6import cuchaz.enigma.utils.validation.ValidationContext; 6import cuchaz.enigma.utils.validation.ValidationContext;
@@ -16,7 +16,7 @@ public class EntryUtil {
16 return mapping; 16 return mapping;
17 } 17 }
18 18
19 public static EntryMapping applyChange(@Nonnull EntryMapping self, EntryChange<?> change) { 19 public static EntryMapping applyChange(@NotNull EntryMapping self, EntryChange<?> change) {
20 if (change.getDeobfName().isSet()) { 20 if (change.getDeobfName().isSet()) {
21 self = self.withName(change.getDeobfName().getNewValue()); 21 self = self.withName(change.getDeobfName().getNewValue());
22 } else if (change.getDeobfName().isReset()) { 22 } else if (change.getDeobfName().isReset()) {
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/IndexEntryResolver.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/IndexEntryResolver.java
index 8dc56599..dde634c0 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/IndexEntryResolver.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/IndexEntryResolver.java
@@ -6,7 +6,7 @@ import java.util.HashSet;
6import java.util.List; 6import java.util.List;
7import java.util.Set; 7import java.util.Set;
8 8
9import javax.annotation.Nullable; 9import org.jetbrains.annotations.Nullable;
10 10
11import cuchaz.enigma.analysis.IndexTreeBuilder; 11import cuchaz.enigma.analysis.IndexTreeBuilder;
12import cuchaz.enigma.analysis.MethodImplementationsTreeNode; 12import cuchaz.enigma.analysis.MethodImplementationsTreeNode;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingPair.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingPair.java
index 21c78cfd..325af950 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingPair.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingPair.java
@@ -1,6 +1,6 @@
1package cuchaz.enigma.translation.mapping; 1package cuchaz.enigma.translation.mapping;
2 2
3import javax.annotation.Nullable; 3import org.jetbrains.annotations.Nullable;
4 4
5import cuchaz.enigma.translation.representation.entry.Entry; 5import cuchaz.enigma.translation.representation.entry.Entry;
6 6
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingValidator.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingValidator.java
index c193828d..dbde4b3a 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingValidator.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/MappingValidator.java
@@ -4,7 +4,7 @@ import java.util.Collection;
4import java.util.HashSet; 4import java.util.HashSet;
5import java.util.List; 5import java.util.List;
6 6
7import javax.annotation.Nullable; 7import org.jetbrains.annotations.Nullable;
8 8
9import cuchaz.enigma.analysis.index.InheritanceIndex; 9import cuchaz.enigma.analysis.index.InheritanceIndex;
10import cuchaz.enigma.analysis.index.JarIndex; 10import cuchaz.enigma.analysis.index.JarIndex;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingFormat.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingFormat.java
index 197abce1..ec36d47d 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingFormat.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingFormat.java
@@ -6,14 +6,13 @@ import java.nio.file.Path;
6import java.util.Arrays; 6import java.util.Arrays;
7import java.util.List; 7import java.util.List;
8 8
9import javax.annotation.Nullable;
10
11import net.fabricmc.mappingio.MappingReader; 9import net.fabricmc.mappingio.MappingReader;
12import net.fabricmc.mappingio.MappingWriter; 10import net.fabricmc.mappingio.MappingWriter;
13import net.fabricmc.mappingio.tree.MemoryMappingTree; 11import net.fabricmc.mappingio.tree.MemoryMappingTree;
14import net.fabricmc.mappingio.tree.VisitOrder; 12import net.fabricmc.mappingio.tree.VisitOrder;
15import net.fabricmc.mappingio.tree.VisitableMappingTree; 13import net.fabricmc.mappingio.tree.VisitableMappingTree;
16import org.jetbrains.annotations.ApiStatus; 14import org.jetbrains.annotations.ApiStatus;
15import org.jetbrains.annotations.Nullable;
17 16
18import cuchaz.enigma.ProgressListener; 17import cuchaz.enigma.ProgressListener;
19import cuchaz.enigma.analysis.index.JarIndex; 18import cuchaz.enigma.analysis.index.JarIndex;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingIoConverter.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingIoConverter.java
index d4e79e18..766202a5 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingIoConverter.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/MappingIoConverter.java
@@ -7,8 +7,6 @@ import java.util.LinkedList;
7import java.util.List; 7import java.util.List;
8import java.util.stream.StreamSupport; 8import java.util.stream.StreamSupport;
9 9
10import javax.annotation.Nullable;
11
12import net.fabricmc.mappingio.MappedElementKind; 10import net.fabricmc.mappingio.MappedElementKind;
13import net.fabricmc.mappingio.tree.MappingTree.ClassMapping; 11import net.fabricmc.mappingio.tree.MappingTree.ClassMapping;
14import net.fabricmc.mappingio.tree.MappingTree.FieldMapping; 12import net.fabricmc.mappingio.tree.MappingTree.FieldMapping;
@@ -18,6 +16,7 @@ import net.fabricmc.mappingio.tree.MappingTree.MethodVarMapping;
18import net.fabricmc.mappingio.tree.MemoryMappingTree; 16import net.fabricmc.mappingio.tree.MemoryMappingTree;
19import net.fabricmc.mappingio.tree.VisitableMappingTree; 17import net.fabricmc.mappingio.tree.VisitableMappingTree;
20import org.jetbrains.annotations.ApiStatus; 18import org.jetbrains.annotations.ApiStatus;
19import org.jetbrains.annotations.Nullable;
21 20
22import cuchaz.enigma.ProgressListener; 21import cuchaz.enigma.ProgressListener;
23import cuchaz.enigma.analysis.index.JarIndex; 22import cuchaz.enigma.analysis.index.JarIndex;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsReader.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsReader.java
index d5570e98..08d0e575 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsReader.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsReader.java
@@ -1,6 +1,7 @@
1package cuchaz.enigma.translation.mapping.serde.enigma; 1package cuchaz.enigma.translation.mapping.serde.enigma;
2 2
3import java.io.IOException; 3import java.io.IOException;
4import java.nio.charset.StandardCharsets;
4import java.nio.file.FileSystem; 5import java.nio.file.FileSystem;
5import java.nio.file.FileSystems; 6import java.nio.file.FileSystems;
6import java.nio.file.Files; 7import java.nio.file.Files;
@@ -12,9 +13,7 @@ import java.util.Deque;
12import java.util.List; 13import java.util.List;
13import java.util.Locale; 14import java.util.Locale;
14 15
15import javax.annotation.Nullable; 16import org.jetbrains.annotations.Nullable;
16
17import com.google.common.base.Charsets;
18 17
19import cuchaz.enigma.ProgressListener; 18import cuchaz.enigma.ProgressListener;
20import cuchaz.enigma.translation.mapping.AccessModifier; 19import cuchaz.enigma.translation.mapping.AccessModifier;
@@ -114,7 +113,7 @@ public enum EnigmaMappingsReader implements MappingsReader {
114 } 113 }
115 114
116 private static void readFile(Path path, EntryTree<EntryMapping> mappings) throws IOException, MappingParseException { 115 private static void readFile(Path path, EntryTree<EntryMapping> mappings) throws IOException, MappingParseException {
117 List<String> lines = Files.readAllLines(path, Charsets.UTF_8); 116 List<String> lines = Files.readAllLines(path, StandardCharsets.UTF_8);
118 Deque<MappingPair<?, RawEntryMapping>> mappingStack = new ArrayDeque<>(); 117 Deque<MappingPair<?, RawEntryMapping>> mappingStack = new ArrayDeque<>();
119 118
120 for (int lineNumber = 0; lineNumber < lines.size(); lineNumber++) { 119 for (int lineNumber = 0; lineNumber < lines.size(); lineNumber++) {
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsWriter.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsWriter.java
index 24867b69..266668dd 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsWriter.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/enigma/EnigmaMappingsWriter.java
@@ -31,13 +31,12 @@ import java.util.concurrent.atomic.AtomicInteger;
31import java.util.stream.Collectors; 31import java.util.stream.Collectors;
32import java.util.stream.Stream; 32import java.util.stream.Stream;
33 33
34import javax.annotation.Nonnull;
35
36import net.fabricmc.mappingio.MappingWriter; 34import net.fabricmc.mappingio.MappingWriter;
37import net.fabricmc.mappingio.format.MappingFormat; 35import net.fabricmc.mappingio.format.MappingFormat;
38import net.fabricmc.mappingio.tree.VisitOrder; 36import net.fabricmc.mappingio.tree.VisitOrder;
39import net.fabricmc.mappingio.tree.VisitableMappingTree; 37import net.fabricmc.mappingio.tree.VisitableMappingTree;
40import org.jetbrains.annotations.ApiStatus; 38import org.jetbrains.annotations.ApiStatus;
39import org.jetbrains.annotations.NotNull;
41 40
42import cuchaz.enigma.ProgressListener; 41import cuchaz.enigma.ProgressListener;
43import cuchaz.enigma.translation.MappingTranslator; 42import cuchaz.enigma.translation.MappingTranslator;
@@ -298,7 +297,7 @@ public enum EnigmaMappingsWriter implements MappingsWriter {
298 return result; 297 return result;
299 } 298 }
300 299
301 protected String writeClass(ClassEntry entry, @Nonnull EntryMapping mapping) { 300 protected String writeClass(ClassEntry entry, @NotNull EntryMapping mapping) {
302 StringBuilder builder = new StringBuilder(EnigmaFormat.CLASS + " "); 301 StringBuilder builder = new StringBuilder(EnigmaFormat.CLASS + " ");
303 builder.append(entry.getName()).append(' '); 302 builder.append(entry.getName()).append(' ');
304 writeMapping(builder, mapping); 303 writeMapping(builder, mapping);
@@ -306,7 +305,7 @@ public enum EnigmaMappingsWriter implements MappingsWriter {
306 return builder.toString(); 305 return builder.toString();
307 } 306 }
308 307
309 protected String writeMethod(MethodEntry entry, @Nonnull EntryMapping mapping) { 308 protected String writeMethod(MethodEntry entry, @NotNull EntryMapping mapping) {
310 StringBuilder builder = new StringBuilder(EnigmaFormat.METHOD + " "); 309 StringBuilder builder = new StringBuilder(EnigmaFormat.METHOD + " ");
311 builder.append(entry.getName()).append(' '); 310 builder.append(entry.getName()).append(' ');
312 writeMapping(builder, mapping); 311 writeMapping(builder, mapping);
@@ -316,7 +315,7 @@ public enum EnigmaMappingsWriter implements MappingsWriter {
316 return builder.toString(); 315 return builder.toString();
317 } 316 }
318 317
319 protected String writeField(FieldEntry entry, @Nonnull EntryMapping mapping) { 318 protected String writeField(FieldEntry entry, @NotNull EntryMapping mapping) {
320 StringBuilder builder = new StringBuilder(EnigmaFormat.FIELD + " "); 319 StringBuilder builder = new StringBuilder(EnigmaFormat.FIELD + " ");
321 builder.append(entry.getName()).append(' '); 320 builder.append(entry.getName()).append(' ');
322 writeMapping(builder, mapping); 321 writeMapping(builder, mapping);
@@ -326,7 +325,7 @@ public enum EnigmaMappingsWriter implements MappingsWriter {
326 return builder.toString(); 325 return builder.toString();
327 } 326 }
328 327
329 protected String writeArgument(LocalVariableEntry entry, @Nonnull EntryMapping mapping) { 328 protected String writeArgument(LocalVariableEntry entry, @NotNull EntryMapping mapping) {
330 return EnigmaFormat.PARAMETER + " " + entry.getIndex() + ' ' + mapping.targetName(); 329 return EnigmaFormat.PARAMETER + " " + entry.getIndex() + ' ' + mapping.targetName();
331 } 330 }
332 331
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/recaf/RecafMappingsWriter.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/recaf/RecafMappingsWriter.java
index df65b3c8..26a29bf1 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/recaf/RecafMappingsWriter.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/recaf/RecafMappingsWriter.java
@@ -5,8 +5,7 @@ import java.io.IOException;
5import java.io.Writer; 5import java.io.Writer;
6import java.nio.file.Files; 6import java.nio.file.Files;
7import java.nio.file.Path; 7import java.nio.file.Path;
8 8import java.util.ArrayList;
9import com.google.common.collect.Lists;
10 9
11import cuchaz.enigma.ProgressListener; 10import cuchaz.enigma.ProgressListener;
12import cuchaz.enigma.translation.mapping.EntryMapping; 11import cuchaz.enigma.translation.mapping.EntryMapping;
@@ -33,7 +32,7 @@ public class RecafMappingsWriter implements MappingsWriter {
33 } 32 }
34 33
35 try (BufferedWriter writer = Files.newBufferedWriter(path)) { 34 try (BufferedWriter writer = Files.newBufferedWriter(path)) {
36 Lists.newArrayList(mappings).stream().map(EntryTreeNode::getEntry).forEach(entry -> writeEntry(writer, mappings, entry)); 35 new ArrayList<>(mappings).stream().map(EntryTreeNode::getEntry).forEach(entry -> writeEntry(writer, mappings, entry));
37 } catch (IOException e) { 36 } catch (IOException e) {
38 e.printStackTrace(); 37 e.printStackTrace();
39 } 38 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/srg/SrgMappingsWriter.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/srg/SrgMappingsWriter.java
index 5addcade..42372373 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/srg/SrgMappingsWriter.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/srg/SrgMappingsWriter.java
@@ -9,8 +9,6 @@ import java.util.Collection;
9import java.util.Comparator; 9import java.util.Comparator;
10import java.util.List; 10import java.util.List;
11 11
12import com.google.common.collect.Lists;
13
14import cuchaz.enigma.ProgressListener; 12import cuchaz.enigma.ProgressListener;
15import cuchaz.enigma.translation.MappingTranslator; 13import cuchaz.enigma.translation.MappingTranslator;
16import cuchaz.enigma.translation.Translator; 14import cuchaz.enigma.translation.Translator;
@@ -44,7 +42,7 @@ public enum SrgMappingsWriter implements MappingsWriter {
44 List<String> fieldLines = new ArrayList<>(); 42 List<String> fieldLines = new ArrayList<>();
45 List<String> methodLines = new ArrayList<>(); 43 List<String> methodLines = new ArrayList<>();
46 44
47 List<? extends Entry<?>> rootEntries = Lists.newArrayList(mappings).stream().map(EntryTreeNode::getEntry).toList(); 45 List<? extends Entry<?>> rootEntries = new ArrayList<>(mappings).stream().map(EntryTreeNode::getEntry).toList();
48 progress.init(rootEntries.size(), I18n.translate("progress.mappings.converting")); 46 progress.init(rootEntries.size(), I18n.translate("progress.mappings.converting"));
49 47
50 int steps = 0; 48 int steps = 0;
@@ -113,8 +111,8 @@ public enum SrgMappingsWriter implements MappingsWriter {
113 return entry.getParent().getFullName() + "/" + entry.getName(); 111 return entry.getParent().getFullName() + "/" + entry.getName();
114 } 112 }
115 113
116 private Collection<Entry<?>> sorted(Iterable<? extends Entry<?>> iterable) { 114 private Collection<Entry<?>> sorted(Collection<? extends Entry<?>> collection) {
117 ArrayList<Entry<?>> sorted = Lists.newArrayList(iterable); 115 ArrayList<Entry<?>> sorted = new ArrayList<>(collection);
118 sorted.sort(Comparator.comparing(Entry::getName)); 116 sorted.sort(Comparator.comparing(Entry::getName));
119 return sorted; 117 return sorted;
120 } 118 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsReader.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsReader.java
index 1575f468..ae003003 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsReader.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsReader.java
@@ -1,12 +1,11 @@
1package cuchaz.enigma.translation.mapping.serde.tiny; 1package cuchaz.enigma.translation.mapping.serde.tiny;
2 2
3import java.io.IOException; 3import java.io.IOException;
4import java.nio.charset.StandardCharsets;
4import java.nio.file.Files; 5import java.nio.file.Files;
5import java.nio.file.Path; 6import java.nio.file.Path;
6import java.util.List; 7import java.util.List;
7 8
8import com.google.common.base.Charsets;
9
10import cuchaz.enigma.ProgressListener; 9import cuchaz.enigma.ProgressListener;
11import cuchaz.enigma.translation.mapping.EntryMapping; 10import cuchaz.enigma.translation.mapping.EntryMapping;
12import cuchaz.enigma.translation.mapping.MappingPair; 11import cuchaz.enigma.translation.mapping.MappingPair;
@@ -28,7 +27,7 @@ public enum TinyMappingsReader implements MappingsReader {
28 27
29 @Override 28 @Override
30 public EntryTree<EntryMapping> read(Path path, ProgressListener progress, MappingSaveParameters saveParameters) throws IOException, MappingParseException { 29 public EntryTree<EntryMapping> read(Path path, ProgressListener progress, MappingSaveParameters saveParameters) throws IOException, MappingParseException {
31 return read(path, Files.readAllLines(path, Charsets.UTF_8), progress); 30 return read(path, Files.readAllLines(path, StandardCharsets.UTF_8), progress);
32 } 31 }
33 32
34 private EntryTree<EntryMapping> read(Path path, List<String> lines, ProgressListener progress) throws MappingParseException { 33 private EntryTree<EntryMapping> read(Path path, List<String> lines, ProgressListener progress) throws MappingParseException {
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsWriter.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsWriter.java
index 972d1807..67582be0 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsWriter.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tiny/TinyMappingsWriter.java
@@ -6,13 +6,11 @@ import java.io.Writer;
6import java.nio.charset.StandardCharsets; 6import java.nio.charset.StandardCharsets;
7import java.nio.file.Files; 7import java.nio.file.Files;
8import java.nio.file.Path; 8import java.nio.file.Path;
9import java.util.ArrayList;
9import java.util.Comparator; 10import java.util.Comparator;
10import java.util.HashSet; 11import java.util.HashSet;
11import java.util.Set; 12import java.util.Set;
12 13
13import com.google.common.base.Joiner;
14import com.google.common.collect.Lists;
15
16import cuchaz.enigma.ProgressListener; 14import cuchaz.enigma.ProgressListener;
17import cuchaz.enigma.translation.MappingTranslator; 15import cuchaz.enigma.translation.MappingTranslator;
18import cuchaz.enigma.translation.Translator; 16import cuchaz.enigma.translation.Translator;
@@ -30,7 +28,6 @@ import cuchaz.enigma.translation.representation.entry.MethodEntry;
30 28
31public class TinyMappingsWriter implements MappingsWriter { 29public class TinyMappingsWriter implements MappingsWriter {
32 private static final String VERSION_CONSTANT = "v1"; 30 private static final String VERSION_CONSTANT = "v1";
33 private static final Joiner TAB_JOINER = Joiner.on('\t');
34 31
35 //Possibly add a gui or a way to select the namespaces when exporting from the gui 32 //Possibly add a gui or a way to select the namespaces when exporting from the gui
36 public static final TinyMappingsWriter INSTANCE = new TinyMappingsWriter("intermediary", "named"); 33 public static final TinyMappingsWriter INSTANCE = new TinyMappingsWriter("intermediary", "named");
@@ -57,7 +54,7 @@ public class TinyMappingsWriter implements MappingsWriter {
57 try (BufferedWriter writer = Files.newBufferedWriter(path, StandardCharsets.UTF_8)) { 54 try (BufferedWriter writer = Files.newBufferedWriter(path, StandardCharsets.UTF_8)) {
58 writeLine(writer, new String[]{VERSION_CONSTANT, nameObf, nameDeobf}); 55 writeLine(writer, new String[]{VERSION_CONSTANT, nameObf, nameDeobf});
59 56
60 Lists.newArrayList(mappings).stream().map(EntryTreeNode::getEntry).sorted(Comparator.comparing(Object::toString)).forEach(entry -> writeEntry(writer, mappings, entry)); 57 new ArrayList<>(mappings).stream().map(EntryTreeNode::getEntry).sorted(Comparator.comparing(Object::toString)).forEach(entry -> writeEntry(writer, mappings, entry));
61 } catch (IOException e) { 58 } catch (IOException e) {
62 e.printStackTrace(); 59 e.printStackTrace();
63 } 60 }
@@ -107,7 +104,7 @@ public class TinyMappingsWriter implements MappingsWriter {
107 104
108 private void writeLine(Writer writer, String[] data) { 105 private void writeLine(Writer writer, String[] data) {
109 try { 106 try {
110 String line = TAB_JOINER.join(data) + "\n"; 107 String line = String.join("\t", data) + "\n";
111 108
112 if (writtenLines.add(line)) { 109 if (writtenLines.add(line)) {
113 writer.write(line); 110 writer.write(line);
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tinyv2/TinyV2Writer.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tinyv2/TinyV2Writer.java
index 959d2d8f..d85ed6e5 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tinyv2/TinyV2Writer.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/serde/tinyv2/TinyV2Writer.java
@@ -9,8 +9,6 @@ import java.util.LinkedList;
9import java.util.List; 9import java.util.List;
10import java.util.stream.StreamSupport; 10import java.util.stream.StreamSupport;
11 11
12import com.google.common.base.Strings;
13
14import cuchaz.enigma.ProgressListener; 12import cuchaz.enigma.ProgressListener;
15import cuchaz.enigma.translation.mapping.EntryMap; 13import cuchaz.enigma.translation.mapping.EntryMap;
16import cuchaz.enigma.translation.mapping.EntryMapping; 14import cuchaz.enigma.translation.mapping.EntryMapping;
@@ -184,6 +182,6 @@ public final class TinyV2Writer implements MappingsWriter {
184 } 182 }
185 183
186 private String indent(int level) { 184 private String indent(int level) {
187 return Strings.repeat("\t", level); 185 return "\t".repeat(level);
188 } 186 }
189} 187}
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/DeltaTrackingTree.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/DeltaTrackingTree.java
index b943cc84..ef746c4d 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/DeltaTrackingTree.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/DeltaTrackingTree.java
@@ -1,10 +1,11 @@
1package cuchaz.enigma.translation.mapping.tree; 1package cuchaz.enigma.translation.mapping.tree;
2 2
3import java.util.AbstractCollection;
3import java.util.Collection; 4import java.util.Collection;
4import java.util.Iterator; 5import java.util.Iterator;
5import java.util.stream.Stream; 6import java.util.stream.Stream;
6 7
7import javax.annotation.Nullable; 8import org.jetbrains.annotations.Nullable;
8 9
9import cuchaz.enigma.translation.Translator; 10import cuchaz.enigma.translation.Translator;
10import cuchaz.enigma.translation.mapping.EntryMap; 11import cuchaz.enigma.translation.mapping.EntryMap;
@@ -13,7 +14,7 @@ import cuchaz.enigma.translation.mapping.EntryResolver;
13import cuchaz.enigma.translation.mapping.MappingDelta; 14import cuchaz.enigma.translation.mapping.MappingDelta;
14import cuchaz.enigma.translation.representation.entry.Entry; 15import cuchaz.enigma.translation.representation.entry.Entry;
15 16
16public class DeltaTrackingTree<T> implements EntryTree<T> { 17public class DeltaTrackingTree<T> extends AbstractCollection<EntryTreeNode<T>> implements EntryTree<T> {
17 private final EntryTree<T> delegate; 18 private final EntryTree<T> delegate;
18 19
19 private EntryTree<T> deltaReference; 20 private EntryTree<T> deltaReference;
@@ -94,6 +95,11 @@ public class DeltaTrackingTree<T> implements EntryTree<T> {
94 return delegate.iterator(); 95 return delegate.iterator();
95 } 96 }
96 97
98 @Override
99 public int size() {
100 return delegate.size();
101 }
102
97 public MappingDelta<T> takeDelta() { 103 public MappingDelta<T> takeDelta() {
98 MappingDelta<T> delta = new MappingDelta<>(deltaReference, changes); 104 MappingDelta<T> delta = new MappingDelta<>(deltaReference, changes);
99 resetDelta(); 105 resetDelta();
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTree.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTree.java
index e1c8e8d6..3fe535f7 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTree.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTree.java
@@ -3,7 +3,7 @@ package cuchaz.enigma.translation.mapping.tree;
3import java.util.Collection; 3import java.util.Collection;
4import java.util.stream.Stream; 4import java.util.stream.Stream;
5 5
6import javax.annotation.Nullable; 6import org.jetbrains.annotations.Nullable;
7 7
8import cuchaz.enigma.translation.Translatable; 8import cuchaz.enigma.translation.Translatable;
9import cuchaz.enigma.translation.TranslateResult; 9import cuchaz.enigma.translation.TranslateResult;
@@ -13,7 +13,7 @@ import cuchaz.enigma.translation.mapping.EntryMapping;
13import cuchaz.enigma.translation.mapping.EntryResolver; 13import cuchaz.enigma.translation.mapping.EntryResolver;
14import cuchaz.enigma.translation.representation.entry.Entry; 14import cuchaz.enigma.translation.representation.entry.Entry;
15 15
16public interface EntryTree<T> extends EntryMap<T>, Iterable<EntryTreeNode<T>>, Translatable { 16public interface EntryTree<T> extends EntryMap<T>, Collection<EntryTreeNode<T>>, Translatable {
17 Collection<Entry<?>> getChildren(Entry<?> entry); 17 Collection<Entry<?>> getChildren(Entry<?> entry);
18 18
19 Collection<Entry<?>> getSiblings(Entry<?> entry); 19 Collection<Entry<?>> getSiblings(Entry<?> entry);
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTreeNode.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTreeNode.java
index 254b3318..ab249dfd 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/EntryTreeNode.java
@@ -4,7 +4,7 @@ import java.util.ArrayList;
4import java.util.Collection; 4import java.util.Collection;
5import java.util.List; 5import java.util.List;
6 6
7import javax.annotation.Nullable; 7import org.jetbrains.annotations.Nullable;
8 8
9import cuchaz.enigma.translation.representation.entry.Entry; 9import cuchaz.enigma.translation.representation.entry.Entry;
10 10
@@ -31,6 +31,16 @@ public interface EntryTreeNode<T> {
31 return nodes; 31 return nodes;
32 } 32 }
33 33
34 default int sizeRecursively() {
35 int size = 1;
36
37 for (EntryTreeNode<T> node : getChildNodes()) {
38 size += node.sizeRecursively();
39 }
40
41 return size;
42 }
43
34 default List<? extends Entry<?>> getChildrenRecursively() { 44 default List<? extends Entry<?>> getChildrenRecursively() {
35 return getNodesRecursively().stream().map(EntryTreeNode::getEntry).toList(); 45 return getNodesRecursively().stream().map(EntryTreeNode::getEntry).toList();
36 } 46 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashEntryTree.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashEntryTree.java
index 2902373d..a026eb61 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashEntryTree.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashEntryTree.java
@@ -1,5 +1,6 @@
1package cuchaz.enigma.translation.mapping.tree; 1package cuchaz.enigma.translation.mapping.tree;
2 2
3import java.util.AbstractCollection;
3import java.util.ArrayList; 4import java.util.ArrayList;
4import java.util.Collection; 5import java.util.Collection;
5import java.util.Collections; 6import java.util.Collections;
@@ -13,8 +14,8 @@ import java.util.function.Function;
13import java.util.stream.Stream; 14import java.util.stream.Stream;
14import java.util.stream.StreamSupport; 15import java.util.stream.StreamSupport;
15 16
16import javax.annotation.Nonnull; 17import org.jetbrains.annotations.NotNull;
17import javax.annotation.Nullable; 18import org.jetbrains.annotations.Nullable;
18 19
19import cuchaz.enigma.translation.Translator; 20import cuchaz.enigma.translation.Translator;
20import cuchaz.enigma.translation.mapping.EntryMap; 21import cuchaz.enigma.translation.mapping.EntryMap;
@@ -22,7 +23,7 @@ import cuchaz.enigma.translation.mapping.EntryMapping;
22import cuchaz.enigma.translation.mapping.EntryResolver; 23import cuchaz.enigma.translation.mapping.EntryResolver;
23import cuchaz.enigma.translation.representation.entry.Entry; 24import cuchaz.enigma.translation.representation.entry.Entry;
24 25
25public class HashEntryTree<T> implements EntryTree<T> { 26public class HashEntryTree<T> extends AbstractCollection<EntryTreeNode<T>> implements EntryTree<T> {
26 private final Map<Entry<?>, HashTreeNode<T>> root = new HashMap<>(); 27 private final Map<Entry<?>, HashTreeNode<T>> root = new HashMap<>();
27 28
28 public HashEntryTree() { 29 public HashEntryTree() {
@@ -177,7 +178,7 @@ public class HashEntryTree<T> implements EntryTree<T> {
177 } 178 }
178 179
179 @Override 180 @Override
180 @Nonnull 181 @NotNull
181 public Iterator<EntryTreeNode<T>> iterator() { 182 public Iterator<EntryTreeNode<T>> iterator() {
182 Collection<EntryTreeNode<T>> nodes = new ArrayList<>(); 183 Collection<EntryTreeNode<T>> nodes = new ArrayList<>();
183 184
@@ -189,6 +190,11 @@ public class HashEntryTree<T> implements EntryTree<T> {
189 } 190 }
190 191
191 @Override 192 @Override
193 public int size() {
194 return root.values().stream().mapToInt(EntryTreeNode::sizeRecursively).sum();
195 }
196
197 @Override
192 public Stream<Entry<?>> getAllEntries() { 198 public Stream<Entry<?>> getAllEntries() {
193 return StreamSupport.stream(spliterator(), false).filter(EntryTreeNode::hasValue).map(EntryTreeNode::getEntry); 199 return StreamSupport.stream(spliterator(), false).filter(EntryTreeNode::hasValue).map(EntryTreeNode::getEntry);
194 } 200 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashTreeNode.java b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashTreeNode.java
index 3ddaf81f..c65bd408 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashTreeNode.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/mapping/tree/HashTreeNode.java
@@ -5,8 +5,8 @@ import java.util.HashMap;
5import java.util.Iterator; 5import java.util.Iterator;
6import java.util.Map; 6import java.util.Map;
7 7
8import javax.annotation.Nonnull; 8import org.jetbrains.annotations.NotNull;
9import javax.annotation.Nullable; 9import org.jetbrains.annotations.Nullable;
10 10
11import cuchaz.enigma.translation.representation.entry.Entry; 11import cuchaz.enigma.translation.representation.entry.Entry;
12 12
@@ -34,7 +34,7 @@ public class HashTreeNode<T> implements EntryTreeNode<T>, Iterable<HashTreeNode<
34 return children.get(entry); 34 return children.get(entry);
35 } 35 }
36 36
37 @Nonnull 37 @NotNull
38 HashTreeNode<T> computeChild(Entry<?> entry) { 38 HashTreeNode<T> computeChild(Entry<?> entry) {
39 return children.computeIfAbsent(entry, HashTreeNode::new); 39 return children.computeIfAbsent(entry, HashTreeNode::new);
40 } 40 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/MethodDescriptor.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/MethodDescriptor.java
index 571488cc..bfd77d0f 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/MethodDescriptor.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/MethodDescriptor.java
@@ -16,8 +16,6 @@ import java.util.List;
16import java.util.Objects; 16import java.util.Objects;
17import java.util.function.Function; 17import java.util.function.Function;
18 18
19import com.google.common.collect.Lists;
20
21import cuchaz.enigma.translation.Translatable; 19import cuchaz.enigma.translation.Translatable;
22import cuchaz.enigma.translation.TranslateResult; 20import cuchaz.enigma.translation.TranslateResult;
23import cuchaz.enigma.translation.Translator; 21import cuchaz.enigma.translation.Translator;
@@ -32,7 +30,7 @@ public class MethodDescriptor implements Translatable {
32 30
33 public MethodDescriptor(String desc) { 31 public MethodDescriptor(String desc) {
34 try { 32 try {
35 this.argumentDescs = Lists.newArrayList(); 33 this.argumentDescs = new ArrayList<>();
36 int i = 0; 34 int i = 0;
37 35
38 while (i < desc.length()) { 36 while (i < desc.length()) {
@@ -86,8 +84,7 @@ public class MethodDescriptor implements Translatable {
86 } 84 }
87 85
88 public Iterable<TypeDescriptor> types() { 86 public Iterable<TypeDescriptor> types() {
89 List<TypeDescriptor> descs = Lists.newArrayList(); 87 List<TypeDescriptor> descs = new ArrayList<>(this.argumentDescs);
90 descs.addAll(this.argumentDescs);
91 descs.add(this.returnDesc); 88 descs.add(this.returnDesc);
92 return descs; 89 return descs;
93 } 90 }
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/TypeDescriptor.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/TypeDescriptor.java
index fd53522d..c714fd51 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/TypeDescriptor.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/TypeDescriptor.java
@@ -12,11 +12,10 @@
12package cuchaz.enigma.translation.representation; 12package cuchaz.enigma.translation.representation;
13 13
14import java.util.Map; 14import java.util.Map;
15import java.util.Objects;
16import java.util.TreeMap;
15import java.util.function.Function; 17import java.util.function.Function;
16 18
17import com.google.common.base.Preconditions;
18import com.google.common.collect.Maps;
19
20import cuchaz.enigma.translation.Translatable; 19import cuchaz.enigma.translation.Translatable;
21import cuchaz.enigma.translation.TranslateResult; 20import cuchaz.enigma.translation.TranslateResult;
22import cuchaz.enigma.translation.Translator; 21import cuchaz.enigma.translation.Translator;
@@ -29,7 +28,7 @@ public class TypeDescriptor implements Translatable {
29 protected final String desc; 28 protected final String desc;
30 29
31 public TypeDescriptor(String desc) { 30 public TypeDescriptor(String desc) {
32 Preconditions.checkNotNull(desc, "Desc cannot be null"); 31 Objects.requireNonNull(desc, "Desc cannot be null");
33 32
34 // don't deal with generics 33 // don't deal with generics
35 // this is just for raw jvm types 34 // this is just for raw jvm types
@@ -260,7 +259,7 @@ public class TypeDescriptor implements Translatable {
260 private static final Map<Character, Primitive> lookup; 259 private static final Map<Character, Primitive> lookup;
261 260
262 static { 261 static {
263 lookup = Maps.newTreeMap(); 262 lookup = new TreeMap<>();
264 263
265 for (Primitive val : values()) { 264 for (Primitive val : values()) {
266 lookup.put(val.getCode(), val); 265 lookup.put(val.getCode(), val);
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassDefEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassDefEntry.java
index eb3ea42a..3cbd0c9a 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassDefEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassDefEntry.java
@@ -12,11 +12,10 @@
12package cuchaz.enigma.translation.representation.entry; 12package cuchaz.enigma.translation.representation.entry;
13 13
14import java.util.Arrays; 14import java.util.Arrays;
15import java.util.Objects;
15 16
16import javax.annotation.Nonnull; 17import org.jetbrains.annotations.NotNull;
17import javax.annotation.Nullable; 18import org.jetbrains.annotations.Nullable;
18
19import com.google.common.base.Preconditions;
20 19
21import cuchaz.enigma.source.RenamableTokenType; 20import cuchaz.enigma.source.RenamableTokenType;
22import cuchaz.enigma.translation.TranslateResult; 21import cuchaz.enigma.translation.TranslateResult;
@@ -41,11 +40,9 @@ public class ClassDefEntry extends ClassEntry implements DefEntry<ClassEntry> {
41 40
42 public ClassDefEntry(ClassEntry parent, String className, Signature signature, AccessFlags access, @Nullable ClassEntry superClass, ClassEntry[] interfaces, String javadocs) { 41 public ClassDefEntry(ClassEntry parent, String className, Signature signature, AccessFlags access, @Nullable ClassEntry superClass, ClassEntry[] interfaces, String javadocs) {
43 super(parent, className, javadocs); 42 super(parent, className, javadocs);
44 Preconditions.checkNotNull(signature, "Class signature cannot be null");
45 Preconditions.checkNotNull(access, "Class access cannot be null");
46 43
47 this.signature = signature; 44 this.signature = Objects.requireNonNull(signature, "Class signature cannot be null");
48 this.access = access; 45 this.access = Objects.requireNonNull(access, "Class access cannot be null");
49 this.superClass = superClass; 46 this.superClass = superClass;
50 this.interfaces = interfaces != null ? interfaces : new ClassEntry[0]; 47 this.interfaces = interfaces != null ? interfaces : new ClassEntry[0];
51 } 48 }
@@ -79,7 +76,7 @@ public class ClassDefEntry extends ClassEntry implements DefEntry<ClassEntry> {
79 } 76 }
80 77
81 @Override 78 @Override
82 public TranslateResult<ClassDefEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 79 public TranslateResult<ClassDefEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
83 Signature translatedSignature = translator.translate(signature); 80 Signature translatedSignature = translator.translate(signature);
84 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 81 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
85 AccessFlags translatedAccess = mapping.accessModifier().transform(access); 82 AccessFlags translatedAccess = mapping.accessModifier().transform(access);
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassEntry.java
index 0e179d7f..23c4f4f9 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ClassEntry.java
@@ -14,8 +14,8 @@ package cuchaz.enigma.translation.representation.entry;
14import java.util.List; 14import java.util.List;
15import java.util.Objects; 15import java.util.Objects;
16 16
17import javax.annotation.Nonnull; 17import org.jetbrains.annotations.NotNull;
18import javax.annotation.Nullable; 18import org.jetbrains.annotations.Nullable;
19 19
20import cuchaz.enigma.source.RenamableTokenType; 20import cuchaz.enigma.source.RenamableTokenType;
21import cuchaz.enigma.translation.TranslateResult; 21import cuchaz.enigma.translation.TranslateResult;
@@ -90,7 +90,7 @@ public class ClassEntry extends ParentedEntry<ClassEntry> implements Comparable<
90 } 90 }
91 91
92 @Override 92 @Override
93 public TranslateResult<? extends ClassEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 93 public TranslateResult<? extends ClassEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
94 if (name.charAt(0) == '[') { 94 if (name.charAt(0) == '[') {
95 TranslateResult<TypeDescriptor> translatedName = translator.extendedTranslate(new TypeDescriptor(name)); 95 TranslateResult<TypeDescriptor> translatedName = translator.extendedTranslate(new TypeDescriptor(name));
96 return translatedName.map(desc -> new ClassEntry(parent, desc.toString())); 96 return translatedName.map(desc -> new ClassEntry(parent, desc.toString()));
@@ -166,7 +166,7 @@ public class ClassEntry extends ParentedEntry<ClassEntry> implements Comparable<
166 return parent; 166 return parent;
167 } 167 }
168 168
169 @Nonnull 169 @NotNull
170 public ClassEntry getOutermostClass() { 170 public ClassEntry getOutermostClass() {
171 if (parent == null) { 171 if (parent == null) {
172 return this; 172 return this;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/Entry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/Entry.java
index 71425e0f..568d01c9 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/Entry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/Entry.java
@@ -15,7 +15,7 @@ import java.util.ArrayList;
15import java.util.List; 15import java.util.List;
16import java.util.Objects; 16import java.util.Objects;
17 17
18import javax.annotation.Nullable; 18import org.jetbrains.annotations.Nullable;
19 19
20import cuchaz.enigma.translation.Translatable; 20import cuchaz.enigma.translation.Translatable;
21import cuchaz.enigma.translation.mapping.IdentifierValidation; 21import cuchaz.enigma.translation.mapping.IdentifierValidation;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldDefEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldDefEntry.java
index 492d72e7..45ef31c5 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldDefEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldDefEntry.java
@@ -11,9 +11,9 @@
11 11
12package cuchaz.enigma.translation.representation.entry; 12package cuchaz.enigma.translation.representation.entry;
13 13
14import javax.annotation.Nonnull; 14import java.util.Objects;
15 15
16import com.google.common.base.Preconditions; 16import org.jetbrains.annotations.NotNull;
17 17
18import cuchaz.enigma.source.RenamableTokenType; 18import cuchaz.enigma.source.RenamableTokenType;
19import cuchaz.enigma.translation.TranslateResult; 19import cuchaz.enigma.translation.TranslateResult;
@@ -33,10 +33,8 @@ public class FieldDefEntry extends FieldEntry implements DefEntry<ClassEntry> {
33 33
34 public FieldDefEntry(ClassEntry owner, String name, TypeDescriptor desc, Signature signature, AccessFlags access, String javadocs) { 34 public FieldDefEntry(ClassEntry owner, String name, TypeDescriptor desc, Signature signature, AccessFlags access, String javadocs) {
35 super(owner, name, desc, javadocs); 35 super(owner, name, desc, javadocs);
36 Preconditions.checkNotNull(access, "Field access cannot be null"); 36 this.access = Objects.requireNonNull(access, "Field access cannot be null");
37 Preconditions.checkNotNull(signature, "Field signature cannot be null"); 37 this.signature = Objects.requireNonNull(signature, "Field signature cannot be null");
38 this.access = access;
39 this.signature = signature;
40 } 38 }
41 39
42 public static FieldDefEntry parse(ClassEntry owner, int access, String name, String desc, String signature) { 40 public static FieldDefEntry parse(ClassEntry owner, int access, String name, String desc, String signature) {
@@ -53,7 +51,7 @@ public class FieldDefEntry extends FieldEntry implements DefEntry<ClassEntry> {
53 } 51 }
54 52
55 @Override 53 @Override
56 protected TranslateResult<FieldEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 54 protected TranslateResult<FieldEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
57 TypeDescriptor translatedDesc = translator.translate(desc); 55 TypeDescriptor translatedDesc = translator.translate(desc);
58 Signature translatedSignature = translator.translate(signature); 56 Signature translatedSignature = translator.translate(signature);
59 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 57 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldEntry.java
index aaa0798c..745485f0 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/FieldEntry.java
@@ -13,9 +13,7 @@ package cuchaz.enigma.translation.representation.entry;
13 13
14import java.util.Objects; 14import java.util.Objects;
15 15
16import javax.annotation.Nonnull; 16import org.jetbrains.annotations.NotNull;
17
18import com.google.common.base.Preconditions;
19 17
20import cuchaz.enigma.source.RenamableTokenType; 18import cuchaz.enigma.source.RenamableTokenType;
21import cuchaz.enigma.translation.TranslateResult; 19import cuchaz.enigma.translation.TranslateResult;
@@ -31,12 +29,9 @@ public class FieldEntry extends ParentedEntry<ClassEntry> implements Comparable<
31 } 29 }
32 30
33 public FieldEntry(ClassEntry parent, String name, TypeDescriptor desc, String javadocs) { 31 public FieldEntry(ClassEntry parent, String name, TypeDescriptor desc, String javadocs) {
34 super(parent, name, javadocs); 32 super(Objects.requireNonNull(parent, "Owner cannot be null"), name, javadocs);
35
36 Preconditions.checkNotNull(parent, "Owner cannot be null");
37 Preconditions.checkNotNull(desc, "Field descriptor cannot be null");
38 33
39 this.desc = desc; 34 this.desc = Objects.requireNonNull(desc, "Field descriptor cannot be null");
40 } 35 }
41 36
42 public static FieldEntry parse(String owner, String name, String desc) { 37 public static FieldEntry parse(String owner, String name, String desc) {
@@ -63,7 +58,7 @@ public class FieldEntry extends ParentedEntry<ClassEntry> implements Comparable<
63 } 58 }
64 59
65 @Override 60 @Override
66 protected TranslateResult<FieldEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 61 protected TranslateResult<FieldEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
67 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 62 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
68 String docs = mapping.javadoc(); 63 String docs = mapping.javadoc();
69 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new FieldEntry(parent, translatedName, translator.translate(desc), docs)); 64 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new FieldEntry(parent, translatedName, translator.translate(desc), docs));
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableDefEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableDefEntry.java
index ac36a483..9eda3a9e 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableDefEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableDefEntry.java
@@ -1,8 +1,8 @@
1package cuchaz.enigma.translation.representation.entry; 1package cuchaz.enigma.translation.representation.entry;
2 2
3import javax.annotation.Nonnull; 3import java.util.Objects;
4 4
5import com.google.common.base.Preconditions; 5import org.jetbrains.annotations.NotNull;
6 6
7import cuchaz.enigma.source.RenamableTokenType; 7import cuchaz.enigma.source.RenamableTokenType;
8import cuchaz.enigma.translation.TranslateResult; 8import cuchaz.enigma.translation.TranslateResult;
@@ -20,9 +20,8 @@ public class LocalVariableDefEntry extends LocalVariableEntry {
20 20
21 public LocalVariableDefEntry(MethodEntry ownerEntry, int index, String name, boolean parameter, TypeDescriptor desc, String javadoc) { 21 public LocalVariableDefEntry(MethodEntry ownerEntry, int index, String name, boolean parameter, TypeDescriptor desc, String javadoc) {
22 super(ownerEntry, index, name, parameter, javadoc); 22 super(ownerEntry, index, name, parameter, javadoc);
23 Preconditions.checkNotNull(desc, "Variable desc cannot be null");
24 23
25 this.desc = desc; 24 this.desc = Objects.requireNonNull(desc, "Variable desc cannot be null");
26 } 25 }
27 26
28 public TypeDescriptor getDesc() { 27 public TypeDescriptor getDesc() {
@@ -30,7 +29,7 @@ public class LocalVariableDefEntry extends LocalVariableEntry {
30 } 29 }
31 30
32 @Override 31 @Override
33 protected TranslateResult<LocalVariableEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 32 protected TranslateResult<LocalVariableEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
34 TypeDescriptor translatedDesc = translator.translate(desc); 33 TypeDescriptor translatedDesc = translator.translate(desc);
35 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 34 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
36 String javadoc = mapping.javadoc(); 35 String javadoc = mapping.javadoc();
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableEntry.java
index 9d0bbedd..b188fb5b 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/LocalVariableEntry.java
@@ -2,9 +2,7 @@ package cuchaz.enigma.translation.representation.entry;
2 2
3import java.util.Objects; 3import java.util.Objects;
4 4
5import javax.annotation.Nonnull; 5import org.jetbrains.annotations.NotNull;
6
7import com.google.common.base.Preconditions;
8 6
9import cuchaz.enigma.source.RenamableTokenType; 7import cuchaz.enigma.source.RenamableTokenType;
10import cuchaz.enigma.translation.TranslateResult; 8import cuchaz.enigma.translation.TranslateResult;
@@ -21,10 +19,11 @@ public class LocalVariableEntry extends ParentedEntry<MethodEntry> implements Co
21 protected final boolean parameter; 19 protected final boolean parameter;
22 20
23 public LocalVariableEntry(MethodEntry parent, int index, String name, boolean parameter, String javadoc) { 21 public LocalVariableEntry(MethodEntry parent, int index, String name, boolean parameter, String javadoc) {
24 super(parent, name, javadoc); 22 super(Objects.requireNonNull(parent, "Variable owner cannot be null"), name, javadoc);
25 23
26 Preconditions.checkNotNull(parent, "Variable owner cannot be null"); 24 if (index < 0) {
27 Preconditions.checkArgument(index >= 0, "Index must be positive"); 25 throw new IllegalArgumentException("Index must be positive");
26 }
28 27
29 this.index = index; 28 this.index = index;
30 this.parameter = parameter; 29 this.parameter = parameter;
@@ -49,7 +48,7 @@ public class LocalVariableEntry extends ParentedEntry<MethodEntry> implements Co
49 } 48 }
50 49
51 @Override 50 @Override
52 protected TranslateResult<LocalVariableEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 51 protected TranslateResult<LocalVariableEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
53 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 52 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
54 String javadoc = mapping.javadoc(); 53 String javadoc = mapping.javadoc();
55 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new LocalVariableEntry(parent, index, translatedName, parameter, javadoc)); 54 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new LocalVariableEntry(parent, index, translatedName, parameter, javadoc));
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodDefEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodDefEntry.java
index c6a4ab73..4392953e 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodDefEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodDefEntry.java
@@ -11,9 +11,9 @@
11 11
12package cuchaz.enigma.translation.representation.entry; 12package cuchaz.enigma.translation.representation.entry;
13 13
14import javax.annotation.Nonnull; 14import java.util.Objects;
15 15
16import com.google.common.base.Preconditions; 16import org.jetbrains.annotations.NotNull;
17 17
18import cuchaz.enigma.source.RenamableTokenType; 18import cuchaz.enigma.source.RenamableTokenType;
19import cuchaz.enigma.translation.TranslateResult; 19import cuchaz.enigma.translation.TranslateResult;
@@ -33,10 +33,8 @@ public class MethodDefEntry extends MethodEntry implements DefEntry<ClassEntry>
33 33
34 public MethodDefEntry(ClassEntry owner, String name, MethodDescriptor descriptor, Signature signature, AccessFlags access, String docs) { 34 public MethodDefEntry(ClassEntry owner, String name, MethodDescriptor descriptor, Signature signature, AccessFlags access, String docs) {
35 super(owner, name, descriptor, docs); 35 super(owner, name, descriptor, docs);
36 Preconditions.checkNotNull(access, "Method access cannot be null"); 36 this.access = Objects.requireNonNull(access, "Method access cannot be null");
37 Preconditions.checkNotNull(signature, "Method signature cannot be null"); 37 this.signature = Objects.requireNonNull(signature, "Method signature cannot be null");
38 this.access = access;
39 this.signature = signature;
40 } 38 }
41 39
42 public static MethodDefEntry parse(ClassEntry owner, int access, String name, String desc, String signature) { 40 public static MethodDefEntry parse(ClassEntry owner, int access, String name, String desc, String signature) {
@@ -53,7 +51,7 @@ public class MethodDefEntry extends MethodEntry implements DefEntry<ClassEntry>
53 } 51 }
54 52
55 @Override 53 @Override
56 protected TranslateResult<MethodDefEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 54 protected TranslateResult<MethodDefEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
57 MethodDescriptor translatedDesc = translator.translate(descriptor); 55 MethodDescriptor translatedDesc = translator.translate(descriptor);
58 Signature translatedSignature = translator.translate(signature); 56 Signature translatedSignature = translator.translate(signature);
59 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 57 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodEntry.java
index 5ccb9081..3390bc57 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/MethodEntry.java
@@ -13,9 +13,7 @@ package cuchaz.enigma.translation.representation.entry;
13 13
14import java.util.Objects; 14import java.util.Objects;
15 15
16import javax.annotation.Nonnull; 16import org.jetbrains.annotations.NotNull;
17
18import com.google.common.base.Preconditions;
19 17
20import cuchaz.enigma.source.RenamableTokenType; 18import cuchaz.enigma.source.RenamableTokenType;
21import cuchaz.enigma.translation.TranslateResult; 19import cuchaz.enigma.translation.TranslateResult;
@@ -31,12 +29,9 @@ public class MethodEntry extends ParentedEntry<ClassEntry> implements Comparable
31 } 29 }
32 30
33 public MethodEntry(ClassEntry parent, String name, MethodDescriptor descriptor, String javadocs) { 31 public MethodEntry(ClassEntry parent, String name, MethodDescriptor descriptor, String javadocs) {
34 super(parent, name, javadocs); 32 super(Objects.requireNonNull(parent, "Parent cannot be null"), name, javadocs);
35
36 Preconditions.checkNotNull(parent, "Parent cannot be null");
37 Preconditions.checkNotNull(descriptor, "Method descriptor cannot be null");
38 33
39 this.descriptor = descriptor; 34 this.descriptor = Objects.requireNonNull(descriptor, "Method descriptor cannot be null");
40 } 35 }
41 36
42 public static MethodEntry parse(String owner, String name, String desc) { 37 public static MethodEntry parse(String owner, String name, String desc) {
@@ -57,7 +52,7 @@ public class MethodEntry extends ParentedEntry<ClassEntry> implements Comparable
57 } 52 }
58 53
59 @Override 54 @Override
60 protected TranslateResult<? extends MethodEntry> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping) { 55 protected TranslateResult<? extends MethodEntry> extendedTranslate(Translator translator, @NotNull EntryMapping mapping) {
61 String translatedName = mapping.targetName() != null ? mapping.targetName() : name; 56 String translatedName = mapping.targetName() != null ? mapping.targetName() : name;
62 String docs = mapping.javadoc(); 57 String docs = mapping.javadoc();
63 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new MethodEntry(parent, translatedName, translator.translate(descriptor), docs)); 58 return TranslateResult.of(mapping.targetName() == null ? RenamableTokenType.OBFUSCATED : RenamableTokenType.DEOBFUSCATED, new MethodEntry(parent, translatedName, translator.translate(descriptor), docs));
diff --git a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ParentedEntry.java b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ParentedEntry.java
index ff5ffa39..e8e6f30d 100644
--- a/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ParentedEntry.java
+++ b/enigma/src/main/java/cuchaz/enigma/translation/representation/entry/ParentedEntry.java
@@ -11,10 +11,10 @@
11 11
12package cuchaz.enigma.translation.representation.entry; 12package cuchaz.enigma.translation.representation.entry;
13 13
14import javax.annotation.Nonnull; 14import java.util.Objects;
15import javax.annotation.Nullable;
16 15
17import com.google.common.base.Preconditions; 16import org.jetbrains.annotations.NotNull;
17import org.jetbrains.annotations.Nullable;
18 18
19import cuchaz.enigma.translation.TranslateResult; 19import cuchaz.enigma.translation.TranslateResult;
20import cuchaz.enigma.translation.Translator; 20import cuchaz.enigma.translation.Translator;
@@ -28,12 +28,10 @@ public abstract class ParentedEntry<P extends Entry<?>> implements Entry<P> {
28 protected final String name; 28 protected final String name;
29 protected final @Nullable String javadocs; 29 protected final @Nullable String javadocs;
30 30
31 protected ParentedEntry(P parent, String name, String javadocs) { 31 protected ParentedEntry(P parent, String name, @Nullable String javadocs) {
32 this.parent = parent; 32 this.parent = parent;
33 this.name = name; 33 this.name = Objects.requireNonNull(name, "Name cannot be null");
34 this.javadocs = javadocs; 34 this.javadocs = javadocs;
35
36 Preconditions.checkNotNull(name, "Name cannot be null");
37 } 35 }
38 36
39 @Override 37 @Override
@@ -42,7 +40,7 @@ public abstract class ParentedEntry<P extends Entry<?>> implements Entry<P> {
42 @Override 40 @Override
43 public abstract ParentedEntry<P> withName(String name); 41 public abstract ParentedEntry<P> withName(String name);
44 42
45 protected abstract TranslateResult<? extends ParentedEntry<P>> extendedTranslate(Translator translator, @Nonnull EntryMapping mapping); 43 protected abstract TranslateResult<? extends ParentedEntry<P>> extendedTranslate(Translator translator, @NotNull EntryMapping mapping);
46 44
47 @Override 45 @Override
48 public String getName() { 46 public String getName() {
diff --git a/enigma/src/main/java/cuchaz/enigma/utils/I18n.java b/enigma/src/main/java/cuchaz/enigma/utils/I18n.java
index 95512026..fff73526 100644
--- a/enigma/src/main/java/cuchaz/enigma/utils/I18n.java
+++ b/enigma/src/main/java/cuchaz/enigma/utils/I18n.java
@@ -8,15 +8,12 @@ import java.nio.charset.StandardCharsets;
8import java.util.ArrayList; 8import java.util.ArrayList;
9import java.util.Arrays; 9import java.util.Arrays;
10import java.util.Collections; 10import java.util.Collections;
11import java.util.HashMap;
12import java.util.List;
11import java.util.Map; 13import java.util.Map;
12import java.util.Objects; 14import java.util.Objects;
13import java.util.stream.Collectors; 15import java.util.stream.Collectors;
14import java.util.stream.Stream;
15 16
16import com.google.common.collect.ImmutableList;
17import com.google.common.collect.Maps;
18import com.google.common.reflect.ClassPath;
19import com.google.common.reflect.ClassPath.ResourceInfo;
20import com.google.gson.Gson; 17import com.google.gson.Gson;
21 18
22public class I18n { 19public class I18n {
@@ -24,7 +21,7 @@ public class I18n {
24 private static final Gson GSON = new Gson(); 21 private static final Gson GSON = new Gson();
25 private static Map<String, String> defaultTranslations = load(DEFAULT_LANGUAGE); 22 private static Map<String, String> defaultTranslations = load(DEFAULT_LANGUAGE);
26 private static Map<String, String> translations = defaultTranslations; 23 private static Map<String, String> translations = defaultTranslations;
27 private static Map<String, String> languageNames = Maps.newHashMap(); 24 private static Map<String, String> languageNames = new HashMap<>();
28 25
29 @SuppressWarnings("unchecked") 26 @SuppressWarnings("unchecked")
30 public static Map<String, String> load(String language) { 27 public static Map<String, String> load(String language) {
@@ -87,19 +84,22 @@ public class I18n {
87 } 84 }
88 85
89 public static ArrayList<String> getAvailableLanguages() { 86 public static ArrayList<String> getAvailableLanguages() {
90 ArrayList<String> list = new ArrayList<String>(); 87 ArrayList<String> list = new ArrayList<>();
91 88
92 try { 89 try {
93 ImmutableList<ResourceInfo> resources = ClassPath.from(Thread.currentThread().getContextClassLoader()).getResources().asList(); 90 ClassLoader cl = Thread.currentThread().getContextClassLoader();
94 Stream<ResourceInfo> dirStream = resources.stream(); 91 List<String> availableTranslations;
95 dirStream.forEach(context -> { 92
96 String file = context.getResourceName(); 93 try (InputStream is = cl.getResourceAsStream("lang/index.txt")) {
97 94 availableTranslations = Arrays.asList(
98 if (file.startsWith("lang/") && file.endsWith(".json")) { 95 new String(is.readAllBytes(), StandardCharsets.UTF_8)
99 String fileName = file.substring(5, file.length() - 5); 96 .split("\n")
100 list.add(fileName); 97 );
101 loadLanguageName(fileName); 98 }
102 } 99
100 availableTranslations.forEach(fileName -> {
101 list.add(fileName);
102 loadLanguageName(fileName);
103 }); 103 });
104 } catch (IOException e) { 104 } catch (IOException e) {
105 e.printStackTrace(); 105 e.printStackTrace();
diff --git a/enigma/src/main/java/cuchaz/enigma/utils/Utils.java b/enigma/src/main/java/cuchaz/enigma/utils/Utils.java
index a1926a8b..8b692b52 100644
--- a/enigma/src/main/java/cuchaz/enigma/utils/Utils.java
+++ b/enigma/src/main/java/cuchaz/enigma/utils/Utils.java
@@ -13,7 +13,6 @@ package cuchaz.enigma.utils;
13 13
14import java.io.IOException; 14import java.io.IOException;
15import java.io.InputStream; 15import java.io.InputStream;
16import java.io.InputStreamReader;
17import java.nio.charset.StandardCharsets; 16import java.nio.charset.StandardCharsets;
18import java.nio.file.Files; 17import java.nio.file.Files;
19import java.nio.file.Path; 18import java.nio.file.Path;
@@ -28,12 +27,9 @@ import java.util.function.Supplier;
28import java.util.zip.ZipEntry; 27import java.util.zip.ZipEntry;
29import java.util.zip.ZipFile; 28import java.util.zip.ZipFile;
30 29
31import com.google.common.base.Preconditions;
32import com.google.common.io.CharStreams;
33
34public class Utils { 30public class Utils {
35 public static String readStreamToString(InputStream in) throws IOException { 31 public static String readStreamToString(InputStream in) throws IOException {
36 return CharStreams.toString(new InputStreamReader(in, StandardCharsets.UTF_8)); 32 return new String(in.readAllBytes(), StandardCharsets.UTF_8);
37 } 33 }
38 34
39 public static String readResourceToString(String path) throws IOException { 35 public static String readResourceToString(String path) throws IOException {
@@ -55,7 +51,10 @@ public class Utils {
55 } 51 }
56 52
57 public static byte[] zipSha1(Path... paths) throws IOException { 53 public static byte[] zipSha1(Path... paths) throws IOException {
58 Preconditions.checkArgument(paths.length >= 1, "Must provide at least one zip"); 54 if (paths.length == 0) {
55 throw new IllegalArgumentException("Must provide at least one zip");
56 }
57
59 MessageDigest digest; 58 MessageDigest digest;
60 59
61 try { 60 try {
diff --git a/enigma/src/main/java/cuchaz/enigma/utils/validation/ValidationContext.java b/enigma/src/main/java/cuchaz/enigma/utils/validation/ValidationContext.java
index 416e8a05..0cb9b816 100644
--- a/enigma/src/main/java/cuchaz/enigma/utils/validation/ValidationContext.java
+++ b/enigma/src/main/java/cuchaz/enigma/utils/validation/ValidationContext.java
@@ -6,7 +6,7 @@ import java.util.HashSet;
6import java.util.List; 6import java.util.List;
7import java.util.Set; 7import java.util.Set;
8 8
9import javax.annotation.Nullable; 9import org.jetbrains.annotations.Nullable;
10 10
11import cuchaz.enigma.utils.validation.Message.Type; 11import cuchaz.enigma.utils.validation.Message.Type;
12 12
diff --git a/enigma/src/test/java/cuchaz/enigma/TokenChecker.java b/enigma/src/test/java/cuchaz/enigma/TokenChecker.java
index 5f510a42..3a4c24ac 100644
--- a/enigma/src/test/java/cuchaz/enigma/TokenChecker.java
+++ b/enigma/src/test/java/cuchaz/enigma/TokenChecker.java
@@ -13,11 +13,10 @@ package cuchaz.enigma;
13 13
14import java.io.IOException; 14import java.io.IOException;
15import java.nio.file.Path; 15import java.nio.file.Path;
16import java.util.ArrayList;
16import java.util.Collection; 17import java.util.Collection;
17import java.util.List; 18import java.util.List;
18 19
19import com.google.common.collect.Lists;
20
21import cuchaz.enigma.analysis.EntryReference; 20import cuchaz.enigma.analysis.EntryReference;
22import cuchaz.enigma.classprovider.CachingClassProvider; 21import cuchaz.enigma.classprovider.CachingClassProvider;
23import cuchaz.enigma.classprovider.JarClassProvider; 22import cuchaz.enigma.classprovider.JarClassProvider;
@@ -63,7 +62,7 @@ public class TokenChecker {
63 SourceIndex index = source.index(); 62 SourceIndex index = source.index();
64 63
65 // get the token values 64 // get the token values
66 List<String> values = Lists.newArrayList(); 65 List<String> values = new ArrayList<>();
67 66
68 for (Token token : index.getReferenceTokens((EntryReference<Entry<?>, Entry<?>>) reference)) { 67 for (Token token : index.getReferenceTokens((EntryReference<Entry<?>, Entry<?>>) reference)) {
69 values.add(string.substring(token.start, token.end)); 68 values.add(string.substring(token.start, token.end));
diff --git a/enigma/src/test/java/cuchaz/enigma/translation/mapping/serde/recaf/TestRecaf.java b/enigma/src/test/java/cuchaz/enigma/translation/mapping/serde/recaf/TestRecaf.java
index bd1ec20a..5f3e47c0 100644
--- a/enigma/src/test/java/cuchaz/enigma/translation/mapping/serde/recaf/TestRecaf.java
+++ b/enigma/src/test/java/cuchaz/enigma/translation/mapping/serde/recaf/TestRecaf.java
@@ -10,7 +10,6 @@ import java.nio.file.Path;
10import java.util.HashSet; 10import java.util.HashSet;
11import java.util.Set; 11import java.util.Set;
12 12
13import com.google.common.collect.Sets;
14import com.google.common.jimfs.Jimfs; 13import com.google.common.jimfs.Jimfs;
15import org.junit.Test; 14import org.junit.Test;
16 15
@@ -24,7 +23,7 @@ public class TestRecaf {
24 Set<String> contents; 23 Set<String> contents;
25 24
26 try (InputStream in = getClass().getResourceAsStream("/recaf.mappings")) { 25 try (InputStream in = getClass().getResourceAsStream("/recaf.mappings")) {
27 contents = Sets.newHashSet(new String(in.readAllBytes(), StandardCharsets.UTF_8).split("\\R")); 26 contents = Set.of(new String(in.readAllBytes(), StandardCharsets.UTF_8).split("\\R"));
28 } 27 }
29 28
30 try (FileSystem fs = Jimfs.newFileSystem()) { 29 try (FileSystem fs = Jimfs.newFileSystem()) {