From 55fbdbd30226e61b1673d98105c9508de76d9145 Mon Sep 17 00:00:00 2001 From: Mikhael Bogdanov Date: Wed, 26 Feb 2014 18:39:24 +0400 Subject: [PATCH] Code clean --- .../codegen/inline/ConstructorInvocation.java | 21 ++++--- .../jet/codegen/inline/InlineCodegen.java | 2 +- .../jet/codegen/inline/InlineCodegenUtil.java | 18 +++--- .../jet/codegen/inline/LambdaTransformer.java | 59 ++++++++++--------- .../jet/codegen/inline/MethodInliner.java | 10 ++-- .../jet/codegen/inline/RemapVisitor.java | 6 ++ 6 files changed, 62 insertions(+), 54 deletions(-) diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/ConstructorInvocation.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/ConstructorInvocation.java index 5c6d035a9c3..d94c8377bd2 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/ConstructorInvocation.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/ConstructorInvocation.java @@ -33,9 +33,9 @@ public class ConstructorInvocation { private String newConstructorDescriptor; - private List recaptured; + private List allRecapturedParameters; - private Map recapturedLambdas; + private Map capturedLambdasToInline; ConstructorInvocation(String ownerInternalName, Map lambdasToInline, boolean isSameModule) { this.ownerInternalName = ownerInternalName; @@ -55,7 +55,6 @@ public class ConstructorInvocation { return lambdasToInline; } - public Type getNewLambdaType() { return newLambdaType; } @@ -72,19 +71,19 @@ public class ConstructorInvocation { this.newConstructorDescriptor = newConstructorDescriptor; } - public List getRecaptured() { - return recaptured; + public List getAllRecapturedParameters() { + return allRecapturedParameters; } - public void setRecaptured(List recaptured) { - this.recaptured = recaptured; + public void setAllRecapturedParameters(List allRecapturedParameters) { + this.allRecapturedParameters = allRecapturedParameters; } - public Map getRecapturedLambdas() { - return recapturedLambdas; + public Map getCapturedLambdasToInline() { + return capturedLambdasToInline; } - public void setRecapturedLambdas(Map recapturedLambdas) { - this.recapturedLambdas = recapturedLambdas; + public void setCapturedLambdasToInline(Map capturedLambdasToInline) { + this.capturedLambdasToInline = capturedLambdasToInline; } } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegen.java index f552fc0ab54..46ce5d8e6c6 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegen.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegen.java @@ -207,7 +207,7 @@ public class InlineCodegen implements ParentCodegenAware, CallGenerator { VarRemapper.ParamRemapper remapper = new VarRemapper.ParamRemapper(parameters, initialFrameSize); - inliner.doTransformAndMerge(codegen.v, remapper); + inliner.doInline(codegen.v, remapper); } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegenUtil.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegenUtil.java index 751990dbe48..70951d72e62 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegenUtil.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/InlineCodegenUtil.java @@ -87,7 +87,7 @@ public class InlineCodegenUtil { FqName namespaceFqName = PackageClassUtils.getPackageClassFqName(((PackageFragmentDescriptor) parentDeclatation).getFqName()).parent().child( name); - file = findVirtualFile(state.getProject(), namespaceFqName, true); + file = findVirtualFileWithHeader(state.getProject(), namespaceFqName); } else { assert false : "Function in namespace should have implClassName property in proto: " + deserializedDescriptor; } @@ -103,13 +103,15 @@ public class InlineCodegenUtil { } @Nullable - public static VirtualFile findVirtualFile(@NotNull Project project, @NotNull FqName containerFqName, boolean onlyKotlin) { + public static VirtualFile findVirtualFileWithHeader(@NotNull Project project, @NotNull FqName containerFqName) { VirtualFileFinder fileFinder = ServiceManager.getService(project, VirtualFileFinder.class); - if (onlyKotlin) { - return fileFinder.findVirtualFileWithHeader(containerFqName); - } else { - return fileFinder.findVirtualFile(containerFqName.asString().replace('.', '/')); - } + return fileFinder.findVirtualFileWithHeader(containerFqName); + } + + @Nullable + public static VirtualFile findVirtualFile(@NotNull Project project, @NotNull String internalName) { + VirtualFileFinder fileFinder = ServiceManager.getService(project, VirtualFileFinder.class); + return fileFinder.findVirtualFile(internalName); } //TODO: navigate to inner classes @@ -185,7 +187,7 @@ public class InlineCodegenUtil { if (containerFqName == null) { return null; } - return findVirtualFile(project, containerFqName, true); + return findVirtualFileWithHeader(project, containerFqName); } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/LambdaTransformer.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/LambdaTransformer.java index adf3a5cc3f2..0da34da5b11 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/LambdaTransformer.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/LambdaTransformer.java @@ -27,10 +27,12 @@ import org.jetbrains.asm4.tree.FieldInsnNode; import org.jetbrains.asm4.tree.MethodNode; import org.jetbrains.asm4.tree.VarInsnNode; import org.jetbrains.jet.OutputFile; -import org.jetbrains.jet.codegen.*; +import org.jetbrains.jet.codegen.AsmUtil; +import org.jetbrains.jet.codegen.ClassBuilder; +import org.jetbrains.jet.codegen.ClosureCodegen; +import org.jetbrains.jet.codegen.FieldInfo; import org.jetbrains.jet.codegen.state.GenerationState; import org.jetbrains.jet.codegen.state.JetTypeMapper; -import org.jetbrains.jet.lang.resolve.name.FqName; import java.io.IOException; import java.util.ArrayList; @@ -55,8 +57,6 @@ public class LambdaTransformer { private final InliningInfo info; - private final Map paramMapping = new HashMap(); - private final Type oldLambdaType; private final Type newLambdaType; @@ -82,7 +82,7 @@ public class LambdaTransformer { if (outputFile != null) { reader = new ClassReader(outputFile.asByteArray()); } else { - VirtualFile file = InlineCodegenUtil.findVirtualFile(state.getProject(), new FqName(lambdaInternalName.replace('/', '.')), false); + VirtualFile file = InlineCodegenUtil.findVirtualFile(state.getProject(), lambdaInternalName); if (file == null) { throw new RuntimeException("Couldn't find virtual file for " + lambdaInternalName); } @@ -93,6 +93,7 @@ public class LambdaTransformer { throw new RuntimeException(e); } + //TODO rewrite to one step constructor = getMethodNode(reader, true, false); invoke = getMethodNode(reader, false, false); bridge = getMethodNode(reader, false, true); @@ -110,6 +111,7 @@ public class LambdaTransformer { public void doTransform(ConstructorInvocation invocation) { ClassBuilder classBuilder = createClassBuilder(); + //TODO: public visibility for inline function classBuilder.defineClass(null, V1_6, classAccess, @@ -122,10 +124,10 @@ public class LambdaTransformer { Parameters parameters = getLambdaParameters(builder, invocation); MethodVisitor invokeVisitor = newMethod(classBuilder, invoke); - InlineFieldRemapper remapper = new InlineFieldRemapper(oldLambdaType.getInternalName(), newLambdaType.getInternalName(), parameters, invocation.getRecapturedLambdas()); + InlineFieldRemapper remapper = new InlineFieldRemapper(oldLambdaType.getInternalName(), newLambdaType.getInternalName(), parameters, invocation.getCapturedLambdasToInline()); MethodInliner inliner = new MethodInliner(invoke, parameters, info.subInline(info.nameGenerator.subGenerator("lambda")), oldLambdaType, remapper, isSameModule); - inliner.doTransformAndMerge(invokeVisitor, new VarRemapper.ParamRemapper(parameters, 0), remapper, false); + inliner.doInline(invokeVisitor, new VarRemapper.ParamRemapper(parameters, 0), remapper, false); invokeVisitor.visitMaxs(-1, -1); generateConstructorAndFields(classBuilder, builder, invocation); @@ -162,6 +164,7 @@ public class LambdaTransformer { AsmUtil.genClosureFields(newConstructorSignature, classBuilder); + //TODO for inline method make public class Method newConstructor = ClosureCodegen.generateConstructor(classBuilder, fields, null, Type.getObjectType(superName), state, AsmUtil.NO_FLAG_PACKAGE_PRIVATE); invocation.setNewConstructorDescriptor(newConstructor.getDescriptor()); } @@ -173,7 +176,7 @@ public class LambdaTransformer { } private ClassBuilder createClassBuilder() { - return new RemappingClassBuilder(state.getFactory().forLambdaInlining(newLambdaType, info.call.getCalleeExpression().getContainingFile()), + return new RemappingClassBuilder(state.getFactory().forLambdaInlining(newLambdaType, info.call.getCallElement().getContainingFile()), new TypeRemapper(info.typeMapping, isSameModule)); } @@ -188,7 +191,7 @@ public class LambdaTransformer { ); } - private void extractParametersMapping(MethodNode constructor, ParametersBuilder builder, ConstructorInvocation invocation) { + private static void extractParametersMapping(MethodNode constructor, ParametersBuilder builder, ConstructorInvocation invocation) { Map indexToLambda = invocation.getLambdasToInline(); AbstractInsnNode cur = constructor.instructions.getFirst(); @@ -197,34 +200,35 @@ public class LambdaTransformer { while (cur != null) { if (cur.getType() == AbstractInsnNode.FIELD_INSN) { FieldInsnNode fieldNode = (FieldInsnNode) cur; + CapturedParamInfo info = builder.addCapturedParam(fieldNode.name, Type.getType(fieldNode.desc), false, null); + + assert fieldNode.getPrevious() instanceof VarInsnNode : "Previous instruction should be VarInsnNode but was " + fieldNode.getPrevious(); VarInsnNode previous = (VarInsnNode) fieldNode.getPrevious(); int varIndex = previous.var; - paramMapping.put(fieldNode.name, varIndex); - - CapturedParamInfo info = builder.addCapturedParam(fieldNode.name, Type.getType(fieldNode.desc), false, null); - LambdaInfo LambdaInfo = indexToLambda.get(varIndex); - if (LambdaInfo != null) { - info.setLambda(LambdaInfo); - additionalCaptured.add(LambdaInfo); + LambdaInfo lambdaInfo = indexToLambda.get(varIndex); + if (lambdaInfo != null) { + info.setLambda(lambdaInfo); + additionalCaptured.add(lambdaInfo); } } cur = cur.getNext(); } - Map recapturedLambdas = new HashMap(); //captured var of inlined parameter - List recaptured = new ArrayList(); + //For all inlined lambdas add their captured parameters + //TODO: some of such parameters could be skipped - we should perform additional analysis + Map capturedLambdasToInline = new HashMap(); //captured var of inlined parameter + List allRecapturedParameters = new ArrayList(); for (LambdaInfo info : additionalCaptured) { - List vars = info.getCapturedVars(); - for (CapturedParamInfo var : vars) { + for (CapturedParamInfo var : info.getCapturedVars()) { CapturedParamInfo recapturedParamInfo = builder.addCapturedParam(getNewFieldName(var.getFieldName()), var.getType(), true, var); recapturedParamInfo.setRecapturedFrom(info); - recaptured.add(var); + allRecapturedParameters.add(var); } - recapturedLambdas.put(info.getLambdaClassType().getInternalName(), info); + capturedLambdasToInline.put(info.getLambdaClassType().getInternalName(), info); } - invocation.setRecaptured(recaptured); - invocation.setRecapturedLambdas(recapturedLambdas); + invocation.setAllRecapturedParameters(allRecapturedParameters); + invocation.setCapturedLambdasToInline(capturedLambdasToInline); } @Nullable @@ -244,7 +248,8 @@ public class LambdaTransformer { @Override public MethodVisitor visitMethod(int access, String name, String desc, String signature, String[] exceptions) { boolean isConstructorMethod = "".equals(name); - if (findConstructor && isConstructorMethod || (!findConstructor && !isConstructorMethod && ((access & Opcodes.ACC_BRIDGE) == (findBridge ? Opcodes.ACC_BRIDGE : 0)))) { + boolean isBridge = (access & Opcodes.ACC_BRIDGE) != 0; + if (findConstructor && isConstructorMethod || (!findConstructor && !isConstructorMethod && (isBridge == findBridge))) { assert methodNode[0] == null : "Wrong lambda/sam structure: " + methodNode[0].name + " conflicts with " + name; return methodNode[0] = new MethodNode(access, name, desc, signature, exceptions); } @@ -259,10 +264,6 @@ public class LambdaTransformer { return methodNode[0]; } - public Type getNewLambdaType() { - return newLambdaType; - } - public static String getNewFieldName(String oldName) { return oldName + "$inlined"; } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/MethodInliner.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/MethodInliner.java index 2a544b9494e..2986a8b5f04 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/MethodInliner.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/MethodInliner.java @@ -71,11 +71,11 @@ public class MethodInliner { } - public void doTransformAndMerge(MethodVisitor adapter, VarRemapper.ParamRemapper remapper) { - doTransformAndMerge(adapter, remapper, new LambdaFieldRemapper(), true); + public void doInline(MethodVisitor adapter, VarRemapper.ParamRemapper remapper) { + doInline(adapter, remapper, new LambdaFieldRemapper(), true); } - public void doTransformAndMerge( + public void doInline( MethodVisitor adapter, VarRemapper.ParamRemapper remapper, LambdaFieldRemapper capturedRemapper, boolean remapReturn @@ -158,7 +158,7 @@ public class MethodInliner { capturedRemapper, true /*cause all calls in same module as lambda*/); VarRemapper.ParamRemapper remapper = new VarRemapper.ParamRemapper(lambdaParameters, valueParamShift); - inliner.doTransformAndMerge(this.mv, remapper); //TODO add skipped this and receiver + inliner.doInline(this.mv, remapper); //TODO add skipped this and receiver //return value boxing/unboxing Method bridge = typeMapper.mapSignature(ClosureCodegen.getInvokeFunction(info.getFunctionDescriptor())).getAsmMethod(); @@ -170,7 +170,7 @@ public class MethodInliner { assert invocation != null : " call not corresponds to new call" + owner + " " + name; if (invocation.shouldRegenerate()) { //put additional captured parameters on stack - List recaptured = invocation.getRecaptured(); + List recaptured = invocation.getAllRecapturedParameters(); List contextCaptured = MethodInliner.this.parameters.getCaptured(); for (CapturedParamInfo capturedParamInfo : recaptured) { CapturedParamInfo result = null; diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/inline/RemapVisitor.java b/compiler/backend/src/org/jetbrains/jet/codegen/inline/RemapVisitor.java index 7c2b5a47da9..0c48282f006 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/inline/RemapVisitor.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/inline/RemapVisitor.java @@ -92,4 +92,10 @@ public class RemapVisitor extends InstructionAdapter { super.visitFieldInsn(opcode, owner, name, desc); } } + + //TODO not skip for lambdas + @Override + public void visitLineNumber(int line, Label start) { + + } }