From 5694a3644c59e04cded79e3acedd996aa3c090bd Mon Sep 17 00:00:00 2001 From: "Pavel V. Talanov" Date: Fri, 10 Aug 2012 21:30:17 +0400 Subject: [PATCH] Remove functionality delegated to LiteralFunctionTranslator from FunctionTranslator. Adapted from https://github.com/develar/kotlin/commit/a9e0a42fb1347fa8e21c86b5a073ef8a7c873da0. --- .../expression/FunctionTranslator.java | 111 +++--------------- 1 file changed, 18 insertions(+), 93 deletions(-) diff --git a/js/js.translator/src/org/jetbrains/k2js/translate/expression/FunctionTranslator.java b/js/js.translator/src/org/jetbrains/k2js/translate/expression/FunctionTranslator.java index 289cafe273d..d9bababb108 100644 --- a/js/js.translator/src/org/jetbrains/k2js/translate/expression/FunctionTranslator.java +++ b/js/js.translator/src/org/jetbrains/k2js/translate/expression/FunctionTranslator.java @@ -17,24 +17,24 @@ package org.jetbrains.k2js.translate.expression; -import com.google.dart.compiler.backend.js.ast.*; -import com.google.dart.compiler.util.AstUtil; +import com.google.dart.compiler.backend.js.ast.JsFunction; +import com.google.dart.compiler.backend.js.ast.JsName; +import com.google.dart.compiler.backend.js.ast.JsParameter; +import com.google.dart.compiler.backend.js.ast.JsPropertyInitializer; import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.Nullable; -import org.jetbrains.jet.lang.descriptors.*; +import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor; +import org.jetbrains.jet.lang.descriptors.FunctionDescriptor; +import org.jetbrains.jet.lang.descriptors.Modality; +import org.jetbrains.jet.lang.descriptors.ValueParameterDescriptor; import org.jetbrains.jet.lang.psi.JetDeclarationWithBody; -import org.jetbrains.jet.lang.psi.JetElement; import org.jetbrains.jet.lang.psi.JetExpression; import org.jetbrains.jet.lang.psi.JetFunctionLiteralExpression; import org.jetbrains.k2js.translate.context.Namer; -import org.jetbrains.k2js.translate.context.TemporaryVariable; import org.jetbrains.k2js.translate.context.TranslationContext; import org.jetbrains.k2js.translate.general.AbstractTranslator; -import org.jetbrains.k2js.translate.reference.ReferenceTranslator; import org.jetbrains.k2js.translate.utils.JsDescriptorUtils; import org.jetbrains.k2js.translate.utils.TranslationUtils; -import org.jetbrains.k2js.translate.utils.closure.ClosureContext; -import org.jetbrains.k2js.translate.utils.closure.ClosureUtils; import java.util.ArrayList; import java.util.List; @@ -43,14 +43,12 @@ import static org.jetbrains.k2js.translate.utils.BindingUtils.getFunctionDescrip import static org.jetbrains.k2js.translate.utils.ErrorReportingUtils.message; import static org.jetbrains.k2js.translate.utils.FunctionBodyTranslator.translateFunctionBody; import static org.jetbrains.k2js.translate.utils.JsAstUtils.setParameters; -import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.*; - +import static org.jetbrains.k2js.translate.utils.JsDescriptorUtils.getExpectedReceiverDescriptor; /** * @author Pavel Talanov */ public final class FunctionTranslator extends AbstractTranslator { - @NotNull public static FunctionTranslator newInstance(@NotNull JetDeclarationWithBody function, @NotNull TranslationContext context) { @@ -59,19 +57,14 @@ public final class FunctionTranslator extends AbstractTranslator { @NotNull private final TranslationContext functionBodyContext; - @Nullable - private TemporaryVariable aliasForContainingClassThis = null; @NotNull private final JetDeclarationWithBody functionDeclaration; @Nullable - private JsName extensionFunctionReceiverName = null; + private JsName extensionFunctionReceiverName; @NotNull private final JsFunction functionObject; @NotNull private final FunctionDescriptor descriptor; - // function body needs to be explicitly created here to include it in the context - @NotNull - private final JsBlock functionBody; private FunctionTranslator(@NotNull JetDeclarationWithBody functionDeclaration, @NotNull TranslationContext context) { @@ -81,33 +74,18 @@ public final class FunctionTranslator extends AbstractTranslator { this.functionObject = context().getFunctionObject(descriptor); assert this.functionObject.getParameters().isEmpty() : message(bindingContext(), descriptor, "Function " + functionDeclaration.getText() + " processed for the second time."); - this.functionBody = functionObject.getBody(); //NOTE: it's important we compute the context before we start the computation this.functionBodyContext = getFunctionBodyContext(); } @NotNull private TranslationContext getFunctionBodyContext() { - if (isLiteral()) { - return getFunctionBodyContextForLiteral(); - } if (isExtensionFunction()) { return getFunctionBodyContextForExtensionFunction(); } return getContextWithFunctionBodyBlock(); } - @NotNull - private TranslationContext getFunctionBodyContextForLiteral() { - ClassDescriptor containingClass = getContainingClass(descriptor); - if (containingClass == null) { - return getContextWithFunctionBodyBlock(); - } - JsExpression thisQualifier = TranslationUtils.getThisObject(context(), containingClass); - aliasForContainingClassThis = context().declareTemporary(thisQualifier); - return getContextWithFunctionBodyBlock().innerContextWithThisAliased(containingClass, aliasForContainingClassThis.name()); - } - @NotNull private TranslationContext getFunctionBodyContextForExtensionFunction() { TranslationContext contextWithFunctionBodyBlock = getContextWithFunctionBodyBlock(); @@ -119,10 +97,9 @@ public final class FunctionTranslator extends AbstractTranslator { @NotNull private TranslationContext getContextWithFunctionBodyBlock() { - return context().newDeclaration(functionDeclaration).innerBlock(functionBody); + return context().newDeclaration(functionDeclaration).innerBlock(functionObject.getBody()); } - @NotNull public JsFunction translateAsLocalFunction() { JsName functionName = context().getNameForElement(functionDeclaration); @@ -144,51 +121,6 @@ public final class FunctionTranslator extends AbstractTranslator { return new JsPropertyInitializer(functionName.makeRef(), functionObject); } - @NotNull - public JsExpression translateAsLiteral() { - assert getExpectedThisDescriptor(descriptor) == null; - generateFunctionObject(); - ClosureContext closureContext = ClosureUtils.captureClosure(context(), (JetElement) functionDeclaration); - if (closureContext.getDescriptors().isEmpty()) { - return mayBeWrapWithThisAlias(); - } - return wrapInClosureCaptureExpression(functionObject, closureContext); - } - - @NotNull - private JsExpression mayBeWrapWithThisAlias() { - if (!shouldAliasThisObject()) { - return functionObject; - } - assert aliasForContainingClassThis != null; - return AstUtil.newSequence(aliasForContainingClassThis.assignmentExpression(), functionObject); - } - - private boolean shouldAliasThisObject() { - if (!isLiteral()) { - return false; - } - ClassDescriptor containingClass = getContainingClass(descriptor); - return containingClass != null; - } - - @NotNull - private JsExpression wrapInClosureCaptureExpression(@NotNull JsExpression wrappedExpression, - @NotNull ClosureContext closureContext) { - JsFunction dummyFunction = new JsFunction(context().scope()); - JsInvocation dummyFunctionInvocation = new JsInvocation(dummyFunction); - for (VariableDescriptor variableDescriptor : closureContext.getDescriptors()) { - dummyFunction.getParameters().add(new JsParameter(context().getNameForDescriptor(variableDescriptor))); - dummyFunctionInvocation.getArguments().add(ReferenceTranslator.translateAsLocalNameReference(variableDescriptor, context())); - if (aliasForContainingClassThis != null) { - dummyFunction.getParameters().add(new JsParameter(aliasForContainingClassThis.name())); - dummyFunctionInvocation.getArguments().add(aliasForContainingClassThis.initExpression()); - } - } - dummyFunction.setBody(new JsBlock(new JsReturn(wrappedExpression))); - return dummyFunctionInvocation; - } - private void generateFunctionObject() { setParameters(functionObject, translateParameters()); translateBody(); @@ -200,24 +132,21 @@ public final class FunctionTranslator extends AbstractTranslator { assert descriptor.getModality().equals(Modality.ABSTRACT); return; } - functionBody.getStatements().add(translateFunctionBody(descriptor, functionDeclaration, functionBodyContext)); + functionObject.getBody().getStatements().addAll(translateFunctionBody(descriptor, functionDeclaration, functionBodyContext).getStatements()); } - @NotNull private List translateParameters() { List jsParameters = new ArrayList(); mayBeAddThisParameterForExtensionFunction(jsParameters); - for (ValueParameterDescriptor valueParameter : descriptor.getValueParameters()) { - JsName parameterName = declareParameter(valueParameter); - jsParameters.add(new JsParameter(parameterName)); - } + addParameters(jsParameters, descriptor, context()); return jsParameters; } - @NotNull - private JsName declareParameter(@NotNull ValueParameterDescriptor valueParameter) { - return context().getNameForDescriptor(valueParameter); + public static void addParameters(List list, FunctionDescriptor descriptor, TranslationContext context) { + for (ValueParameterDescriptor valueParameter : descriptor.getValueParameters()) { + list.add(new JsParameter(context.getNameForDescriptor(valueParameter))); + } } private void mayBeAddThisParameterForExtensionFunction(@NotNull List jsParameters) { @@ -228,10 +157,6 @@ public final class FunctionTranslator extends AbstractTranslator { } private boolean isExtensionFunction() { - return JsDescriptorUtils.isExtension(descriptor) && !isLiteral(); - } - - private boolean isLiteral() { - return functionDeclaration instanceof JetFunctionLiteralExpression; + return JsDescriptorUtils.isExtension(descriptor) && !(functionDeclaration instanceof JetFunctionLiteralExpression); } }