JS backend: mangling JS reserved words.
This commit is contained in:
@@ -8,6 +8,7 @@
|
|||||||
<orderEntry type="inheritedJdk" />
|
<orderEntry type="inheritedJdk" />
|
||||||
<orderEntry type="sourceFolder" forTests="false" />
|
<orderEntry type="sourceFolder" forTests="false" />
|
||||||
<orderEntry type="library" scope="PROVIDED" name="intellij-core" level="project" />
|
<orderEntry type="library" scope="PROVIDED" name="intellij-core" level="project" />
|
||||||
|
<orderEntry type="library" name="kotlin-runtime" level="project" />
|
||||||
</component>
|
</component>
|
||||||
</module>
|
</module>
|
||||||
|
|
||||||
|
|||||||
@@ -14,13 +14,13 @@ public class JsCatchScope extends JsScope {
|
|||||||
private final JsName name;
|
private final JsName name;
|
||||||
|
|
||||||
public JsCatchScope(JsScope parent, String ident) {
|
public JsCatchScope(JsScope parent, String ident) {
|
||||||
super(parent, "Catch scope");
|
super(parent, "Catch scope", null);
|
||||||
name = new JsName(this, ident);
|
name = new JsName(this, ident);
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsName declareName(String identifier) {
|
public JsName declareName(@NotNull String identifier) {
|
||||||
// Declare into parent scope!
|
// Declare into parent scope!
|
||||||
return getParent().declareName(identifier);
|
return getParent().declareName(identifier);
|
||||||
}
|
}
|
||||||
@@ -31,7 +31,7 @@ public class JsCatchScope extends JsScope {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected JsName findOwnName(String ident) {
|
protected JsName findOwnName(@NotNull String ident) {
|
||||||
return name.getIdent().equals(ident) ? name : null;
|
return name.getIdent().equals(ident) ? name : null;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -16,21 +16,21 @@ public final class JsFunction extends JsLiteral implements HasName {
|
|||||||
private JsBlock body;
|
private JsBlock body;
|
||||||
private List<JsParameter> params;
|
private List<JsParameter> params;
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsScope scope;
|
private final JsFunctionScope scope;
|
||||||
private JsName name;
|
private JsName name;
|
||||||
|
|
||||||
public JsFunction(JsScope parentScope) {
|
public JsFunction(@NotNull JsScope parentScope, @NotNull String description) {
|
||||||
this(parentScope, (JsName) null);
|
this(parentScope, description, null);
|
||||||
}
|
}
|
||||||
|
|
||||||
public JsFunction(JsScope parentScope, @NotNull JsBlock body) {
|
public JsFunction(@NotNull JsScope parentScope, @NotNull JsBlock body, @NotNull String description) {
|
||||||
this(parentScope, (JsName) null);
|
this(parentScope, description, null);
|
||||||
this.body = body;
|
this.body = body;
|
||||||
}
|
}
|
||||||
|
|
||||||
private JsFunction(JsScope parentScope, @Nullable JsName name) {
|
private JsFunction(@NotNull JsScope parentScope, @NotNull String description, @Nullable JsName name) {
|
||||||
this.name = name;
|
this.name = name;
|
||||||
scope = new JsScope(parentScope, name == null ? null : name.getIdent());
|
scope = new JsFunctionScope(parentScope, name == null ? description : name.getIdent());
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -57,7 +57,7 @@ public final class JsFunction extends JsLiteral implements HasName {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsScope getScope() {
|
public JsFunctionScope getScope() {
|
||||||
return scope;
|
return scope;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -29,11 +29,11 @@ public final class JsProgram extends SourceInfoAwareJsNode {
|
|||||||
|
|
||||||
private final JsRootScope rootScope;
|
private final JsRootScope rootScope;
|
||||||
private final Map<String, JsStringLiteral> stringLiteralMap = new THashMap<String, JsStringLiteral>();
|
private final Map<String, JsStringLiteral> stringLiteralMap = new THashMap<String, JsStringLiteral>();
|
||||||
private final JsScope topScope;
|
private final JsObjectScope topScope;
|
||||||
|
|
||||||
public JsProgram(String unitId) {
|
public JsProgram(String unitId) {
|
||||||
rootScope = new JsRootScope(this);
|
rootScope = new JsRootScope(this);
|
||||||
topScope = new JsScope(rootScope, "Global", unitId);
|
topScope = new JsObjectScope(rootScope, "Global", unitId);
|
||||||
setFragmentCount(1);
|
setFragmentCount(1);
|
||||||
|
|
||||||
emptyStatement = new JsEmpty();
|
emptyStatement = new JsEmpty();
|
||||||
@@ -94,7 +94,7 @@ public final class JsProgram extends SourceInfoAwareJsNode {
|
|||||||
* Gets the top level scope. This is the scope of all the statements in the
|
* Gets the top level scope. This is the scope of all the statements in the
|
||||||
* main program.
|
* main program.
|
||||||
*/
|
*/
|
||||||
public JsScope getScope() {
|
public JsObjectScope getScope() {
|
||||||
return topScope;
|
return topScope;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -5,6 +5,7 @@
|
|||||||
package com.google.dart.compiler.backend.js.ast;
|
package com.google.dart.compiler.backend.js.ast;
|
||||||
|
|
||||||
import com.google.dart.compiler.backend.js.JsReservedIdentifiers;
|
import com.google.dart.compiler.backend.js.JsReservedIdentifiers;
|
||||||
|
import org.jetbrains.annotations.NotNull;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The root scope is the parent of every scope. All identifiers in this scope
|
* The root scope is the parent of every scope. All identifiers in this scope
|
||||||
@@ -25,7 +26,7 @@ public final class JsRootScope extends JsScope {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
protected JsName findOwnName(String ident) {
|
protected JsName findOwnName(@NotNull String ident) {
|
||||||
JsName name = super.findOwnName(ident);
|
JsName name = super.findOwnName(ident);
|
||||||
if (name == null) {
|
if (name == null) {
|
||||||
if (JsReservedIdentifiers.reservedGlobalSymbols.contains(ident)) {
|
if (JsReservedIdentifiers.reservedGlobalSymbols.contains(ident)) {
|
||||||
|
|||||||
@@ -11,6 +11,8 @@ import org.jetbrains.annotations.Nullable;
|
|||||||
import java.util.Collections;
|
import java.util.Collections;
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
|
import static com.google.dart.compiler.backend.js.ast.AstPackage.JsObjectScope;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A scope is a factory for creating and allocating
|
* A scope is a factory for creating and allocating
|
||||||
* {@link JsName}s. A JavaScript AST is
|
* {@link JsName}s. A JavaScript AST is
|
||||||
@@ -37,40 +39,32 @@ import java.util.Map;
|
|||||||
* with a qualifier and could therefore never be confused with the global scope
|
* with a qualifier and could therefore never be confused with the global scope
|
||||||
* hierarchy.
|
* hierarchy.
|
||||||
*/
|
*/
|
||||||
public class JsScope {
|
public abstract class JsScope {
|
||||||
@Nullable
|
@NotNull
|
||||||
private final String description;
|
private final String description;
|
||||||
private Map<String, JsName> names = Collections.emptyMap();
|
private Map<String, JsName> names = Collections.emptyMap();
|
||||||
private final JsScope parent;
|
private final JsScope parent;
|
||||||
protected int tempIndex = 0;
|
protected int tempIndex = 0;
|
||||||
private final String scopeId;
|
private final String scopeId;
|
||||||
|
|
||||||
public JsScope(JsScope parent, @Nullable String description) {
|
public JsScope(JsScope parent, @NotNull String description, @Nullable String scopeId) {
|
||||||
this(parent, description, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
public JsScope(JsScope parent) {
|
|
||||||
this(parent, null);
|
|
||||||
}
|
|
||||||
|
|
||||||
public JsScope(JsScope parent, @Nullable String description, @Nullable String scopeId) {
|
|
||||||
assert (parent != null);
|
assert (parent != null);
|
||||||
this.scopeId = scopeId;
|
this.scopeId = scopeId;
|
||||||
this.description = description;
|
this.description = description;
|
||||||
this.parent = parent;
|
this.parent = parent;
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
protected JsScope(@NotNull String description) {
|
||||||
public JsScope innerScope(@Nullable String scopeName) {
|
|
||||||
return new JsScope(this, scopeName);
|
|
||||||
}
|
|
||||||
|
|
||||||
protected JsScope(@Nullable String description) {
|
|
||||||
this.description = description;
|
this.description = description;
|
||||||
parent = null;
|
parent = null;
|
||||||
scopeId = null;
|
scopeId = null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@NotNull
|
||||||
|
public JsScope innerObjectScope(@NotNull String scopeName) {
|
||||||
|
return JsObjectScope(this, scopeName);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Gets a name object associated with the specified identifier in this scope,
|
* Gets a name object associated with the specified identifier in this scope,
|
||||||
* creating it if necessary.<br/>
|
* creating it if necessary.<br/>
|
||||||
@@ -81,7 +75,7 @@ public class JsScope {
|
|||||||
* @param identifier An identifier that is unique within this scope.
|
* @param identifier An identifier that is unique within this scope.
|
||||||
*/
|
*/
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsName declareName(String identifier) {
|
public JsName declareName(@NotNull String identifier) {
|
||||||
JsName name = findOwnName(identifier);
|
JsName name = findOwnName(identifier);
|
||||||
return name != null ? name : doCreateName(identifier);
|
return name != null ? name : doCreateName(identifier);
|
||||||
}
|
}
|
||||||
@@ -93,7 +87,7 @@ public class JsScope {
|
|||||||
* (unless they use this function).
|
* (unless they use this function).
|
||||||
*/
|
*/
|
||||||
@NotNull
|
@NotNull
|
||||||
public JsName declareFreshName(String suggestedName) {
|
public JsName declareFreshName(@NotNull String suggestedName) {
|
||||||
String name = suggestedName;
|
String name = suggestedName;
|
||||||
int counter = 0;
|
int counter = 0;
|
||||||
while (hasOwnName(name)) {
|
while (hasOwnName(name)) {
|
||||||
@@ -173,7 +167,7 @@ public class JsScope {
|
|||||||
*
|
*
|
||||||
* @return <code>null</code> if the identifier has no associated name
|
* @return <code>null</code> if the identifier has no associated name
|
||||||
*/
|
*/
|
||||||
protected JsName findOwnName(String ident) {
|
protected JsName findOwnName(@NotNull String ident) {
|
||||||
return names.get(ident);
|
return names.get(ident);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2010-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 com.google.dart.compiler.backend.js.ast
|
||||||
|
|
||||||
|
|
||||||
|
public fun JsObjectScope(parent: JsScope, description: String): JsObjectScope = JsObjectScope(parent, description, null)
|
||||||
|
|
||||||
|
public class JsObjectScope(parent: JsScope, description: String, scopeId: String?) : JsScope(parent, description, scopeId)
|
||||||
|
|
||||||
|
public class JsFunctionScope(parent: JsScope, description: String) : JsScope(parent, description, null) {
|
||||||
|
override fun declareName(identifier: String): JsName = super.declareFreshName(identifier)
|
||||||
|
|
||||||
|
override fun hasOwnName(name: String): Boolean = RESERVED_WORDS.contains(name) || super.hasOwnName(name)
|
||||||
|
|
||||||
|
public fun declareNameUnsafe(identifier: String): JsName = super.declareName(identifier)
|
||||||
|
|
||||||
|
class object {
|
||||||
|
public val RESERVED_WORDS: Set<String> = setOf(
|
||||||
|
// keywords
|
||||||
|
"await", "break", "case", "catch", "continue", "debugger", "default", "delete", "do", "else", "finally", "for", "function", "if",
|
||||||
|
"in", "instanceof", "new", "return", "switch", "this", "throw", "try", "typeof", "var", "void", "while", "with",
|
||||||
|
|
||||||
|
// future reserved words
|
||||||
|
"class", "const", "enum", "export", "extends", "import", "super",
|
||||||
|
|
||||||
|
// as future reserved words in strict mode
|
||||||
|
"implements", "interface", "let", "package", "private", "protected", "public", "static", "yield",
|
||||||
|
|
||||||
|
// additional reserved words
|
||||||
|
"null", "true", "false",
|
||||||
|
|
||||||
|
// disallowed as variable names in strict mode
|
||||||
|
"eval", "arguments",
|
||||||
|
|
||||||
|
// non-reserved words that act like reserved words
|
||||||
|
"NaN", "Infinity", "undefined",
|
||||||
|
|
||||||
|
// the special Kotlin object
|
||||||
|
"Kotlin"
|
||||||
|
)
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -19,10 +19,10 @@ package org.jetbrains.k2js.translate.context
|
|||||||
import com.google.dart.compiler.backend.js.ast.JsExpression
|
import com.google.dart.compiler.backend.js.ast.JsExpression
|
||||||
import com.google.dart.compiler.backend.js.ast.JsPropertyInitializer
|
import com.google.dart.compiler.backend.js.ast.JsPropertyInitializer
|
||||||
import com.google.dart.compiler.backend.js.ast.JsNameRef
|
import com.google.dart.compiler.backend.js.ast.JsNameRef
|
||||||
import com.google.dart.compiler.backend.js.ast.JsScope
|
import com.google.dart.compiler.backend.js.ast.JsObjectScope
|
||||||
|
|
||||||
class DefinitionPlace(
|
class DefinitionPlace(
|
||||||
private val scope: JsScope,
|
private val scope: JsObjectScope,
|
||||||
private val fqName: JsExpression,
|
private val fqName: JsExpression,
|
||||||
val properties: MutableList<JsPropertyInitializer>
|
val properties: MutableList<JsPropertyInitializer>
|
||||||
) {
|
) {
|
||||||
@@ -31,4 +31,4 @@ class DefinitionPlace(
|
|||||||
properties.add(JsPropertyInitializer(name.makeRef(), expression))
|
properties.add(JsPropertyInitializer(name.makeRef(), expression))
|
||||||
return JsNameRef(name, fqName)
|
return JsNameRef(name, fqName)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -23,6 +23,8 @@ import org.jetbrains.jet.lang.resolve.DescriptorUtils;
|
|||||||
import org.jetbrains.jet.lang.resolve.name.FqName;
|
import org.jetbrains.jet.lang.resolve.name.FqName;
|
||||||
import org.jetbrains.jet.plugin.JetLanguage;
|
import org.jetbrains.jet.plugin.JetLanguage;
|
||||||
|
|
||||||
|
import static com.google.dart.compiler.backend.js.ast.AstPackage.JsObjectScope;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Encapuslates different types of constants and naming conventions.
|
* Encapuslates different types of constants and naming conventions.
|
||||||
*/
|
*/
|
||||||
@@ -171,7 +173,7 @@ public final class Namer {
|
|||||||
@NotNull
|
@NotNull
|
||||||
private final JsName kotlinName;
|
private final JsName kotlinName;
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsScope kotlinScope;
|
private final JsObjectScope kotlinScope;
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsName className;
|
private final JsName className;
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -208,7 +210,7 @@ public final class Namer {
|
|||||||
|
|
||||||
private Namer(@NotNull JsScope rootScope) {
|
private Namer(@NotNull JsScope rootScope) {
|
||||||
kotlinName = rootScope.declareName(KOTLIN_NAME);
|
kotlinName = rootScope.declareName(KOTLIN_NAME);
|
||||||
kotlinScope = new JsScope(rootScope, "Kotlin standard object");
|
kotlinScope = JsObjectScope(rootScope, "Kotlin standard object");
|
||||||
traitName = kotlinScope.declareName(TRAIT_OBJECT_NAME);
|
traitName = kotlinScope.declareName(TRAIT_OBJECT_NAME);
|
||||||
|
|
||||||
definePackage = kotlin("definePackage");
|
definePackage = kotlin("definePackage");
|
||||||
@@ -318,7 +320,7 @@ public final class Namer {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
/*package*/ JsScope getKotlinScope() {
|
/*package*/ JsObjectScope getKotlinScope() {
|
||||||
return kotlinScope;
|
return kotlinScope;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -18,7 +18,7 @@ package org.jetbrains.k2js.translate.context;
|
|||||||
|
|
||||||
import com.google.common.collect.Maps;
|
import com.google.common.collect.Maps;
|
||||||
import com.google.dart.compiler.backend.js.ast.JsName;
|
import com.google.dart.compiler.backend.js.ast.JsName;
|
||||||
import com.google.dart.compiler.backend.js.ast.JsScope;
|
import com.google.dart.compiler.backend.js.ast.JsObjectScope;
|
||||||
import org.jetbrains.annotations.NotNull;
|
import org.jetbrains.annotations.NotNull;
|
||||||
import org.jetbrains.annotations.Nullable;
|
import org.jetbrains.annotations.Nullable;
|
||||||
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
|
||||||
@@ -27,6 +27,7 @@ import org.jetbrains.jet.lang.resolve.name.Name;
|
|||||||
|
|
||||||
import java.util.Map;
|
import java.util.Map;
|
||||||
|
|
||||||
|
import static com.google.dart.compiler.backend.js.ast.AstPackage.JsObjectScope;
|
||||||
import static org.jetbrains.jet.lang.resolve.DescriptorUtils.getFqName;
|
import static org.jetbrains.jet.lang.resolve.DescriptorUtils.getFqName;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -85,7 +86,7 @@ public final class StandardClasses {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static StandardClasses bindImplementations(@NotNull JsScope kotlinObjectScope) {
|
public static StandardClasses bindImplementations(@NotNull JsObjectScope kotlinObjectScope) {
|
||||||
StandardClasses standardClasses = new StandardClasses(kotlinObjectScope);
|
StandardClasses standardClasses = new StandardClasses(kotlinObjectScope);
|
||||||
declareKotlinStandardClasses(standardClasses);
|
declareKotlinStandardClasses(standardClasses);
|
||||||
return standardClasses;
|
return standardClasses;
|
||||||
@@ -107,24 +108,24 @@ public final class StandardClasses {
|
|||||||
|
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private final JsScope kotlinScope;
|
private final JsObjectScope kotlinScope;
|
||||||
|
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private final Map<FqNameUnsafe, JsName> standardObjects = Maps.newHashMap();
|
private final Map<FqNameUnsafe, JsName> standardObjects = Maps.newHashMap();
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private final Map<FqNameUnsafe, JsScope> scopeMap = Maps.newHashMap();
|
private final Map<FqNameUnsafe, JsObjectScope> scopeMap = Maps.newHashMap();
|
||||||
|
|
||||||
private StandardClasses(@NotNull JsScope kotlinScope) {
|
private StandardClasses(@NotNull JsObjectScope kotlinScope) {
|
||||||
this.kotlinScope = kotlinScope;
|
this.kotlinScope = kotlinScope;
|
||||||
}
|
}
|
||||||
|
|
||||||
private void declareTopLevelObjectInScope(@NotNull JsScope scope, @NotNull Map<FqNameUnsafe, JsName> map,
|
private void declareTopLevelObjectInScope(@NotNull JsObjectScope scope, @NotNull Map<FqNameUnsafe, JsName> map,
|
||||||
@NotNull FqNameUnsafe fullQualifiedName, @NotNull String name) {
|
@NotNull FqNameUnsafe fullQualifiedName, @NotNull String name) {
|
||||||
JsName declaredName = scope.declareName(name);
|
JsName declaredName = scope.declareName(name);
|
||||||
map.put(fullQualifiedName, declaredName);
|
map.put(fullQualifiedName, declaredName);
|
||||||
scopeMap.put(fullQualifiedName, new JsScope(scope, "scope for " + name));
|
scopeMap.put(fullQualifiedName, JsObjectScope(scope, "scope for " + name));
|
||||||
}
|
}
|
||||||
|
|
||||||
private void declareKotlinObject(@NotNull FqNameUnsafe fullQualifiedName, @NotNull String kotlinLibName) {
|
private void declareKotlinObject(@NotNull FqNameUnsafe fullQualifiedName, @NotNull String kotlinLibName) {
|
||||||
@@ -134,7 +135,7 @@ public final class StandardClasses {
|
|||||||
private void declareInner(@NotNull FqNameUnsafe fullQualifiedClassName,
|
private void declareInner(@NotNull FqNameUnsafe fullQualifiedClassName,
|
||||||
@NotNull String shortMethodName,
|
@NotNull String shortMethodName,
|
||||||
@NotNull String javascriptName) {
|
@NotNull String javascriptName) {
|
||||||
JsScope classScope = scopeMap.get(fullQualifiedClassName);
|
JsObjectScope classScope = scopeMap.get(fullQualifiedClassName);
|
||||||
assert classScope != null;
|
assert classScope != null;
|
||||||
FqNameUnsafe fullQualifiedMethodName = fullQualifiedClassName.child(Name.guess(shortMethodName));
|
FqNameUnsafe fullQualifiedMethodName = fullQualifiedClassName.child(Name.guess(shortMethodName));
|
||||||
standardObjects.put(fullQualifiedMethodName, classScope.declareName(javascriptName));
|
standardObjects.put(fullQualifiedMethodName, classScope.declareName(javascriptName));
|
||||||
|
|||||||
@@ -354,7 +354,7 @@ public final class StaticContext {
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
if (getSuperclass((ClassDescriptor) descriptor) == null) {
|
if (getSuperclass((ClassDescriptor) descriptor) == null) {
|
||||||
return getRootScope().innerScope("Scope for class " + descriptor.getName());
|
return getRootScope().innerObjectScope("Scope for class " + descriptor.getName());
|
||||||
}
|
}
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
@@ -369,7 +369,7 @@ public final class StaticContext {
|
|||||||
if (superclass == null) {
|
if (superclass == null) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return getScopeForDescriptor(superclass).innerScope("Scope for class " + descriptor.getName());
|
return getScopeForDescriptor(superclass).innerObjectScope("Scope for class " + descriptor.getName());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Rule<JsScope> generateNewScopesForPackageDescriptors = new Rule<JsScope>() {
|
Rule<JsScope> generateNewScopesForPackageDescriptors = new Rule<JsScope>() {
|
||||||
@@ -378,7 +378,7 @@ public final class StaticContext {
|
|||||||
if (!(descriptor instanceof PackageFragmentDescriptor)) {
|
if (!(descriptor instanceof PackageFragmentDescriptor)) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
return getRootScope().innerScope("Package " + descriptor.getName());
|
return getRootScope().innerObjectScope("Package " + descriptor.getName());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
//TODO: never get there
|
//TODO: never get there
|
||||||
@@ -386,7 +386,7 @@ public final class StaticContext {
|
|||||||
@Override
|
@Override
|
||||||
public JsScope apply(@NotNull DeclarationDescriptor descriptor) {
|
public JsScope apply(@NotNull DeclarationDescriptor descriptor) {
|
||||||
JsScope enclosingScope = getEnclosingScope(descriptor);
|
JsScope enclosingScope = getEnclosingScope(descriptor);
|
||||||
return enclosingScope.innerScope("Scope for member " + descriptor.getName());
|
return enclosingScope.innerObjectScope("Scope for member " + descriptor.getName());
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
Rule<JsScope> createFunctionObjectsForCallableDescriptors = new Rule<JsScope>() {
|
Rule<JsScope> createFunctionObjectsForCallableDescriptors = new Rule<JsScope>() {
|
||||||
|
|||||||
@@ -19,15 +19,15 @@ package org.jetbrains.k2js.translate.context
|
|||||||
import org.jetbrains.jet.lang.descriptors.*
|
import org.jetbrains.jet.lang.descriptors.*
|
||||||
import org.jetbrains.jet.lang.resolve.DescriptorUtils.isAncestor
|
import org.jetbrains.jet.lang.resolve.DescriptorUtils.isAncestor
|
||||||
import com.google.dart.compiler.backend.js.ast.JsName
|
import com.google.dart.compiler.backend.js.ast.JsName
|
||||||
import com.google.dart.compiler.backend.js.ast.JsScope
|
|
||||||
import org.jetbrains.k2js.translate.utils.TranslationUtils.getSuggestedName
|
import org.jetbrains.k2js.translate.utils.TranslationUtils.getSuggestedName
|
||||||
|
import com.google.dart.compiler.backend.js.ast.JsFunctionScope
|
||||||
|
|
||||||
private val CAPTURED_RECEIVER_NAME_PREFIX : String = "this$"
|
private val CAPTURED_RECEIVER_NAME_PREFIX : String = "this$"
|
||||||
|
|
||||||
class UsageTracker(
|
class UsageTracker(
|
||||||
private val parent: UsageTracker?,
|
private val parent: UsageTracker?,
|
||||||
val containingDescriptor: MemberDescriptor,
|
val containingDescriptor: MemberDescriptor,
|
||||||
private val scope: JsScope
|
private val scope: JsFunctionScope
|
||||||
) {
|
) {
|
||||||
|
|
||||||
private val captured = linkedMapOf<CallableDescriptor, JsName>()
|
private val captured = linkedMapOf<CallableDescriptor, JsName>()
|
||||||
|
|||||||
@@ -114,7 +114,7 @@ public final class ClassTranslator extends AbstractTranslator {
|
|||||||
if (!descriptor.getKind().isSingleton() && !isAnonymousObject(descriptor)) {
|
if (!descriptor.getKind().isSingleton() && !isAnonymousObject(descriptor)) {
|
||||||
qualifiedReference = declarationContext.getQualifiedReference(descriptor);
|
qualifiedReference = declarationContext.getQualifiedReference(descriptor);
|
||||||
JsScope scope = context().getScopeForDescriptor(descriptor);
|
JsScope scope = context().getScopeForDescriptor(descriptor);
|
||||||
definitionPlace = new DefinitionPlace(scope, qualifiedReference, staticProperties);
|
definitionPlace = new DefinitionPlace((JsObjectScope) scope, qualifiedReference, staticProperties);
|
||||||
}
|
}
|
||||||
|
|
||||||
declarationContext = declarationContext.newDeclaration(descriptor, definitionPlace);
|
declarationContext = declarationContext.newDeclaration(descriptor, definitionPlace);
|
||||||
@@ -240,7 +240,7 @@ public final class ClassTranslator extends AbstractTranslator {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
private JsExpression translateObjectInsideClass(@NotNull TranslationContext outerClassContext) {
|
private JsExpression translateObjectInsideClass(@NotNull TranslationContext outerClassContext) {
|
||||||
JsFunction fun = new JsFunction(outerClassContext.scope(), new JsBlock());
|
JsFunction fun = new JsFunction(outerClassContext.scope(), new JsBlock(), "initializer for " + descriptor.getName().asString());
|
||||||
TranslationContext funContext = outerClassContext.newFunctionBodyWithUsageTracker(fun, descriptor);
|
TranslationContext funContext = outerClassContext.newFunctionBodyWithUsageTracker(fun, descriptor);
|
||||||
|
|
||||||
fun.getBody().getStatements().add(new JsReturn(translate(funContext)));
|
fun.getBody().getStatements().add(new JsReturn(translate(funContext)));
|
||||||
|
|||||||
+4
-3
@@ -109,6 +109,7 @@ public class DelegationTranslator(
|
|||||||
val propertyName: String = descriptor.getName().asString()
|
val propertyName: String = descriptor.getName().asString()
|
||||||
|
|
||||||
fun generateDelegateGetterFunction(getterDescriptor: PropertyGetterDescriptor): JsFunction {
|
fun generateDelegateGetterFunction(getterDescriptor: PropertyGetterDescriptor): JsFunction {
|
||||||
|
// TODO review: used wrong scope?
|
||||||
val delegateRefName = context().getScopeForDescriptor(getterDescriptor).declareName(delegateName)
|
val delegateRefName = context().getScopeForDescriptor(getterDescriptor).declareName(delegateName)
|
||||||
val delegateRef = JsNameRef(delegateRefName, JsLiteral.THIS)
|
val delegateRef = JsNameRef(delegateRefName, JsLiteral.THIS)
|
||||||
|
|
||||||
@@ -130,7 +131,8 @@ public class DelegationTranslator(
|
|||||||
}
|
}
|
||||||
|
|
||||||
fun generateDelegateSetterFunction(setterDescriptor: PropertySetterDescriptor): JsFunction {
|
fun generateDelegateSetterFunction(setterDescriptor: PropertySetterDescriptor): JsFunction {
|
||||||
val jsFunction = JsFunction(context().getScopeForDescriptor(setterDescriptor.getContainingDeclaration()))
|
val jsFunction = JsFunction(context().getScopeForDescriptor(setterDescriptor.getContainingDeclaration()),
|
||||||
|
"setter for " + setterDescriptor.getName().asString())
|
||||||
|
|
||||||
assert(setterDescriptor.getValueParameters().size() == 1, "Setter must have 1 parameter")
|
assert(setterDescriptor.getValueParameters().size() == 1, "Setter must have 1 parameter")
|
||||||
val defaultParameter = JsParameter(jsFunction.getScope().declareTemporary())
|
val defaultParameter = JsParameter(jsFunction.getScope().declareTemporary())
|
||||||
@@ -169,8 +171,7 @@ public class DelegationTranslator(
|
|||||||
return generateDelegateAccessor(setterDescriptor, generateDelegateSetterFunction(setterDescriptor))
|
return generateDelegateAccessor(setterDescriptor, generateDelegateSetterFunction(setterDescriptor))
|
||||||
}
|
}
|
||||||
|
|
||||||
properties.addGetterAndSetter(descriptor, context(), ::generateDelegateGetter, ::generateDelegateSetter
|
properties.addGetterAndSetter(descriptor, context(), ::generateDelegateGetter, ::generateDelegateSetter)
|
||||||
)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
+2
-2
@@ -50,7 +50,7 @@ class JsDataClassGenerator extends DataClassMethodGenerator {
|
|||||||
@Override
|
@Override
|
||||||
public void generateCopyFunction(@NotNull FunctionDescriptor function, @NotNull List<JetParameter> constructorParameters) {
|
public void generateCopyFunction(@NotNull FunctionDescriptor function, @NotNull List<JetParameter> constructorParameters) {
|
||||||
JsFunction functionObj = generateJsMethod(function);
|
JsFunction functionObj = generateJsMethod(function);
|
||||||
JsScope funScope = functionObj.getScope();
|
JsFunctionScope funScope = functionObj.getScope();
|
||||||
|
|
||||||
assert function.getValueParameters().size() == constructorParameters.size();
|
assert function.getValueParameters().size() == constructorParameters.size();
|
||||||
|
|
||||||
@@ -145,7 +145,7 @@ class JsDataClassGenerator extends DataClassMethodGenerator {
|
|||||||
assert !classProperties.isEmpty();
|
assert !classProperties.isEmpty();
|
||||||
FunctionDescriptor prototypeFun = CodegenUtil.getAnyEqualsMethod();
|
FunctionDescriptor prototypeFun = CodegenUtil.getAnyEqualsMethod();
|
||||||
JsFunction functionObj = generateJsMethod(prototypeFun);
|
JsFunction functionObj = generateJsMethod(prototypeFun);
|
||||||
JsScope funScope = functionObj.getScope();
|
JsFunctionScope funScope = functionObj.getScope();
|
||||||
|
|
||||||
JsName paramName = funScope.declareName("other");
|
JsName paramName = funScope.declareName("other");
|
||||||
functionObj.getParameters().add(new JsParameter(paramName));
|
functionObj.getParameters().add(new JsParameter(paramName));
|
||||||
|
|||||||
+1
-1
@@ -42,7 +42,7 @@ final class PackageTranslator extends AbstractTranslator {
|
|||||||
JsNameRef reference = context.getQualifiedReference(descriptor);
|
JsNameRef reference = context.getQualifiedReference(descriptor);
|
||||||
SmartList<JsPropertyInitializer> properties = new SmartList<JsPropertyInitializer>();
|
SmartList<JsPropertyInitializer> properties = new SmartList<JsPropertyInitializer>();
|
||||||
|
|
||||||
DefinitionPlace definitionPlace = new DefinitionPlace(scope, reference, properties);
|
DefinitionPlace definitionPlace = new DefinitionPlace((JsObjectScope) scope, reference, properties);
|
||||||
|
|
||||||
TranslationContext newContext = context.newDeclaration(descriptor, definitionPlace);
|
TranslationContext newContext = context.newDeclaration(descriptor, definitionPlace);
|
||||||
FileDeclarationVisitor visitor = new FileDeclarationVisitor(newContext, definitionPlace.getProperties());
|
FileDeclarationVisitor visitor = new FileDeclarationVisitor(newContext, definitionPlace.getProperties());
|
||||||
|
|||||||
@@ -127,7 +127,8 @@ private class PropertyTranslator(
|
|||||||
}
|
}
|
||||||
|
|
||||||
private fun generateDefaultSetterFunction(setterDescriptor: PropertySetterDescriptor): JsFunction {
|
private fun generateDefaultSetterFunction(setterDescriptor: PropertySetterDescriptor): JsFunction {
|
||||||
val jsFunction = JsFunction(context().getScopeForDescriptor(setterDescriptor.getContainingDeclaration()))
|
val jsFunction = JsFunction(context().getScopeForDescriptor(setterDescriptor.getContainingDeclaration()),
|
||||||
|
"setter for " + setterDescriptor.getName().asString())
|
||||||
|
|
||||||
assert(setterDescriptor.getValueParameters().size() == 1, "Setter must have 1 parameter")
|
assert(setterDescriptor.getValueParameters().size() == 1, "Setter must have 1 parameter")
|
||||||
val valueParameterDescriptor = setterDescriptor.getValueParameters().get(0)
|
val valueParameterDescriptor = setterDescriptor.getValueParameters().get(0)
|
||||||
|
|||||||
@@ -351,8 +351,9 @@ public final class ExpressionVisitor extends TranslatorVisitor<JsNode> {
|
|||||||
}
|
}
|
||||||
|
|
||||||
private static String getReferencedName(JetSimpleNameExpression expression) {
|
private static String getReferencedName(JetSimpleNameExpression expression) {
|
||||||
String name = expression.getReferencedName();
|
return expression.getReferencedName()
|
||||||
return name.charAt(0) == '@' ? name.substring(1) + '$' : name;
|
.replaceAll("^@", "")
|
||||||
|
.replaceAll("(?:^`(.*)`$)", "$1");
|
||||||
}
|
}
|
||||||
|
|
||||||
private static String getTargetLabel(JetExpressionWithLabel expression, TranslationContext context) {
|
private static String getTargetLabel(JetExpressionWithLabel expression, TranslationContext context) {
|
||||||
|
|||||||
@@ -24,7 +24,7 @@ public abstract class CommonUnitTester extends JSTester {
|
|||||||
@Override
|
@Override
|
||||||
public void constructTestMethodInvocation(@NotNull JsExpression functionToTestCall,
|
public void constructTestMethodInvocation(@NotNull JsExpression functionToTestCall,
|
||||||
@NotNull JsStringLiteral testName) {
|
@NotNull JsStringLiteral testName) {
|
||||||
JsFunction functionToTest = new JsFunction(getContext().scope());
|
JsFunction functionToTest = new JsFunction(getContext().scope(), "test function");
|
||||||
functionToTest.setBody(new JsBlock(functionToTestCall.makeStmt()));
|
functionToTest.setBody(new JsBlock(functionToTestCall.makeStmt()));
|
||||||
getBlock().getStatements().add(new JsInvocation(getTestMethodRef(), testName, functionToTest).makeStmt());
|
getBlock().getStatements().add(new JsInvocation(getTestMethodRef(), testName, functionToTest).makeStmt());
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -278,7 +278,7 @@ public final class JsAstUtils {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static JsFunction createFunctionWithEmptyBody(@NotNull JsScope parent) {
|
public static JsFunction createFunctionWithEmptyBody(@NotNull JsScope parent) {
|
||||||
return new JsFunction(parent, new JsBlock());
|
return new JsFunction(parent, new JsBlock(), "<anonymous>");
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
@@ -322,10 +322,10 @@ public final class JsAstUtils {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static JsFunction createPackage(@NotNull List<JsStatement> to, @NotNull JsScope scope) {
|
public static JsFunction createPackage(@NotNull List<JsStatement> to, @NotNull JsObjectScope scope) {
|
||||||
JsFunction packageBlockFunction = createFunctionWithEmptyBody(scope);
|
JsFunction packageBlockFunction = createFunctionWithEmptyBody(scope);
|
||||||
|
|
||||||
JsName kotlinObjectAsParameter = packageBlockFunction.getScope().declareName(Namer.KOTLIN_NAME);
|
JsName kotlinObjectAsParameter = packageBlockFunction.getScope().declareNameUnsafe(Namer.KOTLIN_NAME);
|
||||||
packageBlockFunction.getParameters().add(new JsParameter(kotlinObjectAsParameter));
|
packageBlockFunction.getParameters().add(new JsParameter(kotlinObjectAsParameter));
|
||||||
|
|
||||||
to.add(new JsInvocation(packageBlockFunction, Namer.KOTLIN_OBJECT_REF).makeStmt());
|
to.add(new JsInvocation(packageBlockFunction, Namer.KOTLIN_OBJECT_REF).makeStmt());
|
||||||
|
|||||||
@@ -65,7 +65,7 @@ public final class TranslationUtils {
|
|||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
public static JsFunction simpleReturnFunction(@NotNull JsScope functionScope, @NotNull JsExpression returnExpression) {
|
public static JsFunction simpleReturnFunction(@NotNull JsScope functionScope, @NotNull JsExpression returnExpression) {
|
||||||
return new JsFunction(functionScope, new JsBlock(new JsReturn(returnExpression)));
|
return new JsFunction(functionScope, new JsBlock(new JsReturn(returnExpression)), "<simpleReturnFunction>");
|
||||||
}
|
}
|
||||||
|
|
||||||
@NotNull
|
@NotNull
|
||||||
|
|||||||
Reference in New Issue
Block a user