summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorRoman Shevchenko <roman.shevchenko@jetbrains.com>2014-09-02 20:56:03 +0400
committerRoman Shevchenko <roman.shevchenko@jetbrains.com>2014-09-03 11:39:32 +0400
commit2df49d32a71818227e80a8628688906f2ede8a6a (patch)
treedced5f5ebf2f860d5683abf6910f180a67f9471d
parentc0c83126a69a0c652f343e972f727ffd7f5f10af (diff)
downloadfernflower-2df49d32a71818227e80a8628688906f2ede8a6a.tar
fernflower-2df49d32a71818227e80a8628688906f2ede8a6a.tar.gz
fernflower-2df49d32a71818227e80a8628688906f2ede8a6a.tar.lz
fernflower-2df49d32a71818227e80a8628688906f2ede8a6a.tar.xz
fernflower-2df49d32a71818227e80a8628688906f2ede8a6a.zip
java-decompiler: fixes and cleanups
- unified attribute loading code - common methods for checking member flags - verifying skip() - correct resource closing - typos
-rw-r--r--src/org/jetbrains/java/decompiler/main/AssertProcessor.java11
-rw-r--r--src/org/jetbrains/java/decompiler/main/ClassReference14Processor.java62
-rw-r--r--src/org/jetbrains/java/decompiler/main/ClassWriter.java62
-rw-r--r--src/org/jetbrains/java/decompiler/main/ClassesProcessor.java9
-rw-r--r--src/org/jetbrains/java/decompiler/main/EnumProcessor.java5
-rw-r--r--src/org/jetbrains/java/decompiler/main/InitializerProcessor.java2
-rw-r--r--src/org/jetbrains/java/decompiler/main/rels/ClassWrapper.java2
-rw-r--r--src/org/jetbrains/java/decompiler/main/rels/NestedClassProcessor.java10
-rw-r--r--src/org/jetbrains/java/decompiler/main/rels/NestedMemberAccess.java53
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/IdeaNotNullHelper.java2
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/exps/AssignmentExprent.java47
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/exps/InvocationExprent.java13
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAConstructorSparseEx.java3
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAUConstructorSparseEx.java3
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarDefinitionHelper.java2
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarTypeProcessor.java2
-rw-r--r--src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarVersionsProcessor.java2
-rw-r--r--src/org/jetbrains/java/decompiler/modules/renamer/IdentifierConverter.java8
-rw-r--r--src/org/jetbrains/java/decompiler/struct/ContextUnit.java11
-rw-r--r--src/org/jetbrains/java/decompiler/struct/StructClass.java298
-rw-r--r--src/org/jetbrains/java/decompiler/struct/StructContext.java15
-rw-r--r--src/org/jetbrains/java/decompiler/struct/StructField.java92
-rw-r--r--src/org/jetbrains/java/decompiler/struct/StructMember.java87
-rw-r--r--src/org/jetbrains/java/decompiler/struct/StructMethod.java317
-rw-r--r--src/org/jetbrains/java/decompiler/struct/attr/StructExceptionsAttribute.java27
-rw-r--r--src/org/jetbrains/java/decompiler/struct/attr/StructGeneralAttribute.java95
-rw-r--r--src/org/jetbrains/java/decompiler/struct/consts/ConstantPool.java148
-rw-r--r--src/org/jetbrains/java/decompiler/struct/gen/DataPoint.java2
-rw-r--r--src/org/jetbrains/java/decompiler/struct/lazy/LazyLoader.java155
-rw-r--r--src/org/jetbrains/java/decompiler/util/DataInputFullStream.java17
-rw-r--r--test/org/jetbrains/java/decompiler/SingleClassesTest.java2
31 files changed, 569 insertions, 995 deletions
diff --git a/src/org/jetbrains/java/decompiler/main/AssertProcessor.java b/src/org/jetbrains/java/decompiler/main/AssertProcessor.java
index fcef8d7..da703fd 100644
--- a/src/org/jetbrains/java/decompiler/main/AssertProcessor.java
+++ b/src/org/jetbrains/java/decompiler/main/AssertProcessor.java
@@ -69,7 +69,7 @@ public class AssertProcessor {
ClassWrapper wrapper = node.wrapper;
- boolean nosynthflag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
+ boolean noSynthFlag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
for (StructField fd : wrapper.getClassStruct().getFields()) {
@@ -78,12 +78,8 @@ public class AssertProcessor {
// initializer exists
if (wrapper.getStaticFieldInitializers().containsKey(keyField)) {
- int flags = fd.access_flags;
- boolean isSynthetic = (flags & CodeConstants.ACC_SYNTHETIC) != 0 || fd.getAttributes().containsKey("Synthetic");
-
// access flags set
- if ((flags & CodeConstants.ACC_STATIC) != 0 && (flags & CodeConstants.ACC_FINAL) != 0 &&
- (isSynthetic || nosynthflag)) {
+ if (fd.hasModifier(CodeConstants.ACC_STATIC) && fd.hasModifier(CodeConstants.ACC_FINAL) && (noSynthFlag || fd.isSynthetic())) {
// field type boolean
FieldDescriptor fdescr = FieldDescriptor.parseDescriptor(fd.getDescriptor());
@@ -100,8 +96,7 @@ public class AssertProcessor {
if (invexpr.getInstance() != null &&
invexpr.getInstance().type == Exprent.EXPRENT_CONST &&
- "desiredAssertionStatus".equals(invexpr.getName())
- &&
+ "desiredAssertionStatus".equals(invexpr.getName()) &&
"java/lang/Class".equals(invexpr.getClassname()) &&
invexpr.getLstParameters().isEmpty()) {
diff --git a/src/org/jetbrains/java/decompiler/main/ClassReference14Processor.java b/src/org/jetbrains/java/decompiler/main/ClassReference14Processor.java
index c912bf7..4552b1d 100644
--- a/src/org/jetbrains/java/decompiler/main/ClassReference14Processor.java
+++ b/src/org/jetbrains/java/decompiler/main/ClassReference14Processor.java
@@ -33,10 +33,7 @@ import org.jetbrains.java.decompiler.struct.gen.VarType;
import org.jetbrains.java.decompiler.util.InterpreterUtil;
import org.jetbrains.java.decompiler.util.VBStyleCollection;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.HashMap;
-import java.util.HashSet;
+import java.util.*;
import java.util.Map.Entry;
public class ClassReference14Processor {
@@ -105,7 +102,7 @@ public class ClassReference14Processor {
// find the synthetic method Class class$(String) if present
HashMap<ClassWrapper, MethodWrapper> mapClassMeths = new HashMap<ClassWrapper, MethodWrapper>();
- findClassMethod(node, mapClassMeths);
+ mapClassMethods(node, mapClassMeths);
if (mapClassMeths.isEmpty()) {
return;
@@ -176,37 +173,33 @@ public class ClassReference14Processor {
}
}
- private void findClassMethod(ClassNode node, HashMap<ClassWrapper, MethodWrapper> mapClassMeths) {
-
- boolean nosynthflag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
+ private void mapClassMethods(ClassNode node, Map<ClassWrapper, MethodWrapper> map) {
+ boolean noSynthFlag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
ClassWrapper wrapper = node.wrapper;
- for (MethodWrapper meth : wrapper.getMethods()) {
- StructMethod mt = meth.methodStruct;
+ for (MethodWrapper method : wrapper.getMethods()) {
+ StructMethod mt = method.methodStruct;
- if (((mt.getAccessFlags() & CodeConstants.ACC_SYNTHETIC) != 0 || mt.getAttributes().containsKey("Synthetic")
- || nosynthflag) &&
+ if ((noSynthFlag || mt.isSynthetic()) &&
mt.getDescriptor().equals("(Ljava/lang/String;)Ljava/lang/Class;") &&
- (mt.getAccessFlags() & CodeConstants.ACC_STATIC) != 0) {
-
- RootStatement root = meth.root;
- if (root != null) {
- if (root.getFirst().type == Statement.TYPE_TRYCATCH) {
- CatchStatement cst = (CatchStatement)root.getFirst();
- if (cst.getStats().size() == 2 && cst.getFirst().type == Statement.TYPE_BASICBLOCK &&
- cst.getStats().get(1).type == Statement.TYPE_BASICBLOCK &&
- cst.getVars().get(0).getVartype().equals(new VarType(CodeConstants.TYPE_OBJECT, 0, "java/lang/ClassNotFoundException"))) {
-
- BasicBlockStatement body = (BasicBlockStatement)cst.getFirst();
- BasicBlockStatement handler = (BasicBlockStatement)cst.getStats().get(1);
-
- if (body.getExprents().size() == 1 && handler.getExprents().size() == 1) {
- if (bodyexprent.equals(body.getExprents().get(0)) &&
- handlerexprent.equals(handler.getExprents().get(0))) {
- mapClassMeths.put(wrapper, meth);
- break;
- }
+ mt.hasModifier(CodeConstants.ACC_STATIC)) {
+
+ RootStatement root = method.root;
+ if (root != null && root.getFirst().type == Statement.TYPE_TRYCATCH) {
+ CatchStatement cst = (CatchStatement)root.getFirst();
+ if (cst.getStats().size() == 2 && cst.getFirst().type == Statement.TYPE_BASICBLOCK &&
+ cst.getStats().get(1).type == Statement.TYPE_BASICBLOCK &&
+ cst.getVars().get(0).getVartype().equals(new VarType(CodeConstants.TYPE_OBJECT, 0, "java/lang/ClassNotFoundException"))) {
+
+ BasicBlockStatement body = (BasicBlockStatement)cst.getFirst();
+ BasicBlockStatement handler = (BasicBlockStatement)cst.getStats().get(1);
+
+ if (body.getExprents().size() == 1 && handler.getExprents().size() == 1) {
+ if (bodyexprent.equals(body.getExprents().get(0)) &&
+ handlerexprent.equals(handler.getExprents().get(0))) {
+ map.put(wrapper, method);
+ break;
}
}
}
@@ -216,7 +209,7 @@ public class ClassReference14Processor {
// iterate nested classes
for (ClassNode nd : node.nested) {
- findClassMethod(nd, mapClassMeths);
+ mapClassMethods(nd, map);
}
}
@@ -269,9 +262,8 @@ public class ClassReference14Processor {
StructField fd =
wrapper.getClassStruct().getField(field.getName(), field.getDescriptor().descriptorString); // FIXME: can be null! why??
- if (fd != null && (fd.access_flags & CodeConstants.ACC_STATIC) != 0 &&
- ((fd.access_flags & CodeConstants.ACC_SYNTHETIC) != 0 || fd.getAttributes().containsKey("Synthetic")
- || DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET))) {
+ if (fd != null && fd.hasModifier(CodeConstants.ACC_STATIC) &&
+ (fd.isSynthetic() || DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET))) {
if (fexpr.getLstOperands().get(1).type == Exprent.EXPRENT_ASSIGNMENT && fexpr.getLstOperands().get(2).equals(field)) {
AssignmentExprent asexpr = (AssignmentExprent)fexpr.getLstOperands().get(1);
diff --git a/src/org/jetbrains/java/decompiler/main/ClassWriter.java b/src/org/jetbrains/java/decompiler/main/ClassWriter.java
index 5258dee..c6dc7a4 100644
--- a/src/org/jetbrains/java/decompiler/main/ClassWriter.java
+++ b/src/org/jetbrains/java/decompiler/main/ClassWriter.java
@@ -99,7 +99,7 @@ public class ClassWriter {
ref14processor.processClassReferences(node);
}
- if (DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM) && (cl.access_flags & CodeConstants.ACC_ENUM) != 0) {
+ if (cl.hasModifier(CodeConstants.ACC_ENUM) && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM)) {
EnumProcessor.clearEnum(wrapper);
}
@@ -234,11 +234,8 @@ public class ClassWriter {
boolean mthidden = false;
for (StructMethod mt : cl.getMethods()) {
-
- int flags = mt.getAccessFlags();
-
- boolean isSynthetic = (flags & CodeConstants.ACC_SYNTHETIC) != 0 || mt.getAttributes().containsKey("Synthetic");
- boolean isBridge = (flags & CodeConstants.ACC_BRIDGE) != 0;
+ boolean isSynthetic = mt.isSynthetic();
+ boolean isBridge = mt.hasModifier(CodeConstants.ACC_BRIDGE);
if ((!isSynthetic || !DecompilerContext.getOption(IFernflowerPreferences.REMOVE_SYNTHETIC)) &&
(!isBridge || !DecompilerContext.getOption(IFernflowerPreferences.REMOVE_BRIDGE)) &&
@@ -262,12 +259,10 @@ public class ClassWriter {
// fields
for (StructField fd : cl.getFields()) {
- int flags = fd.access_flags;
- boolean isSynthetic = (flags & CodeConstants.ACC_SYNTHETIC) != 0 || fd.getAttributes().containsKey("Synthetic");
- if ((!isSynthetic || !DecompilerContext.getOption(IFernflowerPreferences.REMOVE_SYNTHETIC))
- && !wrapper.getHideMembers().contains(InterpreterUtil.makeUniqueKey(fd.getName(), fd.getDescriptor()))) {
-
- boolean isEnum = DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM) && (flags & CodeConstants.ACC_ENUM) != 0;
+ boolean hide = fd.isSynthetic() && DecompilerContext.getOption(IFernflowerPreferences.REMOVE_SYNTHETIC) ||
+ wrapper.getHideMembers().contains(InterpreterUtil.makeUniqueKey(fd.getName(), fd.getDescriptor()));
+ if (!hide) {
+ boolean isEnum = fd.hasModifier(CodeConstants.ACC_ENUM) && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
if (isEnum) {
if (enumfields) {
bufstrwriter1.write(",");
@@ -310,12 +305,11 @@ public class ClassWriter {
// member classes
for (ClassNode inner : node.nested) {
if (inner.type == ClassNode.CLASS_MEMBER) {
- StructClass innercl = inner.classStruct;
-
- boolean isSynthetic =
- ((inner.access | innercl.access_flags) & CodeConstants.ACC_SYNTHETIC) != 0 || innercl.getAttributes().containsKey("Synthetic");
- if ((!isSynthetic || !DecompilerContext.getOption(IFernflowerPreferences.REMOVE_SYNTHETIC))
- && !wrapper.getHideMembers().contains(innercl.qualifiedName)) {
+ StructClass innerCl = inner.classStruct;
+ boolean isSynthetic = (inner.access & CodeConstants.ACC_SYNTHETIC) != 0 || innerCl.isSynthetic();
+ boolean hide = isSynthetic && DecompilerContext.getOption(IFernflowerPreferences.REMOVE_SYNTHETIC) ||
+ wrapper.getHideMembers().contains(innerCl.qualifiedName);
+ if (!hide) {
writer.write(DecompilerContext.getNewLineSeparator());
classToJava(inner, writer, indent + 1);
}
@@ -347,7 +341,7 @@ public class ClassWriter {
ClassWrapper wrapper = node.wrapper;
StructClass cl = wrapper.getClassStruct();
- int flags = node.type == ClassNode.CLASS_ROOT ? cl.access_flags : node.access;
+ int flags = node.type == ClassNode.CLASS_ROOT ? cl.getAccessFlags() : node.access;
boolean isInterface = (flags & CodeConstants.ACC_INTERFACE) != 0;
boolean isAnnotation = (flags & CodeConstants.ACC_ANNOTATION) != 0;
boolean isEnum = DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM) && (flags & CodeConstants.ACC_ENUM) != 0;
@@ -486,8 +480,7 @@ public class ClassWriter {
String indstr = InterpreterUtil.getIndentString(indent);
- boolean isInterface = (cl.access_flags & CodeConstants.ACC_INTERFACE) != 0;
- int flags = fd.access_flags;
+ boolean isInterface = cl.hasModifier(CodeConstants.ACC_INTERFACE);
if (interceptor != null) {
String oldname = interceptor.getOldName(cl.qualifiedName + " " + fd.getName() + " " + fd.getDescriptor());
@@ -515,8 +508,8 @@ public class ClassWriter {
writer.write(DecompilerContext.getNewLineSeparator());
}
- boolean isSynthetic = (flags & CodeConstants.ACC_SYNTHETIC) != 0 || fd.getAttributes().containsKey("Synthetic");
- boolean isEnum = DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM) && (flags & CodeConstants.ACC_ENUM) != 0;
+ boolean isSynthetic = fd.isSynthetic();
+ boolean isEnum = fd.hasModifier(CodeConstants.ACC_ENUM) && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
if (isSynthetic) {
writer.write(indstr);
@@ -529,7 +522,7 @@ public class ClassWriter {
if (!isEnum) {
for (int i = 0; i < modval_field.length; i++) {
if (!isInterface || !mod_notinterface_fields.contains(modval_field[i])) {
- if ((flags & modval_field[i]) != 0) {
+ if (fd.hasModifier(modval_field[i])) {
writer.write(modstr_field[i]);
}
}
@@ -559,7 +552,7 @@ public class ClassWriter {
writer.write(fd.getName());
Exprent initializer;
- if ((flags & CodeConstants.ACC_STATIC) != 0) {
+ if (fd.hasModifier(CodeConstants.ACC_STATIC)) {
initializer = wrapper.getStaticFieldInitializers().getWithKey(InterpreterUtil.makeUniqueKey(fd.getName(), fd.getDescriptor()));
}
else {
@@ -577,7 +570,7 @@ public class ClassWriter {
writer.write(initializer.toJava(indent));
}
}
- else if ((flags & CodeConstants.ACC_FINAL) != 0 && (flags & CodeConstants.ACC_STATIC) != 0) {
+ else if (fd.hasModifier(CodeConstants.ACC_FINAL) && fd.hasModifier(CodeConstants.ACC_STATIC)) {
StructConstantValueAttribute attr =
(StructConstantValueAttribute)fd.getAttributes().getWithKey(StructGeneralAttribute.ATTRIBUTE_CONSTANT_VALUE);
if (attr != null) {
@@ -704,9 +697,9 @@ public class ClassWriter {
MethodWrapper methold = (MethodWrapper)DecompilerContext.getProperty(DecompilerContext.CURRENT_METHOD_WRAPPER);
DecompilerContext.setProperty(DecompilerContext.CURRENT_METHOD_WRAPPER, meth);
- boolean isInterface = (cl.access_flags & CodeConstants.ACC_INTERFACE) != 0;
- boolean isAnnotation = (cl.access_flags & CodeConstants.ACC_ANNOTATION) != 0;
- boolean isEnum = (cl.access_flags & CodeConstants.ACC_ENUM) != 0 && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
+ boolean isInterface = cl.hasModifier(CodeConstants.ACC_INTERFACE);
+ boolean isAnnotation = cl.hasModifier(CodeConstants.ACC_ANNOTATION);
+ boolean isEnum = cl.hasModifier(CodeConstants.ACC_ENUM) && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
boolean isDeprecated = mt.getAttributes().containsKey("Deprecated");
String indstr = InterpreterUtil.getIndentString(indent);
@@ -721,9 +714,8 @@ public class ClassWriter {
if ((flags & CodeConstants.ACC_NATIVE) != 0) {
flags &= ~CodeConstants.ACC_STRICT; // compiler bug: a strictfp class sets all methods to strictfp
}
-
if ("<clinit>".equals(mt.getName())) {
- flags &= CodeConstants.ACC_STATIC; // ingnore all modifiers except 'static' in a static initializer
+ flags &= CodeConstants.ACC_STATIC; // ignore all modifiers except 'static' in a static initializer
}
if (interceptor != null) {
@@ -816,7 +808,7 @@ public class ClassWriter {
if (!clinit && !dinit) {
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
// formal type parameters
if (descriptor != null && !descriptor.fparameters.isEmpty()) {
@@ -900,8 +892,7 @@ public class ClassWriter {
if (descriptor != null) {
GenericType partype = descriptor.params.get(i);
- boolean isVarArgs = (i == lastparam_index && (mt.getAccessFlags() & CodeConstants.ACC_VARARGS) != 0
- && partype.arraydim > 0);
+ boolean isVarArgs = (i == lastparam_index && mt.hasModifier(CodeConstants.ACC_VARARGS) && partype.arraydim > 0);
if (isVarArgs) {
partype.arraydim--;
@@ -922,8 +913,7 @@ public class ClassWriter {
else {
VarType partype = md.params[i].copy();
- boolean isVarArgs = (i == lastparam_index && (mt.getAccessFlags() & CodeConstants.ACC_VARARGS) != 0
- && partype.arraydim > 0);
+ boolean isVarArgs = (i == lastparam_index && mt.hasModifier(CodeConstants.ACC_VARARGS) && partype.arraydim > 0);
if (isVarArgs) {
partype.decArrayDim();
diff --git a/src/org/jetbrains/java/decompiler/main/ClassesProcessor.java b/src/org/jetbrains/java/decompiler/main/ClassesProcessor.java
index b822021..a16e4e0 100644
--- a/src/org/jetbrains/java/decompiler/main/ClassesProcessor.java
+++ b/src/org/jetbrains/java/decompiler/main/ClassesProcessor.java
@@ -139,7 +139,7 @@ public class ClassesProcessor {
}
ClassNode node = new ClassNode(ClassNode.CLASS_ROOT, cl);
- node.access = cl.access_flags;
+ node.access = cl.getAccessFlags();
mapRootClasses.put(cl.qualifiedName, node);
}
}
@@ -394,12 +394,9 @@ public class ClassesProcessor {
anonimousClassType = new VarType(lambda_class_name, true);
boolean is_method_reference = (content_class_name != classStruct.qualifiedName);
- StructMethod mt = null;
-
if (!is_method_reference) { // content method in the same class, check synthetic flag
- mt = classStruct.getMethod(content_method_name, content_method_descriptor);
- is_method_reference = !((mt.getAccessFlags() & CodeConstants.ACC_SYNTHETIC) != 0 ||
- mt.getAttributes().containsKey("Synthetic")); // if not synthetic -> method reference
+ StructMethod mt = classStruct.getMethod(content_method_name, content_method_descriptor);
+ is_method_reference = !mt.isSynthetic(); // if not synthetic -> method reference
}
lambda_information.is_method_reference = is_method_reference;
diff --git a/src/org/jetbrains/java/decompiler/main/EnumProcessor.java b/src/org/jetbrains/java/decompiler/main/EnumProcessor.java
index 93746b7..fcdeaf1 100644
--- a/src/org/jetbrains/java/decompiler/main/EnumProcessor.java
+++ b/src/org/jetbrains/java/decompiler/main/EnumProcessor.java
@@ -82,7 +82,7 @@ public class EnumProcessor {
// hide dummy synthetic fields of enum constants
for (StructField fd : cl.getFields()) {
- if ((fd.access_flags & CodeConstants.ACC_ENUM) != 0) {
+ if (fd.hasModifier(CodeConstants.ACC_ENUM)) {
Exprent initializer =
wrapper.getStaticFieldInitializers().getWithKey(InterpreterUtil.makeUniqueKey(fd.getName(), fd.getDescriptor()));
if (initializer != null && initializer.type == Exprent.EXPRENT_NEW) {
@@ -97,10 +97,9 @@ public class EnumProcessor {
}
private static void hideDummyFieldInConstant(ClassWrapper wrapper) {
-
StructClass cl = wrapper.getClassStruct();
for (StructField fd : cl.getFields()) {
- if ((fd.access_flags & CodeConstants.ACC_SYNTHETIC) != 0) {
+ if (fd.isSynthetic()) {
FieldDescriptor descr = FieldDescriptor.parseDescriptor(fd.getDescriptor());
VarType ret = descr.type;
diff --git a/src/org/jetbrains/java/decompiler/main/InitializerProcessor.java b/src/org/jetbrains/java/decompiler/main/InitializerProcessor.java
index 59689dc..aabea15 100644
--- a/src/org/jetbrains/java/decompiler/main/InitializerProcessor.java
+++ b/src/org/jetbrains/java/decompiler/main/InitializerProcessor.java
@@ -76,7 +76,7 @@ public class InitializerProcessor {
FieldExprent fexpr = (FieldExprent)asexpr.getLeft();
if (fexpr.getClassname().equals(wrapper.getClassStruct().qualifiedName)) {
StructField structField = wrapper.getClassStruct().getField(fexpr.getName(), fexpr.getDescriptor().descriptorString);
- if (structField != null && (structField.access_flags & CodeConstants.ACC_FINAL) != 0) {
+ if (structField != null && structField.hasModifier(CodeConstants.ACC_FINAL)) {
action = 1;
}
}
diff --git a/src/org/jetbrains/java/decompiler/main/rels/ClassWrapper.java b/src/org/jetbrains/java/decompiler/main/rels/ClassWrapper.java
index 2cadeae..cbaf227 100644
--- a/src/org/jetbrains/java/decompiler/main/rels/ClassWrapper.java
+++ b/src/org/jetbrains/java/decompiler/main/rels/ClassWrapper.java
@@ -123,7 +123,7 @@ public class ClassWrapper {
}
}
else {
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
int paramcount = 0;
diff --git a/src/org/jetbrains/java/decompiler/main/rels/NestedClassProcessor.java b/src/org/jetbrains/java/decompiler/main/rels/NestedClassProcessor.java
index 3eec983..003bdc2 100644
--- a/src/org/jetbrains/java/decompiler/main/rels/NestedClassProcessor.java
+++ b/src/org/jetbrains/java/decompiler/main/rels/NestedClassProcessor.java
@@ -71,7 +71,7 @@ public class NestedClassProcessor {
// ensure not-empty class name
if ((child.type == ClassNode.CLASS_LOCAL || child.type == ClassNode.CLASS_MEMBER) && child.simpleName == null) {
StructClass cl = child.classStruct;
- if (((child.access | cl.access_flags) & CodeConstants.ACC_SYNTHETIC) != 0 || cl.getAttributes().containsKey("Synthetic")) {
+ if ((child.access & CodeConstants.ACC_SYNTHETIC) != 0 || cl.isSynthetic()) {
child.simpleName = "SyntheticClass_" + (++synthetics);
}
else {
@@ -675,7 +675,7 @@ public class NestedClassProcessor {
return null;
}
- boolean notsynth = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
+ boolean noSynthFlag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
// no loop at the begin
DirectNode firstnode = graph.first;
@@ -692,10 +692,8 @@ public class NestedClassProcessor {
if (fd != null) { // local (== not inherited) field
if (cl.qualifiedName.equals(left.getClassname()) &&
- (fd.access_flags & CodeConstants.ACC_FINAL) != 0 &&
- ((fd.access_flags & CodeConstants.ACC_SYNTHETIC) != 0 ||
- fd.getAttributes().containsKey("Synthetic") ||
- (notsynth && (fd.access_flags & CodeConstants.ACC_PRIVATE) != 0))) {
+ fd.hasModifier(CodeConstants.ACC_FINAL) &&
+ (fd.isSynthetic() || (noSynthFlag && fd.hasModifier(CodeConstants.ACC_PRIVATE)))) {
field = InterpreterUtil.makeUniqueKey(left.getName(), left.getDescriptor().descriptorString);
break;
}
diff --git a/src/org/jetbrains/java/decompiler/main/rels/NestedMemberAccess.java b/src/org/jetbrains/java/decompiler/main/rels/NestedMemberAccess.java
index c1251a7..f61de85 100644
--- a/src/org/jetbrains/java/decompiler/main/rels/NestedMemberAccess.java
+++ b/src/org/jetbrains/java/decompiler/main/rels/NestedMemberAccess.java
@@ -32,26 +32,25 @@ import org.jetbrains.java.decompiler.util.InterpreterUtil;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
+import java.util.Map;
public class NestedMemberAccess {
private static final int METHOD_ACCESS_NORMAL = 1;
- private static final int METHOD_ACCESS_FIELDGET = 2;
- private static final int METHOD_ACCESS_FIELDSET = 3;
+ private static final int METHOD_ACCESS_FIELD_GET = 2;
+ private static final int METHOD_ACCESS_FIELD_SET = 3;
private static final int METHOD_ACCESS_METHOD = 4;
- private boolean notSetSync;
-
- private HashMap<MethodWrapper, Integer> mapMethodType = new HashMap<MethodWrapper, Integer>();
+ private boolean noSynthFlag;
+ private Map<MethodWrapper, Integer> mapMethodType = new HashMap<MethodWrapper, Integer>();
public void propagateMemberAccess(ClassNode root) {
-
if (root.nested.isEmpty()) {
return;
}
- notSetSync = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
+ noSynthFlag = DecompilerContext.getOption(IFernflowerPreferences.SYNTHETIC_NOT_SET);
computeMethodTypes(root);
@@ -60,7 +59,6 @@ public class NestedMemberAccess {
private void computeMethodTypes(ClassNode node) {
-
if (node.type == ClassNode.CLASS_LAMBDA) {
return;
}
@@ -69,27 +67,24 @@ public class NestedMemberAccess {
computeMethodTypes(nd);
}
- for (MethodWrapper meth : node.wrapper.getMethods()) {
- computeMethodType(node, meth);
+ for (MethodWrapper method : node.wrapper.getMethods()) {
+ computeMethodType(node, method);
}
}
- private void computeMethodType(ClassNode node, MethodWrapper meth) {
-
+ private void computeMethodType(ClassNode node, MethodWrapper method) {
int type = METHOD_ACCESS_NORMAL;
- if (meth.root != null) {
-
- DirectGraph graph = meth.getOrBuildGraph();
+ if (method.root != null) {
+ DirectGraph graph = method.getOrBuildGraph();
- int flags = meth.methodStruct.getAccessFlags();
- if (((flags & CodeConstants.ACC_SYNTHETIC) != 0 || meth.methodStruct.getAttributes().containsKey("Synthetic") || notSetSync) &&
- (flags & CodeConstants.ACC_STATIC) != 0) {
+ StructMethod mt = method.methodStruct;
+ if ((noSynthFlag || mt.isSynthetic()) && mt.hasModifier(CodeConstants.ACC_STATIC)) {
if (graph.nodes.size() == 2) { // incl. dummy exit node
if (graph.first.exprents.size() == 1) {
Exprent exprent = graph.first.exprents.get(0);
- MethodDescriptor mtdesc = MethodDescriptor.parseDescriptor(meth.methodStruct.getDescriptor());
+ MethodDescriptor mtdesc = MethodDescriptor.parseDescriptor(mt.getDescriptor());
int parcount = mtdesc.params.length;
Exprent exprCore = exprent;
@@ -109,7 +104,7 @@ public class NestedMemberAccess {
if (fexpr.getClassname().equals(node.classStruct.qualifiedName)) { // FIXME: check for private flag of the field
if (fexpr.isStatic() ||
(fexpr.getInstance().type == Exprent.EXPRENT_VAR && ((VarExprent)fexpr.getInstance()).getIndex() == 0)) {
- type = METHOD_ACCESS_FIELDGET;
+ type = METHOD_ACCESS_FIELD_GET;
}
}
}
@@ -118,7 +113,7 @@ public class NestedMemberAccess {
if (parcount == 1) {
// this or final variable
if (((VarExprent)exprCore).getIndex() != 0) {
- type = METHOD_ACCESS_FIELDGET;
+ type = METHOD_ACCESS_FIELD_GET;
}
}
@@ -136,7 +131,7 @@ public class NestedMemberAccess {
if (fexpras.isStatic() ||
(fexpras.getInstance().type == Exprent.EXPRENT_VAR && ((VarExprent)fexpras.getInstance()).getIndex() == 0)) {
if (((VarExprent)asexpr.getRight()).getIndex() == parcount - 1) {
- type = METHOD_ACCESS_FIELDSET;
+ type = METHOD_ACCESS_FIELD_SET;
}
}
}
@@ -179,7 +174,7 @@ public class NestedMemberAccess {
if (exprentFirst.type == Exprent.EXPRENT_ASSIGNMENT &&
exprentSecond.type == Exprent.EXPRENT_EXIT) {
- MethodDescriptor mtdesc = MethodDescriptor.parseDescriptor(meth.methodStruct.getDescriptor());
+ MethodDescriptor mtdesc = MethodDescriptor.parseDescriptor(mt.getDescriptor());
int parcount = mtdesc.params.length;
AssignmentExprent asexpr = (AssignmentExprent)exprentFirst;
@@ -196,7 +191,7 @@ public class NestedMemberAccess {
if (exexpr.getExittype() == ExitExprent.EXIT_RETURN && exexpr.getValue() != null) {
if (exexpr.getValue().type == Exprent.EXPRENT_VAR &&
((VarExprent)asexpr.getRight()).getIndex() == parcount - 1) {
- type = METHOD_ACCESS_FIELDSET;
+ type = METHOD_ACCESS_FIELD_SET;
}
}
}
@@ -211,10 +206,10 @@ public class NestedMemberAccess {
}
if (type != METHOD_ACCESS_NORMAL) {
- mapMethodType.put(meth, type);
+ mapMethodType.put(method, type);
}
else {
- mapMethodType.remove(meth);
+ mapMethodType.remove(method);
}
}
@@ -365,7 +360,7 @@ public class NestedMemberAccess {
Exprent retexprent = null;
switch (type) {
- case METHOD_ACCESS_FIELDGET:
+ case METHOD_ACCESS_FIELD_GET:
ExitExprent exsource = (ExitExprent)source;
if (exsource.getValue().type == Exprent.EXPRENT_VAR) { // qualified this
VarExprent var = (VarExprent)exsource.getValue();
@@ -393,7 +388,7 @@ public class NestedMemberAccess {
retexprent = ret;
}
break;
- case METHOD_ACCESS_FIELDSET:
+ case METHOD_ACCESS_FIELD_SET:
AssignmentExprent ret;
if (source.type == Exprent.EXPRENT_EXIT) {
ExitExprent extex = (ExitExprent)source;
@@ -440,7 +435,7 @@ public class NestedMemberAccess {
if (node.type == ClassNode.CLASS_ROOT || (node.access & CodeConstants.ACC_STATIC) != 0) {
StructMethod mt = methsource.methodStruct;
- if ((mt.getAccessFlags() & CodeConstants.ACC_SYNTHETIC) == 0 && !mt.getAttributes().containsKey("Synthetic")) {
+ if (!mt.isSynthetic()) {
hide = false;
}
}
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/IdeaNotNullHelper.java b/src/org/jetbrains/java/decompiler/modules/decompiler/IdeaNotNullHelper.java
index 9934298..0f5141a 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/IdeaNotNullHelper.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/IdeaNotNullHelper.java
@@ -82,7 +82,7 @@ public class IdeaNotNullHelper {
if (first_param.type == Exprent.EXPRENT_VAR) {
VarExprent var = (VarExprent)first_param;
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
VBStyleCollection<StructGeneralAttribute, String> attributes = mt.getAttributes();
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/exps/AssignmentExprent.java b/src/org/jetbrains/java/decompiler/modules/decompiler/exps/AssignmentExprent.java
index 33d30e9..6c6b1f3 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/exps/AssignmentExprent.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/exps/AssignmentExprent.java
@@ -109,43 +109,40 @@ public class AssignmentExprent extends Exprent {
VarType leftType = left.getExprType();
VarType rightType = right.getExprType();
- String res = right.toJava(indent);
-
- if (condtype == CONDITION_NONE &&
- !leftType.isSuperset(rightType) &&
- (rightType.equals(VarType.VARTYPE_OBJECT) || leftType.type != CodeConstants.TYPE_OBJECT)) {
- if (right.getPrecedence() >= FunctionExprent.getPrecedence(FunctionExprent.FUNCTION_CAST)) {
- res = "(" + res + ")";
- }
-
- res = "(" + ExprProcessor.getCastTypeName(leftType) + ")" + res;
- }
-
- StringBuilder buffer = new StringBuilder();
-
- boolean finstat_init = false;
+ boolean fieldInStatInit = false;
if (left.type == Exprent.EXPRENT_FIELD) { // first assignment to a final field. Field name without "this" in front of it
FieldExprent field = (FieldExprent)left;
- if (field.isStatic()) {
- ClassNode node = ((ClassNode)DecompilerContext.getProperty(DecompilerContext.CURRENT_CLASS_NODE));
- if (node != null) {
- StructClass cl = node.classStruct;
- StructField fd = cl.getField(field.getName(), field.getDescriptor().descriptorString);
-
- if (fd != null && (fd.access_flags & CodeConstants.ACC_FINAL) != 0) {
- finstat_init = true;
- }
+ ClassNode node = ((ClassNode)DecompilerContext.getProperty(DecompilerContext.CURRENT_CLASS_NODE));
+ if (node != null) {
+ StructClass cl = node.classStruct;
+ StructField fd = cl.getField(field.getName(), field.getDescriptor().descriptorString);
+ if (fd != null && field.isStatic() && fd.hasModifier(CodeConstants.ACC_FINAL)) {
+ fieldInStatInit = true;
}
}
}
- if (finstat_init) {
+ StringBuilder buffer = new StringBuilder();
+
+ if (fieldInStatInit) {
buffer.append(((FieldExprent)left).getName());
}
else {
buffer.append(left.toJava(indent));
}
+ String res = right.toJava(indent);
+
+ if (condtype == CONDITION_NONE &&
+ !leftType.isSuperset(rightType) &&
+ (rightType.equals(VarType.VARTYPE_OBJECT) || leftType.type != CodeConstants.TYPE_OBJECT)) {
+ if (right.getPrecedence() >= FunctionExprent.getPrecedence(FunctionExprent.FUNCTION_CAST)) {
+ res = "(" + res + ")";
+ }
+
+ res = "(" + ExprProcessor.getCastTypeName(leftType) + ")" + res;
+ }
+
buffer.append(condtype == CONDITION_NONE ? " = " : funceq[condtype]).append(res);
return buffer.toString();
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/exps/InvocationExprent.java b/src/org/jetbrains/java/decompiler/modules/decompiler/exps/InvocationExprent.java
index 1edebc9..04758dc 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/exps/InvocationExprent.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/exps/InvocationExprent.java
@@ -330,20 +330,19 @@ public class InvocationExprent extends Exprent {
List<VarVersionPaar> sigFields = null;
boolean isEnum = false;
if (functype == TYP_INIT) {
- ClassNode newnode = DecompilerContext.getClassProcessor().getMapRootClasses().get(classname);
+ ClassNode newNode = DecompilerContext.getClassProcessor().getMapRootClasses().get(classname);
- if (newnode != null) { // own class
- if (newnode.wrapper != null) {
- sigFields = newnode.wrapper.getMethodWrapper("<init>", stringDescriptor).signatureFields;
+ if (newNode != null) { // own class
+ if (newNode.wrapper != null) {
+ sigFields = newNode.wrapper.getMethodWrapper("<init>", stringDescriptor).signatureFields;
}
else {
- if (newnode.type == ClassNode.CLASS_MEMBER && (newnode.access & CodeConstants.ACC_STATIC) == 0) { // non-static member class
+ if (newNode.type == ClassNode.CLASS_MEMBER && (newNode.access & CodeConstants.ACC_STATIC) == 0) { // non-static member class
sigFields = new ArrayList<VarVersionPaar>(Collections.nCopies(lstParameters.size(), (VarVersionPaar)null));
sigFields.set(0, new VarVersionPaar(-1, 0));
}
}
- isEnum = (newnode.classStruct.access_flags & CodeConstants.ACC_ENUM) != 0 &&
- DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
+ isEnum = newNode.classStruct.hasModifier(CodeConstants.ACC_ENUM) && DecompilerContext.getOption(IFernflowerPreferences.DECOMPILE_ENUM);
}
}
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAConstructorSparseEx.java b/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAConstructorSparseEx.java
index 2150f86..dbec793 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAConstructorSparseEx.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAConstructorSparseEx.java
@@ -487,8 +487,7 @@ public class SSAConstructorSparseEx {
}
private SFormsFastMapDirect createFirstMap(StructMethod mt) {
-
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAUConstructorSparseEx.java b/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAUConstructorSparseEx.java
index 97b6448..fbd652c 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAUConstructorSparseEx.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/sforms/SSAUConstructorSparseEx.java
@@ -756,8 +756,7 @@ public class SSAUConstructorSparseEx {
}
private SFormsFastMapDirect createFirstMap(StructMethod mt, RootStatement root) {
-
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarDefinitionHelper.java b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarDefinitionHelper.java
index 24207ef..fdd6cd5 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarDefinitionHelper.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarDefinitionHelper.java
@@ -53,7 +53,7 @@ public class VarDefinitionHelper {
VarNamesCollector vc = DecompilerContext.getVarNamesCollector();
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarTypeProcessor.java b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarTypeProcessor.java
index d7d3d2e..a21d71f 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarTypeProcessor.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarTypeProcessor.java
@@ -49,7 +49,7 @@ public class VarTypeProcessor {
StructMethod mt = (StructMethod)DecompilerContext.getProperty(DecompilerContext.CURRENT_METHOD);
// method descriptor
- boolean thisvar = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0;
+ boolean thisvar = !mt.hasModifier(CodeConstants.ACC_STATIC);
MethodDescriptor md = (MethodDescriptor)DecompilerContext.getProperty(DecompilerContext.CURRENT_METHOD_DESCRIPTOR);
diff --git a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarVersionsProcessor.java b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarVersionsProcessor.java
index 09d8def..06b7216 100644
--- a/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarVersionsProcessor.java
+++ b/src/org/jetbrains/java/decompiler/modules/decompiler/vars/VarVersionsProcessor.java
@@ -170,7 +170,7 @@ public class VarVersionsProcessor {
}
}
- boolean is_method_static = (mt.getAccessFlags() & CodeConstants.ACC_STATIC) != 0;
+ boolean is_method_static = mt.hasModifier(CodeConstants.ACC_STATIC);
final HashMap<VarVersionPaar, Integer> mapMergedVersions = new HashMap<VarVersionPaar, Integer>();
diff --git a/src/org/jetbrains/java/decompiler/modules/renamer/IdentifierConverter.java b/src/org/jetbrains/java/decompiler/modules/renamer/IdentifierConverter.java
index 546ece3..adff502 100644
--- a/src/org/jetbrains/java/decompiler/modules/renamer/IdentifierConverter.java
+++ b/src/org/jetbrains/java/decompiler/modules/renamer/IdentifierConverter.java
@@ -232,11 +232,10 @@ public class IdentifierConverter {
StructMethod mt = methods.get(i);
String key = methods.getKey(i);
- int access_flags = mt.getAccessFlags();
- boolean isPrivate = ((access_flags & CodeConstants.ACC_PRIVATE) != 0);
+ boolean isPrivate = mt.hasModifier(CodeConstants.ACC_PRIVATE);
String name = mt.getName();
- if (!cl.isOwn() || (access_flags & CodeConstants.ACC_NATIVE) != 0) {
+ if (!cl.isOwn() || mt.hasModifier(CodeConstants.ACC_NATIVE)) {
// external and native methods must not be renamed
if (!isPrivate) {
names.put(key, name);
@@ -426,8 +425,7 @@ public class IdentifierConverter {
break;
}
else {
-
- boolean isInterface = ((clstr.access_flags & CodeConstants.ACC_INTERFACE) != 0);
+ boolean isInterface = clstr.hasModifier(CodeConstants.ACC_INTERFACE);
boolean found_parent = false;
if (isInterface) {
diff --git a/src/org/jetbrains/java/decompiler/struct/ContextUnit.java b/src/org/jetbrains/java/decompiler/struct/ContextUnit.java
index c942e76..44ec746 100644
--- a/src/org/jetbrains/java/decompiler/struct/ContextUnit.java
+++ b/src/org/jetbrains/java/decompiler/struct/ContextUnit.java
@@ -18,6 +18,7 @@ package org.jetbrains.java.decompiler.struct;
import org.jetbrains.java.decompiler.main.extern.IDecompilatSaver;
import org.jetbrains.java.decompiler.struct.lazy.LazyLoader;
import org.jetbrains.java.decompiler.struct.lazy.LazyLoader.Link;
+import org.jetbrains.java.decompiler.util.DataInputFullStream;
import java.io.IOException;
import java.util.ArrayList;
@@ -98,7 +99,15 @@ public class ContextUnit {
List<StructClass> lstClasses = new ArrayList<StructClass>();
for (StructClass cl : classes) {
String oldname = cl.qualifiedName;
- StructClass newcl = new StructClass(loader.getClassStream(oldname), cl.isOwn(), loader);
+
+ StructClass newcl;
+ DataInputFullStream in = loader.getClassStream(oldname);
+ try {
+ newcl = new StructClass(in, cl.isOwn(), loader);
+ }
+ finally {
+ in.close();
+ }
lstClasses.add(newcl);
diff --git a/src/org/jetbrains/java/decompiler/struct/StructClass.java b/src/org/jetbrains/java/decompiler/struct/StructClass.java
index 78e941d..9afe081 100644
--- a/src/org/jetbrains/java/decompiler/struct/StructClass.java
+++ b/src/org/jetbrains/java/decompiler/struct/StructClass.java
@@ -16,7 +16,6 @@
package org.jetbrains.java.decompiler.struct;
import org.jetbrains.java.decompiler.code.CodeConstants;
-import org.jetbrains.java.decompiler.struct.attr.StructGeneralAttribute;
import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
import org.jetbrains.java.decompiler.struct.consts.PrimitiveConstant;
import org.jetbrains.java.decompiler.struct.lazy.LazyLoader;
@@ -24,272 +23,127 @@ import org.jetbrains.java.decompiler.util.DataInputFullStream;
import org.jetbrains.java.decompiler.util.InterpreterUtil;
import org.jetbrains.java.decompiler.util.VBStyleCollection;
-import java.io.*;
+import java.io.IOException;
+import java.io.InputStream;
/*
- ClassFile {
- u4 magic;
- u2 minor_version;
- u2 major_version;
- u2 constant_pool_count;
- cp_info constant_pool[constant_pool_count-1];
- u2 access_flags;
- u2 this_class;
- u2 super_class;
- u2 interfaces_count;
- u2 interfaces[interfaces_count];
- u2 fields_count;
- field_info fields[fields_count];
- u2 methods_count;
- method_info methods[methods_count];
- u2 attributes_count;
- attribute_info attributes[attributes_count];
- }
+ class_file {
+ u4 magic;
+ u2 minor_version;
+ u2 major_version;
+ u2 constant_pool_count;
+ cp_info constant_pool[constant_pool_count-1];
+ u2 access_flags;
+ u2 this_class;
+ u2 super_class;
+ u2 interfaces_count;
+ u2 interfaces[interfaces_count];
+ u2 fields_count;
+ field_info fields[fields_count];
+ u2 methods_count;
+ method_info methods[methods_count];
+ u2 attributes_count;
+ attribute_info attributes[attributes_count];
+ }
*/
+public class StructClass extends StructMember {
-public class StructClass {
-
- // *****************************************************************************
- // public fields
- // *****************************************************************************
-
- public int minor_version;
-
- public int major_version;
-
- public int access_flags;
-
- public int this_class;
+ public final String qualifiedName;
+ public final PrimitiveConstant superClass;
- public int super_class;
-
- public PrimitiveConstant thisClass;
-
- public PrimitiveConstant superClass;
-
- public String qualifiedName;
-
-
- // *****************************************************************************
- // private fields
- // *****************************************************************************
+ private final boolean own;
+ private final LazyLoader loader;
+ private final int minorVersion;
+ private final int majorVersion;
+ private final int[] interfaces;
+ private final String[] interfaceNames;
+ private final VBStyleCollection<StructField, String> fields;
+ private final VBStyleCollection<StructMethod, String> methods;
private ConstantPool pool;
- private int[] interfaces;
-
- private String[] interfaceNames;
-
- private VBStyleCollection<StructField, String> fields = new VBStyleCollection<StructField, String>();
-
- private VBStyleCollection<StructMethod, String> methods = new VBStyleCollection<StructMethod, String>();
-
- private VBStyleCollection<StructGeneralAttribute, String> attributes = new VBStyleCollection<StructGeneralAttribute, String>();
-
- private boolean own = true;
-
- private LazyLoader loader;
-
- // *****************************************************************************
- // constructors
- // *****************************************************************************
-
- public StructClass(String filename, boolean own, LazyLoader loader) throws IOException {
- this(new FileInputStream(filename), own, loader);
- }
-
public StructClass(InputStream inStream, boolean own, LazyLoader loader) throws IOException {
this(new DataInputFullStream(inStream), own, loader);
}
- public StructClass(DataInputFullStream inStream, boolean own, LazyLoader loader) throws IOException {
+ public StructClass(DataInputFullStream in, boolean own, LazyLoader loader) throws IOException {
this.own = own;
this.loader = loader;
- initStruct(inStream);
- }
-
- // *****************************************************************************
- // public methods
- // *****************************************************************************
-
- public boolean hasField(String name, String descriptor) {
- return getField(name, descriptor) != null;
- }
-
- public StructField getField(String name, String descriptor) {
- return fields.getWithKey(InterpreterUtil.makeUniqueKey(name, descriptor));
- }
-
- public StructMethod getMethod(String key) {
- return methods.getWithKey(key);
- }
-
- public StructMethod getMethod(String name, String descriptor) {
- return methods.getWithKey(InterpreterUtil.makeUniqueKey(name, descriptor));
- }
-
- public void writeToFile(File file) throws IOException {
- DataOutputStream out = new DataOutputStream(new FileOutputStream(file));
- writeToOutputStream(out);
- out.close();
- }
-
- public void writeToOutputStream(DataOutputStream out) throws IOException {
-
- out.writeInt(0xCAFEBABE);
- out.writeShort(minor_version);
- out.writeShort(major_version);
-
- getPool().writeToOutputStream(out);
-
- out.writeShort(access_flags);
- out.writeShort(this_class);
- out.writeShort(super_class);
-
- out.writeShort(interfaces.length);
- for (int i = 0; i < interfaces.length; i++) {
- out.writeShort(interfaces[i]);
- }
-
- out.writeShort(fields.size());
- for (int i = 0; i < fields.size(); i++) {
- fields.get(i).writeToStream(out);
- }
-
- out.writeShort(methods.size());
- for (int i = 0; i < methods.size(); i++) {
- methods.get(i).writeToStream(out);
- }
-
- out.writeShort(attributes.size());
- for (StructGeneralAttribute attr : attributes) {
- attr.writeToStream(out);
- }
- }
-
- public String getInterface(int i) {
- return interfaceNames[i];
- }
-
- public void releaseResources() {
- if (loader != null) {
- pool = null;
- }
- }
-
- // *****************************************************************************
- // private methods
- // *****************************************************************************
-
- private void initStruct(DataInputFullStream in) throws IOException {
+ in.discard(4);
- in.skip(4);
-
- this.minor_version = in.readUnsignedShort();
- this.major_version = in.readUnsignedShort();
+ minorVersion = in.readUnsignedShort();
+ majorVersion = in.readUnsignedShort();
pool = new ConstantPool(in);
- this.access_flags = in.readUnsignedShort();
-
- this_class = in.readUnsignedShort();
- thisClass = pool.getPrimitiveConstant(this_class);
- qualifiedName = thisClass.getString();
-
- super_class = in.readUnsignedShort();
- superClass = pool.getPrimitiveConstant(super_class);
+ accessFlags = in.readUnsignedShort();
+ int thisClassIdx = in.readUnsignedShort();
+ int superClassIdx = in.readUnsignedShort();
+ qualifiedName = pool.getPrimitiveConstant(thisClassIdx).getString();
+ superClass = pool.getPrimitiveConstant(superClassIdx);
// interfaces
int length = in.readUnsignedShort();
- int[] arrInterfaces = new int[length];
- String[] arrInterfaceNames = new String[length];
-
+ interfaces = new int[length];
+ interfaceNames = new String[length];
for (int i = 0; i < length; i++) {
- arrInterfaces[i] = in.readUnsignedShort();
- arrInterfaceNames[i] = pool.getPrimitiveConstant(arrInterfaces[i]).getString();
+ interfaces[i] = in.readUnsignedShort();
+ interfaceNames[i] = pool.getPrimitiveConstant(interfaces[i]).getString();
}
- this.interfaces = arrInterfaces;
- this.interfaceNames = arrInterfaceNames;
// fields
- VBStyleCollection<StructField, String> lstFields = new VBStyleCollection<StructField, String>();
length = in.readUnsignedShort();
+ fields = new VBStyleCollection<StructField, String>();
for (int i = 0; i < length; i++) {
- StructField field = new StructField();
- field.access_flags = in.readUnsignedShort();
- field.name_index = in.readUnsignedShort();
- field.descriptor_index = in.readUnsignedShort();
-
- field.initStrings(pool, this_class);
-
- field.setAttributes(readAttributes(in));
-
- lstFields.addWithKey(field, InterpreterUtil.makeUniqueKey(field.getName(), field.getDescriptor()));
+ StructField field = new StructField(in, this);
+ fields.addWithKey(field, InterpreterUtil.makeUniqueKey(field.getName(), field.getDescriptor()));
}
- this.fields = lstFields;
// methods
length = in.readUnsignedShort();
+ methods = new VBStyleCollection<StructMethod, String>();
for (int i = 0; i < length; i++) {
- StructMethod meth = new StructMethod(in, own, this);
-
- //if(qualifiedName.endsWith("JUnitStatusLine") && !meth.getName().equals("onProcessStarted") && !meth.getName().startsWith("access")) {
- //if(!meth.getName().equals("run")) {
- // continue;
- //}
-
- methods.addWithKey(meth, InterpreterUtil.makeUniqueKey(meth.getName(), meth.getDescriptor()));
+ StructMethod method = new StructMethod(in, this);
+ methods.addWithKey(method, InterpreterUtil.makeUniqueKey(method.getName(), method.getDescriptor()));
}
// attributes
- this.attributes = readAttributes(in);
-
+ attributes = readAttributes(in, pool);
- // release memory
- if (loader != null) {
- pool = null;
- }
+ releaseResources();
}
- private VBStyleCollection<StructGeneralAttribute, String> readAttributes(DataInputFullStream in) throws IOException {
+ public boolean hasField(String name, String descriptor) {
+ return getField(name, descriptor) != null;
+ }
- VBStyleCollection<StructGeneralAttribute, String> lstAttribute = new VBStyleCollection<StructGeneralAttribute, String>();
+ public StructField getField(String name, String descriptor) {
+ return fields.getWithKey(InterpreterUtil.makeUniqueKey(name, descriptor));
+ }
- int length = in.readUnsignedShort();
- for (int i = 0; i < length; i++) {
- int attr_nameindex = in.readUnsignedShort();
- String attrname = pool.getPrimitiveConstant(attr_nameindex).getString();
-
- StructGeneralAttribute attr = StructGeneralAttribute.getMatchingAttributeInstance(attr_nameindex, attrname);
-
- if (attr != null) {
- byte[] arr = new byte[in.readInt()];
- in.readFull(arr);
- attr.setInfo(arr);
-
- attr.initContent(pool);
- lstAttribute.addWithKey(attr, attr.getName());
- }
- else {
- in.skip(in.readInt());
- }
- }
+ public StructMethod getMethod(String key) {
+ return methods.getWithKey(key);
+ }
- return lstAttribute;
+ public StructMethod getMethod(String name, String descriptor) {
+ return methods.getWithKey(InterpreterUtil.makeUniqueKey(name, descriptor));
}
+ public String getInterface(int i) {
+ return interfaceNames[i];
+ }
- // *****************************************************************************
- // getter and setter methods
- // *****************************************************************************
+ public void releaseResources() {
+ if (loader != null) {
+ pool = null;
+ }
+ }
public ConstantPool getPool() {
-
if (pool == null && loader != null) {
pool = loader.loadPool(qualifiedName);
}
-
return pool;
}
@@ -309,10 +163,6 @@ public class StructClass {
return fields;
}
- public VBStyleCollection<StructGeneralAttribute, String> getAttributes() {
- return attributes;
- }
-
public boolean isOwn() {
return own;
}
@@ -322,15 +172,15 @@ public class StructClass {
}
public boolean isVersionGE_1_5() {
- return (major_version > 48 || (major_version == 48 && minor_version > 0)); // FIXME: check second condition
+ return (majorVersion > 48 || (majorVersion == 48 && minorVersion > 0)); // FIXME: check second condition
}
public boolean isVersionGE_1_7() {
- return (major_version >= 51);
+ return (majorVersion >= 51);
}
public int getBytecodeVersion() {
- switch (major_version) {
+ switch (majorVersion) {
case 52:
return CodeConstants.BYTECODE_JAVA_8;
case 51:
diff --git a/src/org/jetbrains/java/decompiler/struct/StructContext.java b/src/org/jetbrains/java/decompiler/struct/StructContext.java
index ecca95a..da562e9 100644
--- a/src/org/jetbrains/java/decompiler/struct/StructContext.java
+++ b/src/org/jetbrains/java/decompiler/struct/StructContext.java
@@ -19,6 +19,7 @@ import org.jetbrains.java.decompiler.main.DecompilerContext;
import org.jetbrains.java.decompiler.main.extern.IDecompilatSaver;
import org.jetbrains.java.decompiler.main.extern.IFernflowerLogger;
import org.jetbrains.java.decompiler.struct.lazy.LazyLoader;
+import org.jetbrains.java.decompiler.util.DataInputFullStream;
import java.io.File;
import java.io.IOException;
@@ -136,7 +137,15 @@ public class StructContext {
if (filename.endsWith(".class")) {
try {
- StructClass cl = new StructClass(loader.getClassStream(file.getAbsolutePath(), null), isOwn, loader);
+ StructClass cl;
+
+ DataInputFullStream in = loader.getClassStream(file.getAbsolutePath(), null);
+ try {
+ cl = new StructClass(in, isOwn, loader);
+ }
+ finally {
+ in.close();
+ }
classes.put(cl.qualifiedName, cl);
unit.addClass(cl, filename);
@@ -145,8 +154,8 @@ public class StructContext {
isClass = true;
}
catch (IOException ex) {
- DecompilerContext.getLogger()
- .writeMessage("Invalid class file: " + (path.length() > 0 ? path + "/" : "") + filename, IFernflowerLogger.ERROR);
+ DecompilerContext.getLogger().writeMessage("Invalid class file: " + (path.length() > 0 ? path + "/" : "") + filename,
+ IFernflowerLogger.ERROR);
}
}
diff --git a/src/org/jetbrains/java/decompiler/struct/StructField.java b/src/org/jetbrains/java/decompiler/struct/StructField.java
index 4c0f25d..796d77f 100644
--- a/src/org/jetbrains/java/decompiler/struct/StructField.java
+++ b/src/org/jetbrains/java/decompiler/struct/StructField.java
@@ -15,96 +15,44 @@
*/
package org.jetbrains.java.decompiler.struct;
-import org.jetbrains.java.decompiler.struct.attr.StructGeneralAttribute;
import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
-import org.jetbrains.java.decompiler.util.VBStyleCollection;
+import org.jetbrains.java.decompiler.util.DataInputFullStream;
-import java.io.DataOutputStream;
import java.io.IOException;
/*
- field_info {
- u2 access_flags;
- u2 name_index;
- u2 descriptor_index;
- u2 attributes_count;
- attribute_info attributes[attributes_count];
- }
+ field_info {
+ u2 access_flags;
+ u2 name_index;
+ u2 descriptor_index;
+ u2 attributes_count;
+ attribute_info attributes[attributes_count];
+ }
*/
+public class StructField extends StructMember {
-public class StructField {
+ private final String name;
+ private final String descriptor;
- // *****************************************************************************
- // public fields
- // *****************************************************************************
- public int access_flags;
- public int name_index;
- public int descriptor_index;
+ public StructField(DataInputFullStream in, StructClass clStruct) throws IOException {
+ accessFlags = in.readUnsignedShort();
+ int nameIndex = in.readUnsignedShort();
+ int descriptorIndex = in.readUnsignedShort();
- private String name;
- private String descriptor;
-
- // *****************************************************************************
- // private fields
- // *****************************************************************************
-
- private VBStyleCollection<StructGeneralAttribute, String> attributes;
-
- // *****************************************************************************
- // constructors
- // *****************************************************************************
-
- public StructField() {
- }
-
- // *****************************************************************************
- // public methods
- // *****************************************************************************
-
- public void writeToStream(DataOutputStream out) throws IOException {
-
- out.writeShort(access_flags);
- out.writeShort(name_index);
- out.writeShort(descriptor_index);
-
- out.writeShort(attributes.size());
- for (StructGeneralAttribute attr : attributes) {
- attr.writeToStream(out);
- }
- }
-
- public void initStrings(ConstantPool pool, int class_index) {
- String[] values = pool.getClassElement(ConstantPool.FIELD, class_index, name_index, descriptor_index);
+ ConstantPool pool = clStruct.getPool();
+ String[] values = pool.getClassElement(ConstantPool.FIELD, clStruct.qualifiedName, nameIndex, descriptorIndex);
name = values[0];
descriptor = values[1];
- }
- // *****************************************************************************
- // getter and setter methods
- // *****************************************************************************
-
- public VBStyleCollection<StructGeneralAttribute, String> getAttributes() {
- return attributes;
- }
-
- public void setAttributes(VBStyleCollection<StructGeneralAttribute, String> attributes) {
- this.attributes = attributes;
- }
-
- public String getDescriptor() {
- return descriptor;
- }
-
- public void setDescriptor(String descriptor) {
- this.descriptor = descriptor;
+ attributes = readAttributes(in, pool);
}
public String getName() {
return name;
}
- public void setName(String name) {
- this.name = name;
+ public String getDescriptor() {
+ return descriptor;
}
}
diff --git a/src/org/jetbrains/java/decompiler/struct/StructMember.java b/src/org/jetbrains/java/decompiler/struct/StructMember.java
new file mode 100644
index 0000000..f681e19
--- /dev/null
+++ b/src/org/jetbrains/java/decompiler/struct/StructMember.java
@@ -0,0 +1,87 @@
+/*
+ * Copyright 2000-2014 JetBrains s.r.o.
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package org.jetbrains.java.decompiler.struct;
+
+import org.jetbrains.java.decompiler.code.CodeConstants;
+import org.jetbrains.java.decompiler.struct.attr.StructGeneralAttribute;
+import org.jetbrains.java.decompiler.struct.attr.StructLocalVariableTableAttribute;
+import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
+import org.jetbrains.java.decompiler.util.DataInputFullStream;
+import org.jetbrains.java.decompiler.util.VBStyleCollection;
+
+import java.io.IOException;
+
+public class StructMember {
+
+ protected int accessFlags;
+ protected VBStyleCollection<StructGeneralAttribute, String> attributes;
+
+
+ public int getAccessFlags() {
+ return accessFlags;
+ }
+
+ public VBStyleCollection<StructGeneralAttribute, String> getAttributes() {
+ return attributes;
+ }
+
+ public boolean hasModifier(int modifier) {
+ return (accessFlags & modifier) == modifier;
+ }
+
+ public boolean isSynthetic() {
+ return hasModifier(CodeConstants.ACC_SYNTHETIC) || attributes.containsKey(StructGeneralAttribute.ATTRIBUTE_SYNTHETIC);
+ }
+
+ protected VBStyleCollection<StructGeneralAttribute, String> readAttributes(DataInputFullStream in, ConstantPool pool) throws IOException {
+ VBStyleCollection<StructGeneralAttribute, String> attributes = new VBStyleCollection<StructGeneralAttribute, String>();
+
+ int length = in.readUnsignedShort();
+ for (int i = 0; i < length; i++) {
+ int nameIndex = in.readUnsignedShort();
+ String name = pool.getPrimitiveConstant(nameIndex).getString();
+
+ StructGeneralAttribute attribute = readAttribute(in, pool, name);
+
+ if (attribute != null) {
+ if (StructGeneralAttribute.ATTRIBUTE_LOCAL_VARIABLE_TABLE.equals(name) && attributes.containsKey(name)) {
+ // merge all variable tables
+ StructLocalVariableTableAttribute table = (StructLocalVariableTableAttribute)attributes.getWithKey(name);
+ table.addLocalVariableTable((StructLocalVariableTableAttribute)attribute);
+ }
+ else {
+ attributes.addWithKey(attribute, attribute.getName());
+ }
+ }
+ }
+
+ return attributes;
+ }
+
+ protected StructGeneralAttribute readAttribute(DataInputFullStream in, ConstantPool pool, String name) throws IOException {
+ StructGeneralAttribute attribute = StructGeneralAttribute.createAttribute(name);
+ if (attribute == null) {
+ in.discard(in.readInt());
+ }
+ else {
+ byte[] data = new byte[in.readInt()];
+ in.readFull(data);
+ attribute.setInfo(data);
+ attribute.initContent(pool);
+ }
+ return attribute;
+ }
+}
diff --git a/src/org/jetbrains/java/decompiler/struct/StructMethod.java b/src/org/jetbrains/java/decompiler/struct/StructMethod.java
index e3de510..b055df6 100644
--- a/src/org/jetbrains/java/decompiler/struct/StructMethod.java
+++ b/src/org/jetbrains/java/decompiler/struct/StructMethod.java
@@ -17,267 +17,106 @@ package org.jetbrains.java.decompiler.struct;
import org.jetbrains.java.decompiler.code.*;
import org.jetbrains.java.decompiler.struct.attr.StructGeneralAttribute;
-import org.jetbrains.java.decompiler.struct.attr.StructLocalVariableTableAttribute;
import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
+import org.jetbrains.java.decompiler.struct.lazy.LazyLoader;
import org.jetbrains.java.decompiler.util.DataInputFullStream;
import org.jetbrains.java.decompiler.util.VBStyleCollection;
import java.io.ByteArrayInputStream;
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
+import static org.jetbrains.java.decompiler.code.CodeConstants.*;
+
/*
- method_info {
- u2 access_flags;
- u2 name_index;
- u2 descriptor_index;
- u2 attributes_count;
- attribute_info attributes[attributes_count];
- }
+ method_info {
+ u2 access_flags;
+ u2 name_index;
+ u2 descriptor_index;
+ u2 attributes_count;
+ attribute_info attributes[attributes_count];
+ }
*/
+public class StructMethod extends StructMember {
-public class StructMethod implements CodeConstants {
-
- // *****************************************************************************
- // public fields
- // *****************************************************************************
-
- public int name_index;
-
- public int descriptor_index;
-
- // *****************************************************************************
- // private fields
- // *****************************************************************************
-
- private static final int[] opr_iconst = new int[]{-1, 0, 1, 2, 3, 4, 5};
-
- private static final int[] opr_loadstore = new int[]{0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3};
-
- private static final int[] opcs_load = new int[]{opc_iload, opc_lload, opc_fload, opc_dload, opc_aload};
-
- private static final int[] opcs_store = new int[]{opc_istore, opc_lstore, opc_fstore, opc_dstore, opc_astore};
-
-
- private int accessFlags;
+ private static final int[] opr_iconst = {-1, 0, 1, 2, 3, 4, 5};
+ private static final int[] opr_loadstore = {0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3, 0, 1, 2, 3};
+ private static final int[] opcs_load = {opc_iload, opc_lload, opc_fload, opc_dload, opc_aload};
+ private static final int[] opcs_store = {opc_istore, opc_lstore, opc_fstore, opc_dstore, opc_astore};
- private VBStyleCollection<StructGeneralAttribute, String> attributes;
-
- private int localVariables;
-
- private int maxStack;
-
- private String name;
-
- private String descriptor;
-
- private InstructionSequence seq;
+ private final StructClass classStruct;
+ private final String name;
+ private final String descriptor;
private boolean containsCode = false;
+ private int localVariables = 0;
+ private int codeLength = 0;
+ private int codeFullLength = 0;
+ private InstructionSequence seq;
+ private boolean expanded = false;
- private StructClass classStruct;
-
-
- // lazy properties
- private boolean lazy;
-
- private boolean expanded;
-
- private byte[] code_content;
-
- private int code_length = 0;
-
- private int code_fulllength = 0;
-
- // *****************************************************************************
- // constructors
- // *****************************************************************************
-
- public StructMethod(DataInputFullStream in, boolean own, StructClass clstruct) throws IOException {
- this(in, true, own, clstruct);
- }
-
- public StructMethod(DataInputFullStream in, boolean lazy, boolean own, StructClass clstruct) throws IOException {
- this.lazy = lazy;
- this.expanded = !lazy;
- this.classStruct = clstruct;
+ public StructMethod(DataInputFullStream in, StructClass clStruct) throws IOException {
+ classStruct = clStruct;
accessFlags = in.readUnsignedShort();
- name_index = in.readUnsignedShort();
- descriptor_index = in.readUnsignedShort();
-
- ConstantPool pool = clstruct.getPool();
-
- initStrings(pool, clstruct.this_class);
-
- VBStyleCollection<StructGeneralAttribute, String> lstAttribute = new VBStyleCollection<StructGeneralAttribute, String>();
- int len = in.readUnsignedShort();
- for (int i = 0; i < len; i++) {
-
- int attr_nameindex = in.readUnsignedShort();
- String attrname = pool.getPrimitiveConstant(attr_nameindex).getString();
-
- if (StructGeneralAttribute.ATTRIBUTE_CODE.equals(attrname)) {
- if (!own) {
- // skip code in foreign classes
- in.skip(8);
- in.skip(in.readInt());
- in.skip(8 * in.readUnsignedShort());
- }
- else {
- containsCode = true;
-
- in.skip(4);
-
- maxStack = in.readUnsignedShort();
- localVariables = in.readUnsignedShort();
-
- if (lazy) {
- code_length = in.readInt();
+ int nameIndex = in.readUnsignedShort();
+ int descriptorIndex = in.readUnsignedShort();
- in.skip(code_length);
-
- int exc_length = in.readUnsignedShort();
- code_fulllength = code_length + exc_length * 8 + 2;
-
- in.skip(exc_length * 8);
- }
- else {
- seq = parseBytecode(in, in.readInt(), pool);
- }
- }
-
- // code attributes
- int length = in.readUnsignedShort();
- for (int j = 0; j < length; j++) {
- int codeattr_nameindex = in.readUnsignedShort();
- String codeattrname = pool.getPrimitiveConstant(codeattr_nameindex).getString();
-
- readAttribute(in, pool, lstAttribute, codeattr_nameindex, codeattrname);
- }
- }
- else {
- readAttribute(in, pool, lstAttribute, attr_nameindex, attrname);
- }
- }
+ ConstantPool pool = clStruct.getPool();
+ String[] values = pool.getClassElement(ConstantPool.METHOD, clStruct.qualifiedName, nameIndex, descriptorIndex);
+ name = values[0];
+ descriptor = values[1];
- attributes = lstAttribute;
+ attributes = readAttributes(in, pool);
}
-
- // *****************************************************************************
- // public methods
- // *****************************************************************************
-
- public void writeToStream(DataOutputStream out) throws IOException {
-
- out.writeShort(accessFlags);
- out.writeShort(name_index);
- out.writeShort(descriptor_index);
-
- out.writeShort(attributes.size());
-
- for (StructGeneralAttribute attr : attributes) {
- if (StructGeneralAttribute.ATTRIBUTE_CODE.equals(attr.getName())) {
- out.writeShort(attr.getAttribute_name_index());
-
- if (lazy && !expanded) {
- out.writeInt(10 + code_content.length);
- out.writeShort(maxStack);
- out.writeShort(localVariables);
- out.writeInt(code_length);
- out.write(code_content);
- }
- else {
- ByteArrayOutputStream codeout = new ByteArrayOutputStream();
- seq.writeCodeToStream(new DataOutputStream(codeout));
-
- ByteArrayOutputStream excout = new ByteArrayOutputStream();
- seq.writeExceptionsToStream(new DataOutputStream(excout));
-
- out.writeInt(10 + codeout.size() + excout.size());
-
- out.writeShort(maxStack);
- out.writeShort(localVariables);
- out.writeInt(codeout.size());
- codeout.writeTo(out);
- excout.writeTo(out);
- }
- // no attributes
- out.writeShort(0);
+ @Override
+ protected StructGeneralAttribute readAttribute(DataInputFullStream in, ConstantPool pool, String name) throws IOException {
+ if (StructGeneralAttribute.ATTRIBUTE_CODE.equals(name)) {
+ if (!classStruct.isOwn()) {
+ // skip code in foreign classes
+ in.discard(8);
+ in.discard(in.readInt());
+ in.discard(8 * in.readUnsignedShort());
}
else {
- attr.writeToStream(out);
+ containsCode = true;
+ in.discard(6);
+ localVariables = in.readUnsignedShort();
+ codeLength = in.readInt();
+ in.discard(codeLength);
+ int exc_length = in.readUnsignedShort();
+ in.discard(exc_length * 8);
+ codeFullLength = codeLength + exc_length * 8 + 2;
}
- }
- }
-
- private static void readAttribute(DataInputFullStream in,
- ConstantPool pool,
- VBStyleCollection<StructGeneralAttribute, String> lstAttribute,
- int attr_nameindex,
- String attrname) throws IOException {
- StructGeneralAttribute attribute = StructGeneralAttribute.getMatchingAttributeInstance(attr_nameindex, attrname);
+ LazyLoader.skipAttributes(in);
- if (attribute != null) {
- attrname = attribute.getName();
-
- byte[] arr = new byte[in.readInt()];
- in.readFull(arr);
- attribute.setInfo(arr);
-
- attribute.initContent(pool);
-
- if (StructGeneralAttribute.ATTRIBUTE_LOCAL_VARIABLE_TABLE.equals(attrname) &&
- lstAttribute.containsKey(attrname)) {
- // merge all variable tables
- StructLocalVariableTableAttribute oldattr = (StructLocalVariableTableAttribute)lstAttribute.getWithKey(attrname);
- oldattr.addLocalVariableTable((StructLocalVariableTableAttribute)attribute);
- }
- else {
- lstAttribute.addWithKey(attribute, attribute.getName());
- }
- }
- else {
- in.skip(in.readInt());
+ return null;
}
- }
- private void initStrings(ConstantPool pool, int class_index) {
- String[] values = pool.getClassElement(ConstantPool.METHOD, class_index, name_index, descriptor_index);
- name = values[0];
- descriptor = values[1];
+ return super.readAttribute(in, pool, name);
}
public void expandData() throws IOException {
- if (containsCode && lazy && !expanded) {
-
- byte[] codearr = classStruct.getLoader().loadBytecode(this, code_fulllength);
-
- seq = parseBytecode(new DataInputFullStream(new ByteArrayInputStream(codearr)), code_length, classStruct.getPool());
+ if (containsCode && !expanded) {
+ byte[] code = classStruct.getLoader().loadBytecode(this, codeFullLength);
+ seq = parseBytecode(new DataInputFullStream(new ByteArrayInputStream(code)), codeLength, classStruct.getPool());
expanded = true;
}
}
public void releaseResources() throws IOException {
- if (containsCode && lazy && expanded) {
+ if (containsCode && expanded) {
seq = null;
expanded = false;
}
}
- // *****************************************************************************
- // private methods
- // *****************************************************************************
-
private InstructionSequence parseBytecode(DataInputFullStream in, int length, ConstantPool pool) throws IOException {
-
- VBStyleCollection<Instruction, Integer> collinstr = new VBStyleCollection<Instruction, Integer>();
+ VBStyleCollection<Instruction, Integer> instructions = new VBStyleCollection<Instruction, Integer>();
int bytecode_version = classStruct.getBytecodeVersion();
@@ -370,7 +209,7 @@ public class StructMethod implements CodeConstants {
case opc_invokedynamic:
if (classStruct.isVersionGE_1_7()) { // instruction unused in Java 6 and before
operands.add(new Integer(in.readUnsignedShort()));
- in.skip(2);
+ in.discard(2);
group = GROUP_INVOCATION;
i += 4;
}
@@ -420,7 +259,7 @@ public class StructMethod implements CodeConstants {
case opc_invokeinterface:
operands.add(new Integer(in.readUnsignedShort()));
operands.add(new Integer(in.readUnsignedByte()));
- in.skip(1);
+ in.discard(1);
group = GROUP_INVOCATION;
i += 4;
break;
@@ -430,7 +269,7 @@ public class StructMethod implements CodeConstants {
i += 3;
break;
case opc_tableswitch:
- in.skip((4 - (i + 1) % 4) % 4);
+ in.discard((4 - (i + 1) % 4) % 4);
i += ((4 - (i + 1) % 4) % 4); // padding
operands.add(new Integer(in.readInt()));
i += 4;
@@ -449,7 +288,7 @@ public class StructMethod implements CodeConstants {
break;
case opc_lookupswitch:
- in.skip((4 - (i + 1) % 4) % 4);
+ in.discard((4 - (i + 1) % 4) % 4);
i += ((4 - (i + 1) % 4) % 4); // padding
operands.add(new Integer(in.readInt()));
i += 4;
@@ -483,7 +322,7 @@ public class StructMethod implements CodeConstants {
Instruction instr = ConstantsUtil.getInstructionInstance(opcode, wide, group, bytecode_version, ops);
- collinstr.addWithKey(instr, new Integer(offset));
+ instructions.addWithKey(instr, new Integer(offset));
i++;
}
@@ -507,7 +346,7 @@ public class StructMethod implements CodeConstants {
lstHandlers.add(handler);
}
- InstructionSequence seq = new FullInstructionSequence(collinstr, new ExceptionTable(lstHandlers));
+ InstructionSequence seq = new FullInstructionSequence(instructions, new ExceptionTable(lstHandlers));
// initialize instructions
int i = seq.length() - 1;
@@ -524,41 +363,27 @@ public class StructMethod implements CodeConstants {
return seq;
}
- // *****************************************************************************
- // getter and setter methods
- // *****************************************************************************
+ public StructClass getClassStruct() {
+ return classStruct;
+ }
- public InstructionSequence getInstructionSequence() {
- return seq;
+ public String getName() {
+ return name;
}
public String getDescriptor() {
return descriptor;
}
- public String getName() {
- return name;
- }
-
- public int getAccessFlags() {
- return accessFlags;
+ public boolean containsCode() {
+ return containsCode;
}
public int getLocalVariables() {
return localVariables;
}
- public VBStyleCollection<StructGeneralAttribute, String> getAttributes() {
- return attributes;
- }
-
- public StructClass getClassStruct() {
- return classStruct;
- }
-
- public boolean containsCode() {
- return containsCode;
+ public InstructionSequence getInstructionSequence() {
+ return seq;
}
}
-
-
diff --git a/src/org/jetbrains/java/decompiler/struct/attr/StructExceptionsAttribute.java b/src/org/jetbrains/java/decompiler/struct/attr/StructExceptionsAttribute.java
index c52fcc7..53c02ec 100644
--- a/src/org/jetbrains/java/decompiler/struct/attr/StructExceptionsAttribute.java
+++ b/src/org/jetbrains/java/decompiler/struct/attr/StructExceptionsAttribute.java
@@ -17,9 +17,6 @@ package org.jetbrains.java.decompiler.struct.attr;
import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
-import java.io.ByteArrayOutputStream;
-import java.io.DataOutputStream;
-import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@@ -38,30 +35,6 @@ public class StructExceptionsAttribute extends StructGeneralAttribute {
}
}
- public void writeToStream(DataOutputStream out) throws IOException {
-
- out.writeShort(attribute_name_index);
-
- ByteArrayOutputStream codeout = new ByteArrayOutputStream();
- DataOutputStream dataout = new DataOutputStream(codeout);
-
- int len = throwsExceptions.size();
- dataout.writeShort(len);
-
- if (len > 0) {
- info = new byte[len * 2];
- for (int i = 0, j = 0; i < len; i++, j += 2) {
- int index = throwsExceptions.get(i).intValue();
- info[j] = (byte)(index >> 8);
- info[j + 1] = (byte)(index & 0xFF);
- }
- dataout.write(info);
- }
-
- out.writeInt(codeout.size());
- out.write(codeout.toByteArray());
- }
-
public String getExcClassname(int index, ConstantPool pool) {
return pool.getPrimitiveConstant(throwsExceptions.get(index).intValue()).getString();
}
diff --git a/src/org/jetbrains/java/decompiler/struct/attr/StructGeneralAttribute.java b/src/org/jetbrains/java/decompiler/struct/attr/StructGeneralAttribute.java
index bd0596a..632575f 100644
--- a/src/org/jetbrains/java/decompiler/struct/attr/StructGeneralAttribute.java
+++ b/src/org/jetbrains/java/decompiler/struct/attr/StructGeneralAttribute.java
@@ -17,17 +17,13 @@ package org.jetbrains.java.decompiler.struct.attr;
import org.jetbrains.java.decompiler.struct.consts.ConstantPool;
-import java.io.DataOutputStream;
-import java.io.IOException;
-
/*
- attribute_info {
- u2 attribute_name_index;
- u4 attribute_length;
- u1 info[attribute_length];
- }
+ attribute_info {
+ u2 attribute_name_index;
+ u4 attribute_length;
+ u1 info[attribute_length];
+ }
*/
-
public class StructGeneralAttribute {
public static final String ATTRIBUTE_CODE = "Code";
@@ -48,74 +44,51 @@ public class StructGeneralAttribute {
public static final String ATTRIBUTE_SYNTHETIC = "Synthetic";
public static final String ATTRIBUTE_DEPRECATED = "Deprecated";
-
- // *****************************************************************************
- // private fields
- // *****************************************************************************
-
- protected int attribute_name_index;
-
- protected byte[] info;
-
protected String name;
+ protected byte[] info;
- // *****************************************************************************
- // public methods
- // *****************************************************************************
-
- public void writeToStream(DataOutputStream out) throws IOException {
- out.writeShort(attribute_name_index);
- out.writeInt(info.length);
- if (info.length > 0) {
- out.write(info);
- }
- }
-
- public void initContent(ConstantPool pool) {
- name = pool.getPrimitiveConstant(attribute_name_index).getString();
- }
-
- public static StructGeneralAttribute getMatchingAttributeInstance(int nameindex, String attrname) {
+ public static StructGeneralAttribute createAttribute(String name) {
StructGeneralAttribute attr;
- if (ATTRIBUTE_INNER_CLASSES.equals(attrname)) {
+ if (ATTRIBUTE_INNER_CLASSES.equals(name)) {
attr = new StructInnerClassesAttribute();
}
- else if (ATTRIBUTE_CONSTANT_VALUE.equals(attrname)) {
+ else if (ATTRIBUTE_CONSTANT_VALUE.equals(name)) {
attr = new StructConstantValueAttribute();
}
- else if (ATTRIBUTE_SIGNATURE.equals(attrname)) {
+ else if (ATTRIBUTE_SIGNATURE.equals(name)) {
attr = new StructGenericSignatureAttribute();
}
- else if (ATTRIBUTE_ANNOTATION_DEFAULT.equals(attrname)) {
+ else if (ATTRIBUTE_ANNOTATION_DEFAULT.equals(name)) {
attr = new StructAnnDefaultAttribute();
}
- else if (ATTRIBUTE_EXCEPTIONS.equals(attrname)) {
+ else if (ATTRIBUTE_EXCEPTIONS.equals(name)) {
attr = new StructExceptionsAttribute();
}
- else if (ATTRIBUTE_ENCLOSING_METHOD.equals(attrname)) {
+ else if (ATTRIBUTE_ENCLOSING_METHOD.equals(name)) {
attr = new StructEnclosingMethodAttribute();
}
- else if (ATTRIBUTE_RUNTIME_VISIBLE_ANNOTATIONS.equals(attrname) ||
- ATTRIBUTE_RUNTIME_INVISIBLE_ANNOTATIONS.equals(attrname)) {
+ else if (ATTRIBUTE_RUNTIME_VISIBLE_ANNOTATIONS.equals(name) ||
+ ATTRIBUTE_RUNTIME_INVISIBLE_ANNOTATIONS.equals(name)) {
attr = new StructAnnotationAttribute();
}
- else if (ATTRIBUTE_RUNTIME_VISIBLE_PARAMETER_ANNOTATIONS.equals(attrname) ||
- ATTRIBUTE_RUNTIME_INVISIBLE_PARAMETER_ANNOTATIONS.equals(attrname)) {
+ else if (ATTRIBUTE_RUNTIME_VISIBLE_PARAMETER_ANNOTATIONS.equals(name) ||
+ ATTRIBUTE_RUNTIME_INVISIBLE_PARAMETER_ANNOTATIONS.equals(name)) {
attr = new StructAnnotationParameterAttribute();
}
- else if (ATTRIBUTE_RUNTIME_VISIBLE_TYPE_ANNOTATIONS.equals(attrname) ||
- ATTRIBUTE_RUNTIME_INVISIBLE_TYPE_ANNOTATIONS.equals(attrname)) {
+ else if (ATTRIBUTE_RUNTIME_VISIBLE_TYPE_ANNOTATIONS.equals(name) ||
+ ATTRIBUTE_RUNTIME_INVISIBLE_TYPE_ANNOTATIONS.equals(name)) {
attr = new StructAnnotationTypeAttribute();
}
- else if (ATTRIBUTE_LOCAL_VARIABLE_TABLE.equals(attrname)) {
+ else if (ATTRIBUTE_LOCAL_VARIABLE_TABLE.equals(name)) {
attr = new StructLocalVariableTableAttribute();
}
- else if (ATTRIBUTE_BOOTSTRAP_METHODS.equals(attrname)) {
+ else if (ATTRIBUTE_BOOTSTRAP_METHODS.equals(name)) {
attr = new StructBootstrapMethodsAttribute();
}
- else if (ATTRIBUTE_SYNTHETIC.equals(attrname) || ATTRIBUTE_DEPRECATED.equals(attrname)) {
+ else if (ATTRIBUTE_SYNTHETIC.equals(name) ||
+ ATTRIBUTE_DEPRECATED.equals(name)) {
attr = new StructGeneralAttribute();
}
else {
@@ -123,17 +96,11 @@ public class StructGeneralAttribute {
return null;
}
- attr.setAttribute_name_index(nameindex);
+ attr.name = name;
return attr;
}
- // *****************************************************************************
- // getter and setter methods
- // *****************************************************************************
-
- public byte[] getInfo() {
- return info;
- }
+ public void initContent(ConstantPool pool) { }
public void setInfo(byte[] info) {
this.info = info;
@@ -142,16 +109,4 @@ public class StructGeneralAttribute {
public String getName() {
return name;
}
-
- public void setName(String name) {
- this.name = name;
- }
-
- public int getAttribute_name_index() {
- return attribute_name_index;
- }
-
- public void setAttribute_name_index(int attribute_name_index) {
- this.attribute_name_index = attribute_name_index;
- }
}
diff --git a/src/org/jetbrains/java/decompiler/struct/consts/ConstantPool.java b/src/org/jetbrains/java/decompiler/struct/consts/ConstantPool.java
index 1b21828..d534e6d 100644
--- a/src/org/jetbrains/java/decompiler/struct/consts/ConstantPool.java
+++ b/src/org/jetbrains/java/decompiler/struct/consts/ConstantPool.java
@@ -21,9 +21,9 @@ import org.jetbrains.java.decompiler.modules.renamer.PoolInterceptor;
import org.jetbrains.java.decompiler.struct.gen.FieldDescriptor;
import org.jetbrains.java.decompiler.struct.gen.MethodDescriptor;
import org.jetbrains.java.decompiler.struct.gen.VarType;
+import org.jetbrains.java.decompiler.util.DataInputFullStream;
import java.io.DataInputStream;
-import java.io.DataOutputStream;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
@@ -31,25 +31,14 @@ import java.util.List;
public class ConstantPool {
public static final int FIELD = 1;
-
public static final int METHOD = 2;
- // *****************************************************************************
- // private fields
- // *****************************************************************************
-
private List<PooledConstant> pool = new ArrayList<PooledConstant>();
-
private PoolInterceptor interceptor;
- // *****************************************************************************
- // constructors
- // *****************************************************************************
public ConstantPool(DataInputStream in) throws IOException {
-
int size = in.readUnsignedShort();
-
int[] pass = new int[size];
// first dummy constant
@@ -57,7 +46,6 @@ public class ConstantPool {
// first pass: read the elements
for (int i = 1; i < size; i++) {
-
byte tag = (byte)in.readUnsignedByte();
switch (tag) {
@@ -106,11 +94,10 @@ public class ConstantPool {
}
}
-
// resolving complex pool elements
- for (int pass_index = 1; pass_index <= 3; pass_index++) {
+ for (int passIndex = 1; passIndex <= 3; passIndex++) {
for (int i = 1; i < size; i++) {
- if (pass[i] == pass_index) {
+ if (pass[i] == passIndex) {
pool.get(i).resolveConstant(this);
}
}
@@ -120,23 +107,7 @@ public class ConstantPool {
interceptor = DecompilerContext.getPoolInterceptor();
}
- // *****************************************************************************
- // public methods
- // *****************************************************************************
-
- public void writeToOutputStream(DataOutputStream out) throws IOException {
-
- out.writeShort(pool.size());
- for (int i = 1; i < pool.size(); i++) {
- PooledConstant cnst = pool.get(i);
- if (cnst != null) {
- cnst.writeToStream(out);
- }
- }
- }
-
- public static void skipPool(DataInputStream in) throws IOException {
-
+ public static void skipPool(DataInputFullStream in) throws IOException {
int size = in.readUnsignedShort();
for (int i = 1; i < size; i++) {
@@ -151,20 +122,20 @@ public class ConstantPool {
case CodeConstants.CONSTANT_InterfaceMethodref:
case CodeConstants.CONSTANT_NameAndType:
case CodeConstants.CONSTANT_InvokeDynamic:
- in.skip(4);
+ in.discard(4);
break;
case CodeConstants.CONSTANT_Long:
case CodeConstants.CONSTANT_Double:
- in.skip(8);
+ in.discard(8);
i++;
break;
case CodeConstants.CONSTANT_Class:
case CodeConstants.CONSTANT_String:
case CodeConstants.CONSTANT_MethodType:
- in.skip(2);
+ in.discard(2);
break;
case CodeConstants.CONSTANT_MethodHandle:
- in.skip(3);
+ in.discard(3);
}
}
}
@@ -173,27 +144,24 @@ public class ConstantPool {
return pool.size();
}
- public String[] getClassElement(int element_type, int class_index, int name_index, int descriptor_index) {
-
- String classname = ((PrimitiveConstant)getConstant(class_index)).getString();
- String elementname = ((PrimitiveConstant)getConstant(name_index)).getString();
- String descriptor = ((PrimitiveConstant)getConstant(descriptor_index)).getString();
+ public String[] getClassElement(int elementType, String className, int nameIndex, int descriptorIndex) {
+ String elementName = ((PrimitiveConstant)getConstant(nameIndex)).getString();
+ String descriptor = ((PrimitiveConstant)getConstant(descriptorIndex)).getString();
if (interceptor != null) {
- String new_element = interceptor.getName(classname + " " + elementname + " " + descriptor);
-
- if (new_element != null) {
- elementname = new_element.split(" ")[1];
+ String newElement = interceptor.getName(className + " " + elementName + " " + descriptor);
+ if (newElement != null) {
+ elementName = newElement.split(" ")[1];
}
- String new_descriptor = buildNewDescriptor(element_type == FIELD ? CodeConstants.CONSTANT_Fieldref : CodeConstants.CONSTANT_Methodref,
- descriptor);
- if (new_descriptor != null) {
- descriptor = new_descriptor;
+ int type = elementType == FIELD ? CodeConstants.CONSTANT_Fieldref : CodeConstants.CONSTANT_Methodref;
+ String newDescriptor = buildNewDescriptor(type, descriptor);
+ if (newDescriptor != null) {
+ descriptor = newDescriptor;
}
}
- return new String[]{elementname, descriptor};
+ return new String[]{elementName, descriptor};
}
public PooledConstant getConstant(int index) {
@@ -205,9 +173,9 @@ public class ConstantPool {
if (cn != null && interceptor != null) {
if (cn.type == CodeConstants.CONSTANT_Class) {
- String newname = buildNewClassname(cn.getString());
- if (newname != null) {
- cn = new PrimitiveConstant(CodeConstants.CONSTANT_Class, newname);
+ String newName = buildNewClassname(cn.getString());
+ if (newName != null) {
+ cn = new PrimitiveConstant(CodeConstants.CONSTANT_Class, newName);
}
}
}
@@ -218,33 +186,30 @@ public class ConstantPool {
public LinkConstant getLinkConstant(int index) {
LinkConstant ln = (LinkConstant)getConstant(index);
- if (ln != null && interceptor != null) {
- if (ln.type == CodeConstants.CONSTANT_Fieldref ||
- ln.type == CodeConstants.CONSTANT_Methodref ||
- ln.type == CodeConstants.CONSTANT_InterfaceMethodref) {
-
- String new_classname = buildNewClassname(ln.classname);
- String new_element = interceptor.getName(ln.classname + " " + ln.elementname + " " + ln.descriptor);
- String new_descriptor = buildNewDescriptor(ln.type, ln.descriptor);
-
- if (new_classname != null || new_element != null || new_descriptor != null) {
-
- ln = new LinkConstant(ln.type, new_classname == null ? ln.classname : new_classname,
- new_element == null ? ln.elementname : new_element.split(" ")[1],
- new_descriptor == null ? ln.descriptor : new_descriptor);
- }
+ if (ln != null && interceptor != null &&
+ (ln.type == CodeConstants.CONSTANT_Fieldref ||
+ ln.type == CodeConstants.CONSTANT_Methodref ||
+ ln.type == CodeConstants.CONSTANT_InterfaceMethodref)) {
+ String newClassName = buildNewClassname(ln.classname);
+ String newElement = interceptor.getName(ln.classname + " " + ln.elementname + " " + ln.descriptor);
+ String newDescriptor = buildNewDescriptor(ln.type, ln.descriptor);
+
+ if (newClassName != null || newElement != null || newDescriptor != null) {
+ String className = newClassName == null ? ln.classname : newClassName;
+ String elementName = newElement == null ? ln.elementname : newElement.split(" ")[1];
+ String descriptor = newDescriptor == null ? ln.descriptor : newDescriptor;
+ ln = new LinkConstant(ln.type, className, elementName, descriptor);
}
}
return ln;
}
- private String buildNewClassname(String classname) {
-
- VarType vt = new VarType(classname, true);
+ private String buildNewClassname(String className) {
+ VarType vt = new VarType(className, true);
- String newname = interceptor.getName(vt.value);
- if (newname != null) {
+ String newName = interceptor.getName(vt.value);
+ if (newName != null) {
StringBuilder buffer = new StringBuilder();
if (vt.arraydim > 0) {
@@ -252,10 +217,10 @@ public class ConstantPool {
buffer.append("[");
}
- buffer.append("L").append(newname).append(";");
+ buffer.append("L").append(newName).append(";");
}
else {
- buffer.append(newname);
+ buffer.append(newName);
}
return buffer.toString();
@@ -265,17 +230,16 @@ public class ConstantPool {
}
private String buildNewDescriptor(int type, String descriptor) {
-
boolean updated = false;
if (type == CodeConstants.CONSTANT_Fieldref) {
FieldDescriptor fd = FieldDescriptor.parseDescriptor(descriptor);
- VarType ftype = fd.type;
- if (ftype.type == CodeConstants.TYPE_OBJECT) {
- String newclname = buildNewClassname(ftype.value);
- if (newclname != null) {
- ftype.value = newclname;
+ VarType fType = fd.type;
+ if (fType.type == CodeConstants.TYPE_OBJECT) {
+ String newClassName = buildNewClassname(fType.value);
+ if (newClassName != null) {
+ fType.value = newClassName;
updated = true;
}
}
@@ -285,14 +249,14 @@ public class ConstantPool {
}
}
else {
-
MethodDescriptor md = MethodDescriptor.parseDescriptor(descriptor);
- // params
- for (VarType partype : md.params) {
- if (partype.type == CodeConstants.TYPE_OBJECT) {
- String newclname = buildNewClassname(partype.value);
- if (newclname != null) {
- partype.value = newclname;
+
+ // parameters
+ for (VarType paramType : md.params) {
+ if (paramType.type == CodeConstants.TYPE_OBJECT) {
+ String newClassName = buildNewClassname(paramType.value);
+ if (newClassName != null) {
+ paramType.value = newClassName;
updated = true;
}
}
@@ -300,9 +264,9 @@ public class ConstantPool {
// return value
if (md.ret.type == CodeConstants.TYPE_OBJECT) {
- String newclname = buildNewClassname(md.ret.value);
- if (newclname != null) {
- md.ret.value = newclname;
+ String newClassName = buildNewClassname(md.ret.value);
+ if (newClassName != null) {
+ md.ret.value = newClassName;
updated = true;
}
}
diff --git a/src/org/jetbrains/java/decompiler/struct/gen/DataPoint.java b/src/org/jetbrains/java/decompiler/struct/gen/DataPoint.java
index 53269da..65a6213 100644
--- a/src/org/jetbrains/java/decompiler/struct/gen/DataPoint.java
+++ b/src/org/jetbrains/java/decompiler/struct/gen/DataPoint.java
@@ -65,7 +65,7 @@ public class DataPoint {
MethodDescriptor md = MethodDescriptor.parseDescriptor(mt.getDescriptor());
int k = 0;
- if ((mt.getAccessFlags() & CodeConstants.ACC_STATIC) == 0) {
+ if (!mt.hasModifier(CodeConstants.ACC_STATIC)) {
point.setVariable(k++, new VarType(CodeConstants.TYPE_OBJECT, 0, null));
}
diff --git a/src/org/jetbrains/java/decompiler/struct/lazy/LazyLoader.java b/src/org/jetbrains/java/decompiler/struct/lazy/LazyLoader.java
index 8673c21..f610900 100644
--- a/src/org/jetbrains/java/decompiler/struct/lazy/LazyLoader.java
+++ b/src/org/jetbrains/java/decompiler/struct/lazy/LazyLoader.java
@@ -24,11 +24,11 @@ import org.jetbrains.java.decompiler.util.DataInputFullStream;
import java.io.IOException;
import java.io.InputStream;
import java.util.HashMap;
+import java.util.Map;
public class LazyLoader {
- private HashMap<String, Link> mapClassLinks = new HashMap<String, Link>();
-
+ private Map<String, Link> mapClassLinks = new HashMap<String, Link>();
private IBytecodeProvider provider;
public LazyLoader(IBytecodeProvider provider) {
@@ -47,98 +47,88 @@ public class LazyLoader {
return mapClassLinks.get(classname);
}
-
public ConstantPool loadPool(String classname) {
-
try {
-
DataInputFullStream in = getClassStream(classname);
- if (in == null) {
- return null;
- }
-
- in.skip(8);
+ if (in == null) return null;
- return new ConstantPool(in);
+ try {
+ in.discard(8);
+ return new ConstantPool(in);
+ }
+ finally {
+ in.close();
+ }
}
catch (IOException ex) {
throw new RuntimeException(ex);
}
}
- public byte[] loadBytecode(StructMethod mt, int code_fulllength) {
+ public byte[] loadBytecode(StructMethod mt, int codeFullLength) {
+ String className = mt.getClassStruct().qualifiedName;
try {
+ DataInputFullStream in = getClassStream(className);
+ if (in == null) return null;
- DataInputFullStream in = getClassStream(mt.getClassStruct().qualifiedName);
- if (in == null) {
- return null;
- }
-
- byte[] res = null;
-
- in.skip(8);
-
- ConstantPool pool = mt.getClassStruct().getPool();
- if (pool == null) {
- pool = new ConstantPool(in);
- }
- else {
- ConstantPool.skipPool(in);
- }
+ try {
+ in.discard(8);
- in.skip(2);
- int this_class = in.readUnsignedShort();
- in.skip(2);
-
- // interfaces
- in.skip(in.readUnsignedShort() * 2);
-
- // fields
- int size = in.readUnsignedShort();
- for (int i = 0; i < size; i++) {
- in.skip(6);
- skipAttributes(in);
- }
-
- // methods
- size = in.readUnsignedShort();
- for (int i = 0; i < size; i++) {
- in.skip(2);
+ ConstantPool pool = mt.getClassStruct().getPool();
+ if (pool == null) {
+ pool = new ConstantPool(in);
+ }
+ else {
+ ConstantPool.skipPool(in);
+ }
- int name_index = in.readUnsignedShort();
- int descriptor_index = in.readUnsignedShort();
+ in.discard(6);
- String[] elem_arr = pool.getClassElement(ConstantPool.METHOD, this_class, name_index, descriptor_index);
- String name = elem_arr[0];
+ // interfaces
+ in.discard(in.readUnsignedShort() * 2);
- if (mt.getName().equals(name)) {
- String descriptor = elem_arr[1];
- if (mt.getDescriptor().equals(descriptor)) {
+ // fields
+ int size = in.readUnsignedShort();
+ for (int i = 0; i < size; i++) {
+ in.discard(6);
+ skipAttributes(in);
+ }
- int len = in.readUnsignedShort();
- for (int j = 0; j < len; j++) {
+ // methods
+ size = in.readUnsignedShort();
+ for (int i = 0; i < size; i++) {
+ in.discard(2);
- int attr_nameindex = in.readUnsignedShort();
- String attrname = pool.getPrimitiveConstant(attr_nameindex).getString();
+ int nameIndex = in.readUnsignedShort();
+ int descriptorIndex = in.readUnsignedShort();
- if (StructGeneralAttribute.ATTRIBUTE_CODE.equals(attrname)) {
- in.skip(12);
+ String[] values = pool.getClassElement(ConstantPool.METHOD, className, nameIndex, descriptorIndex);
+ if (!mt.getName().equals(values[0]) || !mt.getDescriptor().equals(values[1])) {
+ skipAttributes(in);
+ continue;
+ }
- res = new byte[code_fulllength];
- in.readFull(res);
- return res;
- }
- else {
- in.skip(in.readInt());
- }
+ int attrSize = in.readUnsignedShort();
+ for (int j = 0; j < attrSize; j++) {
+ int attrNameIndex = in.readUnsignedShort();
+ String attrName = pool.getPrimitiveConstant(attrNameIndex).getString();
+ if (!StructGeneralAttribute.ATTRIBUTE_CODE.equals(attrName)) {
+ in.discard(in.readInt());
+ continue;
}
- return null;
+ in.discard(12);
+ byte[] code = new byte[codeFullLength];
+ in.readFull(code);
+ return code;
}
- }
- skipAttributes(in);
+ break;
+ }
+ }
+ finally {
+ in.close();
}
return null;
@@ -148,39 +138,38 @@ public class LazyLoader {
}
}
- public DataInputFullStream getClassStream(String externPath, String internPath) throws IOException {
- InputStream instream = provider.getBytecodeStream(externPath, internPath);
- return instream == null ? null : new DataInputFullStream(instream);
+ @SuppressWarnings("IOResourceOpenedButNotSafelyClosed")
+ public DataInputFullStream getClassStream(String externalPath, String internalPath) throws IOException {
+ InputStream stream = provider.getBytecodeStream(externalPath, internalPath);
+ return stream == null ? null : new DataInputFullStream(stream);
}
public DataInputFullStream getClassStream(String qualifiedClassName) throws IOException {
Link link = mapClassLinks.get(qualifiedClassName);
- return link == null ? null : getClassStream(link.externPath, link.internPath);
+ return link == null ? null : getClassStream(link.externalPath, link.internalPath);
}
- private static void skipAttributes(DataInputFullStream in) throws IOException {
-
+ public static void skipAttributes(DataInputFullStream in) throws IOException {
int length = in.readUnsignedShort();
for (int i = 0; i < length; i++) {
- in.skip(2);
- in.skip(in.readInt());
+ in.discard(2);
+ in.discard(in.readInt());
}
}
public static class Link {
-
public static final int CLASS = 1;
public static final int ENTRY = 2;
public int type;
- public String externPath;
- public String internPath;
+ public String externalPath;
+ public String internalPath;
- public Link(int type, String externPath, String internPath) {
+ public Link(int type, String externalPath, String internalPath) {
this.type = type;
- this.externPath = externPath;
- this.internPath = internPath;
+ this.externalPath = externalPath;
+ this.internalPath = internalPath;
}
}
}
diff --git a/src/org/jetbrains/java/decompiler/util/DataInputFullStream.java b/src/org/jetbrains/java/decompiler/util/DataInputFullStream.java
index 0ed20dc..79e8c1d 100644
--- a/src/org/jetbrains/java/decompiler/util/DataInputFullStream.java
+++ b/src/org/jetbrains/java/decompiler/util/DataInputFullStream.java
@@ -25,20 +25,19 @@ public class DataInputFullStream extends DataInputStream {
super(in);
}
- public final int readFull(byte[] b) throws IOException {
-
+ public int readFull(byte[] b) throws IOException {
int length = b.length;
- byte[] btemp = new byte[length];
+ byte[] temp = new byte[length];
int pos = 0;
- int bytes_read = -1;
+ int bytes_read;
while (true) {
- bytes_read = read(btemp, 0, length - pos);
+ bytes_read = read(temp, 0, length - pos);
if (bytes_read == -1) {
return -1;
}
- System.arraycopy(btemp, 0, b, pos, bytes_read);
+ System.arraycopy(temp, 0, b, pos, bytes_read);
pos += bytes_read;
if (pos == length) {
break;
@@ -47,4 +46,10 @@ public class DataInputFullStream extends DataInputStream {
return length;
}
+
+ public void discard(int n) throws IOException {
+ if (super.skip(n) != n) {
+ throw new IOException("Skip failed");
+ }
+ }
}
diff --git a/test/org/jetbrains/java/decompiler/SingleClassesTest.java b/test/org/jetbrains/java/decompiler/SingleClassesTest.java
index 291c0e7..02fb612 100644
--- a/test/org/jetbrains/java/decompiler/SingleClassesTest.java
+++ b/test/org/jetbrains/java/decompiler/SingleClassesTest.java
@@ -33,9 +33,11 @@ public class SingleClassesTest {
@Before
public void setUp() throws IOException {
+ //noinspection SSBasedInspection
tempDir = File.createTempFile("decompiler_test_", "_dir");
assertTrue(tempDir.delete());
assertTrue(tempDir.mkdirs());
+
decompiler = new ConsoleDecompiler(new HashMap<String, Object>() {{
put(IFernflowerPreferences.LOG_LEVEL, "warn");
put(IFernflowerPreferences.DECOMPILE_GENERIC_SIGNATURES, "1");