diff --git a/.idea/libraries/asm.xml b/.idea/libraries/asm.xml
index 479c49dcb20..fc8083b4e42 100644
--- a/.idea/libraries/asm.xml
+++ b/.idea/libraries/asm.xml
@@ -4,6 +4,8 @@
-
+
+
+
\ No newline at end of file
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ClassBuilderFactory.java b/compiler/backend/src/org/jetbrains/jet/codegen/ClassBuilderFactory.java
new file mode 100644
index 00000000000..dc4075d0cf4
--- /dev/null
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/ClassBuilderFactory.java
@@ -0,0 +1,57 @@
+package org.jetbrains.jet.codegen;
+
+import org.objectweb.asm.ClassWriter;
+import org.objectweb.asm.util.TraceClassVisitor;
+
+import java.io.PrintWriter;
+import java.io.StringWriter;
+
+/**
+ * @author max
+ */
+public interface ClassBuilderFactory {
+ ClassBuilder newClassBuilder();
+ String asText(ClassBuilder builder);
+ byte[] asBytes(ClassBuilder builder);
+
+ ClassBuilderFactory TEXT = new ClassBuilderFactory() {
+ @Override
+ public ClassBuilder newClassBuilder() {
+ return new ClassBuilder(new TraceClassVisitor(new PrintWriter(new StringWriter())));
+ }
+
+ @Override
+ public String asText(ClassBuilder builder) {
+ TraceClassVisitor visitor = (TraceClassVisitor) builder.getVisitor();
+
+ StringWriter writer = new StringWriter();
+ visitor.print(new PrintWriter(writer));
+
+ return writer.toString();
+ }
+
+ @Override
+ public byte[] asBytes(ClassBuilder builder) {
+ throw new UnsupportedOperationException("TEXT generator asked for bytes");
+ }
+ };
+
+ ClassBuilderFactory BINARIES = new ClassBuilderFactory() {
+ @Override
+ public ClassBuilder newClassBuilder() {
+ return new ClassBuilder(new ClassWriter(ClassWriter.COMPUTE_FRAMES | ClassWriter.COMPUTE_MAXS));
+ }
+
+ @Override
+ public String asText(ClassBuilder builder) {
+ throw new UnsupportedOperationException("BINARIES generator asked for text");
+ }
+
+ @Override
+ public byte[] asBytes(ClassBuilder builder) {
+ ClassWriter visitor = (ClassWriter) builder.getVisitor();
+ return visitor.toByteArray();
+ }
+ };
+
+}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ClassFileFactory.java b/compiler/backend/src/org/jetbrains/jet/codegen/ClassFileFactory.java
index 0fadb452d83..98da6b5fb40 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/ClassFileFactory.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/ClassFileFactory.java
@@ -1,42 +1,26 @@
package org.jetbrains.jet.codegen;
-import com.intellij.openapi.project.Project;
import org.jetbrains.jet.lang.psi.JetNamespace;
-import org.objectweb.asm.ClassVisitor;
-import org.objectweb.asm.ClassWriter;
-import org.objectweb.asm.util.TraceClassVisitor;
-import java.io.PrintWriter;
-import java.io.StringWriter;
import java.util.*;
/**
* @author max
*/
public class ClassFileFactory {
- private final Project project;
- private final boolean isText;
+ private final ClassBuilderFactory builderFactory;
private final Map ns2codegen = new HashMap();
private final Map generators = new LinkedHashMap();
private boolean isDone = false;
public final GenerationState state;
- public ClassFileFactory(Project project, boolean text, GenerationState state) {
- this.project = project;
- isText = text;
+ public ClassFileFactory(ClassBuilderFactory builderFactory, GenerationState state) {
+ this.builderFactory = builderFactory;
this.state = state;
}
ClassBuilder newVisitor(String filePath) {
- ClassVisitor visitor;
- if (isText) {
- visitor = new TraceClassVisitor(new PrintWriter(new StringWriter()));
- }
- else {
- visitor = new ClassWriter(ClassWriter.COMPUTE_FRAMES | ClassWriter.COMPUTE_MAXS);
- }
-
- final ClassBuilder answer = new ClassBuilder(visitor);
+ final ClassBuilder answer = builderFactory.newClassBuilder();
generators.put(filePath, answer);
return answer;
}
@@ -68,25 +52,13 @@ public class ClassFileFactory {
}
public String asText(String file) {
- assert isText : "Need to create with text=true";
-
done();
-
- TraceClassVisitor visitor = (TraceClassVisitor) generators.get(file).getVisitor();
-
- StringWriter writer = new StringWriter();
- visitor.print(new PrintWriter(writer));
-
- return writer.toString();
+ return builderFactory.asText(generators.get(file));
}
public byte[] asBytes(String file) {
- assert !isText : "This is debug stuff, only produces texts.";
-
done();
-
- ClassWriter visitor = (ClassWriter) generators.get(file).getVisitor();
- return visitor.toByteArray();
+ return builderFactory.asBytes(generators.get(file));
}
public List files() {
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ClosureCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ClosureCodegen.java
index 33eaf4ec4e0..9217feb4cce 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/ClosureCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/ClosureCodegen.java
@@ -69,7 +69,7 @@ public class ClosureCodegen extends FunctionOrClosureCodegen {
signatureWriter.visitEnd();
cv.defineClass(V1_6,
- ACC_PUBLIC,
+ ACC_PUBLIC/*|ACC_SUPER*/,
name,
null,
funClass,
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/CodegenUtil.java b/compiler/backend/src/org/jetbrains/jet/codegen/CodegenUtil.java
index 3e3fe413c90..01c767cfd25 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/CodegenUtil.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/CodegenUtil.java
@@ -1,14 +1,9 @@
package org.jetbrains.jet.codegen;
-import com.intellij.psi.PsiClass;
-import com.intellij.psi.PsiElement;
import org.jetbrains.jet.lang.descriptors.ClassDescriptor;
import org.jetbrains.jet.lang.descriptors.ClassKind;
import org.jetbrains.jet.lang.descriptors.DeclarationDescriptor;
-import org.jetbrains.jet.lang.psi.JetClass;
-import org.jetbrains.jet.lang.resolve.BindingContext;
import org.jetbrains.jet.lang.types.JetType;
-import org.jetbrains.jet.lang.types.TypeProjection;
import org.objectweb.asm.Type;
/**
@@ -67,39 +62,4 @@ public class CodegenUtil {
return hasOuterTypeInfo(outerClassDescriptor);
}
-
- public static boolean hasTypeInfoField(JetType type) {
- if(type.getConstructor().getParameters().size() > 0)
- return true;
-
- for (JetType jetType : type.getConstructor().getSupertypes()) {
- if(hasTypeInfoField(jetType))
- return true;
- }
-
- ClassDescriptor outerClassDescriptor = getOuterClassDescriptor(type.getConstructor().getDeclarationDescriptor());
- if(outerClassDescriptor == null)
- return false;
-
- return hasTypeInfoField(outerClassDescriptor.getDefaultType());
- }
-
- public static boolean hasDerivedTypeInfoField(JetType type, boolean exceptOwn) {
- if(!exceptOwn) {
- if(!isInterface(type))
- if(hasTypeInfoField(type))
- return true;
- }
-
- for (JetType jetType : type.getConstructor().getSupertypes()) {
- if(hasDerivedTypeInfoField(jetType, false))
- return true;
- }
-
- return false;
- }
-
- public static Type arrayElementType(Type type) {
- return Type.getType(type.getDescriptor().substring(1));
- }
}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java
index 545e9f9a791..1792a90c644 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java
@@ -128,6 +128,23 @@ public class ExpressionCodegen extends JetVisitor {
throw new UnsupportedOperationException("Codegen for " + expression + " is not yet implemented");
}
+ @Override
+ public StackValue visitNamedFunction(JetNamedFunction function, StackValue data) {
+ throw new UnsupportedOperationException("Codegen for named functions is not yet implemented");
+ }
+
+ @Override
+ public StackValue visitSuperExpression(JetSuperExpression expression, StackValue data) {
+// final DeclarationDescriptor descriptor = bindingContext.get(BindingContext.REFERENCE_TARGET, expression.getInstanceReference());
+// if (descriptor instanceof ClassDescriptor) {
+// return generateThisOrOuter((ClassDescriptor) descriptor);
+// }
+// else {
+// return thisExpression();
+// }
+ return StackValue.none();
+ }
+
@Override
public StackValue visitParenthesizedExpression(JetParenthesizedExpression expression, StackValue receiver) {
return genQualified(receiver, expression.getExpression());
@@ -285,7 +302,7 @@ public class ExpressionCodegen extends JetVisitor {
// if(hND != null)
// invokeFunctionNoParams(hND, Type.BOOLEAN_TYPE, v);
// else
- intermediateValueForProperty((PropertyDescriptor) hasNextDescriptor, false, false).put(Type.BOOLEAN_TYPE, v);
+ intermediateValueForProperty((PropertyDescriptor) hasNextDescriptor, false, false, false).put(Type.BOOLEAN_TYPE, v);
}
v.ifeq(end);
@@ -793,16 +810,17 @@ public class ExpressionCodegen extends JetVisitor {
}
else {
boolean isStatic = container instanceof NamespaceDescriptorImpl;
- final boolean directToField = expression.getReferencedNameElementType() == JetTokens.FIELD_IDENTIFIER;
+ final boolean directToField = expression.getReferencedNameElementType() == JetTokens.FIELD_IDENTIFIER && contextKind() != OwnerKind.TRAIT_IMPL ;
JetExpression r = getReceiverForSelector(expression);
final boolean forceInterface = r != null && !(r instanceof JetThisExpression);
- final StackValue iValue = intermediateValueForProperty(propertyDescriptor, directToField, forceInterface);
+ final boolean isSuper = r instanceof JetSuperExpression;
+ final StackValue iValue = intermediateValueForProperty(propertyDescriptor, directToField, forceInterface, isSuper);
if (!isStatic) {
if (receiver == StackValue.none()) {
receiver = generateThisOrOuter((ClassDescriptor) propertyDescriptor.getContainingDeclaration());
}
JetType receiverType = bindingContext.get(BindingContext.EXPRESSION_TYPE, r);
- receiver.put(receiverType != null ? typeMapper.mapType(receiverType) : JetTypeMapper.TYPE_OBJECT, v);
+ receiver.put(receiverType != null && !isSuper? typeMapper.mapType(receiverType) : JetTypeMapper.TYPE_OBJECT, v);
if(receiverType != null) {
ClassDescriptor propReceiverDescriptor = (ClassDescriptor) propertyDescriptor.getContainingDeclaration();
if(!CodegenUtil.isInterface(propReceiverDescriptor) && CodegenUtil.isInterface(receiverType.getConstructor().getDeclarationDescriptor())) {
@@ -895,11 +913,11 @@ public class ExpressionCodegen extends JetVisitor {
StackValue.onStack(typeMapper.mapType(functionDescriptor.getReturnType())).coerce(type, v);
}
- public StackValue intermediateValueForProperty(PropertyDescriptor propertyDescriptor, final boolean forceField, boolean forceInterface) {
+ public StackValue intermediateValueForProperty(PropertyDescriptor propertyDescriptor, final boolean forceField, boolean forceInterface, boolean isSuper) {
DeclarationDescriptor containingDeclaration = propertyDescriptor.getContainingDeclaration();
boolean isStatic = containingDeclaration instanceof NamespaceDescriptorImpl;
propertyDescriptor = propertyDescriptor.getOriginal();
- boolean isInsideClass = !forceInterface && containingDeclaration == context.getContextClass();
+ boolean isInsideClass = !forceInterface && containingDeclaration == context.getContextClass() && contextKind() != OwnerKind.TRAIT_IMPL;
Method getter;
Method setter;
if (forceField) {
@@ -909,10 +927,10 @@ public class ExpressionCodegen extends JetVisitor {
else {
//noinspection ConstantConditions
getter = isInsideClass && (propertyDescriptor.getGetter() == null || propertyDescriptor.getGetter().isDefault())
- ? null : typeMapper.mapGetterSignature(propertyDescriptor);
+ ? null : typeMapper.mapGetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION);
//noinspection ConstantConditions
setter = isInsideClass && (propertyDescriptor.getSetter() == null || propertyDescriptor.getSetter().isDefault())
- ? null : typeMapper.mapSetterSignature(propertyDescriptor);
+ ? null : typeMapper.mapSetterSignature(propertyDescriptor, OwnerKind.IMPLEMENTATION);
}
String owner;
@@ -931,7 +949,7 @@ public class ExpressionCodegen extends JetVisitor {
}
}
- return StackValue.property(propertyDescriptor.getName(), owner, typeMapper.mapType(propertyDescriptor.getOutType()), isStatic, isInterface, getter, setter);
+ return StackValue.property(propertyDescriptor.getName(), owner, typeMapper.mapType(propertyDescriptor.getOutType()), isStatic, isInterface, isSuper, getter, setter);
}
@Override
@@ -1009,10 +1027,10 @@ public class ExpressionCodegen extends JetVisitor {
private DeclarationDescriptor resolveCalleeDescriptor(JetCallExpression call) {
JetExpression callee = call.getCalleeExpression();
- if (!(callee instanceof JetSimpleNameExpression)) {
+ if (!(callee instanceof JetReferenceExpression)) {
throw new UnsupportedOperationException("Don't know how to generate a call to " + callee);
}
- DeclarationDescriptor funDescriptor = bindingContext.get(BindingContext.REFERENCE_TARGET, (JetSimpleNameExpression) callee);
+ DeclarationDescriptor funDescriptor = bindingContext.get(BindingContext.REFERENCE_TARGET, (JetReferenceExpression) callee);
if (funDescriptor == null) {
throw new CompilationException("Cannot resolve: " + callee.getText());
}
@@ -1883,7 +1901,7 @@ public class ExpressionCodegen extends JetVisitor {
Type type = JetTypeMapper.psiClassType(javaClass);
v.anew(type);
v.dup();
- final CallableMethod callableMethod = typeMapper.mapToCallableMethod(constructor);
+ final CallableMethod callableMethod = JetTypeMapper.mapToCallableMethod(constructor);
invokeMethodWithArguments(callableMethod, expression, StackValue.none());
return type;
}
@@ -2071,6 +2089,7 @@ public class ExpressionCodegen extends JetVisitor {
return generateThisOrOuter((ClassDescriptor) descriptor);
}
else {
+ // estension function or ???
return thisExpression();
}
}
@@ -2260,7 +2279,8 @@ public class ExpressionCodegen extends JetVisitor {
private void generateInstanceOf(StackValue expressionToGen, JetType jetType, boolean leaveExpressionOnStack) {
DeclarationDescriptor descriptor = jetType.getConstructor().getDeclarationDescriptor();
- if (jetType.getArguments().size() > 0 || !(descriptor instanceof ClassDescriptor)) {
+ boolean javaClass = bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, descriptor) instanceof PsiClass;
+ if (!javaClass && (jetType.getArguments().size() > 0 || !(descriptor instanceof ClassDescriptor))) {
generateTypeInfo(jetType);
expressionToGen.put(OBJECT_TYPE, v);
if (leaveExpressionOnStack) {
@@ -2306,7 +2326,7 @@ public class ExpressionCodegen extends JetVisitor {
return;
}
- if(!CodegenUtil.hasTypeInfoField(jetType)) {
+ if(!typeMapper.hasTypeInfoField(jetType) && !(bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, jetType.getConstructor().getDeclarationDescriptor()) instanceof PsiClass)) {
// TODO: we need some better checks here
v.getstatic(typeMapper.mapType(jetType, OwnerKind.IMPLEMENTATION).getInternalName(), "$staticTypeInfo", "Ljet/typeinfo/TypeInfo;");
return;
@@ -2368,7 +2388,7 @@ public class ExpressionCodegen extends JetVisitor {
ownerType = JetTypeMapper.boxType(ownerType);
if (containingDeclaration == context.getContextClass()) {
if(!CodegenUtil.isInterface(descriptor)) {
- if (CodegenUtil.hasTypeInfoField(defaultType)) {
+ if (typeMapper.hasTypeInfoField(defaultType)) {
v.load(0, JetTypeMapper.TYPE_OBJECT);
v.getfield(ownerType.getInternalName(), "$typeInfo", "Ljet/typeinfo/TypeInfo;");
}
@@ -2481,7 +2501,7 @@ public class ExpressionCodegen extends JetVisitor {
final DeclarationDescriptor descriptor = bindingContext.get(BindingContext.REFERENCE_TARGET, (JetSimpleNameExpression) call);
if (descriptor instanceof PropertyDescriptor) {
v.load(subjectLocal, subjectType);
- conditionValue = intermediateValueForProperty((PropertyDescriptor) descriptor, false, false);
+ conditionValue = intermediateValueForProperty((PropertyDescriptor) descriptor, false, false, false);
}
else {
throw new UnsupportedOperationException("unknown simple name resolve result: " + descriptor);
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/GenerationState.java b/compiler/backend/src/org/jetbrains/jet/codegen/GenerationState.java
index 8a4ec90771a..5c50f0bcf7b 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/GenerationState.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/GenerationState.java
@@ -28,10 +28,10 @@ public class GenerationState {
private final JetStandardLibrary standardLibrary;
private final IntrinsicMethods intrinsics;
- public GenerationState(Project project, boolean text) {
+ public GenerationState(Project project, ClassBuilderFactory builderFactory) {
this.project = project;
this.standardLibrary = JetStandardLibrary.getJetStandardLibrary(project);
- this.factory = new ClassFileFactory(project, text, this);
+ this.factory = new ClassFileFactory(builderFactory, this);
this.intrinsics = new IntrinsicMethods(project, standardLibrary);
}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java
index 6834d94c79c..98838271061 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/ImplementationBodyCodegen.java
@@ -95,7 +95,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
v.defineClass(Opcodes.V1_6,
Opcodes.ACC_PUBLIC | (isAbstract ? Opcodes.ACC_ABSTRACT : 0) | (isInterface
? Opcodes.ACC_INTERFACE
- : 0),
+ : 0/*Opcodes.ACC_SUPER*/),
jvmName(),
null,
superClass,
@@ -339,7 +339,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
iv.putfield(classname, fieldName, interfaceDesc);
}
- if (CodegenUtil.hasTypeInfoField(descriptor.getDefaultType()) && kind == OwnerKind.IMPLEMENTATION) {
+ if (state.getTypeMapper().hasTypeInfoField(descriptor.getDefaultType()) && kind == OwnerKind.IMPLEMENTATION) {
generateTypeInfoInitializer(frameMap.getFirstTypeParameter(), frameMap.getTypeParameterCount(), iv);
}
@@ -652,7 +652,7 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
if(propertyDescriptor.getOutType().isNullable())
type = JetTypeMapper.boxType(type);
codegen.gen(initializer, type);
- codegen.intermediateValueForProperty(propertyDescriptor, false, false).store(iv);
+ codegen.intermediateValueForProperty(propertyDescriptor, false, false, false).store(iv);
}
}
@@ -706,8 +706,8 @@ public class ImplementationBodyCodegen extends ClassBodyCodegen {
return;
JetType defaultType = descriptor.getDefaultType();
- if(CodegenUtil.hasTypeInfoField(defaultType)) {
- if(!CodegenUtil.hasDerivedTypeInfoField(defaultType, true)) {
+ if(state.getTypeMapper().hasTypeInfoField(defaultType)) {
+ if(!state.getTypeMapper().hasDerivedTypeInfoField(defaultType, true)) {
v.newField(myClass, Opcodes.ACC_PRIVATE, "$typeInfo", "Ljet/typeinfo/TypeInfo;", null, null);
MethodVisitor mv = v.newMethod(myClass, Opcodes.ACC_PUBLIC, "getTypeInfo", "()Ljet/typeinfo/TypeInfo;", null, null);
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/JetTypeMapper.java b/compiler/backend/src/org/jetbrains/jet/codegen/JetTypeMapper.java
index ad1521696de..66737f8de1e 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/JetTypeMapper.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/JetTypeMapper.java
@@ -186,6 +186,39 @@ public class JetTypeMapper {
return type;
}
+ public boolean hasTypeInfoField(JetType type) {
+ if(type.getConstructor().getParameters().size() > 0) {
+ if(!(bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, type.getConstructor().getDeclarationDescriptor()) instanceof PsiClass))
+ return true;
+ }
+
+ for (JetType jetType : type.getConstructor().getSupertypes()) {
+ if(hasTypeInfoField(jetType))
+ return true;
+ }
+
+ ClassDescriptor outerClassDescriptor = CodegenUtil.getOuterClassDescriptor(type.getConstructor().getDeclarationDescriptor());
+ if(outerClassDescriptor == null)
+ return false;
+
+ return hasTypeInfoField(outerClassDescriptor.getDefaultType());
+ }
+
+ public boolean hasDerivedTypeInfoField(JetType type, boolean exceptOwn) {
+ if(!exceptOwn) {
+ if(!CodegenUtil.isInterface(type))
+ if(hasTypeInfoField(type))
+ return true;
+ }
+
+ for (JetType jetType : type.getConstructor().getSupertypes()) {
+ if(hasDerivedTypeInfoField(jetType, false))
+ return true;
+ }
+
+ return false;
+ }
+
public String jvmName(ClassDescriptor jetClass, OwnerKind kind) {
PsiElement declaration = bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, jetClass);
if (declaration instanceof PsiClass) {
@@ -627,18 +660,29 @@ public class JetTypeMapper {
answer.append(p.getName()); // TODO: BOUND!
}
- public Method mapGetterSignature(PropertyDescriptor descriptor) {
+ public Method mapGetterSignature(PropertyDescriptor descriptor, OwnerKind kind) {
Type returnType = mapType(descriptor.getOutType());
- return new Method(PropertyCodegen.getterName(descriptor.getName()), returnType, new Type[0]);
+ if(kind != OwnerKind.TRAIT_IMPL)
+ return new Method(PropertyCodegen.getterName(descriptor.getName()), returnType, new Type[0]);
+ else {
+ ClassDescriptor containingDeclaration = (ClassDescriptor) descriptor.getContainingDeclaration();
+ return new Method(PropertyCodegen.getterName(descriptor.getName()), returnType, new Type[] { mapType(containingDeclaration.getDefaultType()) });
+ }
}
- public Method mapSetterSignature(PropertyDescriptor descriptor) {
+ public Method mapSetterSignature(PropertyDescriptor descriptor, OwnerKind kind) {
final JetType inType = descriptor.getInType();
if (inType == null) {
return null;
}
Type paramType = mapType(inType);
- return new Method(PropertyCodegen.setterName(descriptor.getName()), Type.VOID_TYPE, new Type[] { paramType });
+ if(kind != OwnerKind.TRAIT_IMPL) {
+ return new Method(PropertyCodegen.setterName(descriptor.getName()), Type.VOID_TYPE, new Type[] { paramType });
+ }
+ else {
+ ClassDescriptor containingDeclaration = (ClassDescriptor) descriptor.getContainingDeclaration();
+ return new Method(PropertyCodegen.setterName(descriptor.getName()), Type.VOID_TYPE, new Type[] { mapType(containingDeclaration.getDefaultType()), paramType });
+ }
}
private Method mapConstructorSignature(ConstructorDescriptor descriptor, List valueParameterTypes) {
@@ -654,9 +698,12 @@ public class JetTypeMapper {
valueParameterTypes.add(type);
}
- List typeParameters = classDescriptor.getTypeConstructor().getParameters();
- for (int n = typeParameters.size(); n > 0; n--) {
- parameterTypes.add(TYPE_TYPEINFO);
+ PsiElement psiElement = bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, classDescriptor);
+ if(!(psiElement instanceof PsiClass)) {
+ List typeParameters = classDescriptor.getTypeConstructor().getParameters();
+ for (int n = typeParameters.size(); n > 0; n--) {
+ parameterTypes.add(TYPE_TYPEINFO);
+ }
}
return new Method("", Type.VOID_TYPE, parameterTypes.toArray(new Type[parameterTypes.size()]));
@@ -667,7 +714,7 @@ public class JetTypeMapper {
final Method method = mapConstructorSignature(descriptor, valueParameterTypes);
String owner = jvmName(descriptor.getContainingDeclaration(), kind);
final CallableMethod result = new CallableMethod(owner, method, Opcodes.INVOKESPECIAL, valueParameterTypes);
- result.setAcceptsTypeArguments(true);
+ result.setAcceptsTypeArguments(!(bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, descriptor.getContainingDeclaration()) instanceof PsiClass));
return result;
}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/NamespaceCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/NamespaceCodegen.java
index a456c64b74a..2bef71dfaa6 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/NamespaceCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/NamespaceCodegen.java
@@ -32,7 +32,7 @@ public class NamespaceCodegen {
this.state = state;
v.defineClass(V1_6,
- ACC_PUBLIC,
+ ACC_PUBLIC/*|ACC_SUPER*/,
getJVMClassName(fqName),
null,
//"jet/lang/Namespace",
@@ -93,7 +93,7 @@ public class NamespaceCodegen {
if (initializer != null && !(initializer instanceof JetConstantExpression)) {
final PropertyDescriptor descriptor = (PropertyDescriptor) state.getBindingContext().get(BindingContext.VARIABLE, declaration);
codegen.genToJVMStack(initializer);
- codegen.intermediateValueForProperty(descriptor, true, false).store(new InstructionAdapter(mv));
+ codegen.intermediateValueForProperty(descriptor, true, false, false).store(new InstructionAdapter(mv));
}
}
}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/PropertyCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/PropertyCodegen.java
index be9733fac27..ddb3f9ed8fd 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/PropertyCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/PropertyCodegen.java
@@ -37,8 +37,9 @@ public class PropertyCodegen {
throw new UnsupportedOperationException("expect a property to have a property descriptor");
}
final PropertyDescriptor propertyDescriptor = (PropertyDescriptor) descriptor;
- if (kind == OwnerKind.NAMESPACE || kind == OwnerKind.IMPLEMENTATION) {
- generateBackingField(p, propertyDescriptor);
+ if (kind == OwnerKind.NAMESPACE || kind == OwnerKind.IMPLEMENTATION || kind ==OwnerKind.TRAIT_IMPL ) {
+ if(kind != OwnerKind.TRAIT_IMPL)
+ generateBackingField(p, propertyDescriptor);
generateGetter(p, propertyDescriptor);
generateSetter(p, propertyDescriptor);
}
@@ -81,7 +82,7 @@ public class PropertyCodegen {
final JetPropertyAccessor getter = p.getGetter();
if (getter != null) {
if (getter.getBodyExpression() != null) {
- functionCodegen.generateMethod(getter, state.getTypeMapper().mapGetterSignature(propertyDescriptor), propertyDescriptor.getGetter());
+ functionCodegen.generateMethod(getter, state.getTypeMapper().mapGetterSignature(propertyDescriptor, kind), propertyDescriptor.getGetter());
}
else if (!getter.hasModifier(JetTokens.PRIVATE_KEYWORD)) {
generateDefaultGetter(p, getter);
@@ -102,7 +103,7 @@ public class PropertyCodegen {
if (setter.getBodyExpression() != null) {
final PropertySetterDescriptor setterDescriptor = propertyDescriptor.getSetter();
assert setterDescriptor != null;
- functionCodegen.generateMethod(setter, state.getTypeMapper().mapSetterSignature(propertyDescriptor), setterDescriptor);
+ functionCodegen.generateMethod(setter, state.getTypeMapper().mapSetterSignature(propertyDescriptor, kind), setterDescriptor);
}
else if (!p.hasModifier(JetTokens.PRIVATE_KEYWORD)) {
generateDefaultSetter(p, setter);
@@ -120,6 +121,10 @@ public class PropertyCodegen {
}
public void generateDefaultGetter(PropertyDescriptor propertyDescriptor, int flags, PsiElement origin) {
+ if (kind == OwnerKind.TRAIT_IMPL) {
+ return;
+ }
+
if (kind == OwnerKind.NAMESPACE) {
flags |= Opcodes.ACC_STATIC;
}
@@ -129,7 +134,7 @@ public class PropertyCodegen {
if(isTrait && !(kind instanceof OwnerKind.DelegateKind))
flags |= Opcodes.ACC_ABSTRACT;
- final String signature = state.getTypeMapper().mapGetterSignature(propertyDescriptor).getDescriptor();
+ final String signature = state.getTypeMapper().mapGetterSignature(propertyDescriptor, kind).getDescriptor();
String getterName = getterName(propertyDescriptor.getName());
MethodVisitor mv = v.newMethod(origin, flags, getterName, signature, null, null);
if (!isTrait || kind instanceof OwnerKind.DelegateKind) {
@@ -162,6 +167,10 @@ public class PropertyCodegen {
}
public void generateDefaultSetter(PropertyDescriptor propertyDescriptor, int flags, PsiElement origin) {
+ if (kind == OwnerKind.TRAIT_IMPL) {
+ return;
+ }
+
if (kind == OwnerKind.NAMESPACE) {
flags |= Opcodes.ACC_STATIC;
}
@@ -171,7 +180,7 @@ public class PropertyCodegen {
if(isTrait && !(kind instanceof OwnerKind.DelegateKind))
flags |= Opcodes.ACC_ABSTRACT;
- final String signature = state.getTypeMapper().mapSetterSignature(propertyDescriptor).getDescriptor();
+ final String signature = state.getTypeMapper().mapSetterSignature(propertyDescriptor, kind).getDescriptor();
MethodVisitor mv = v.newMethod(origin, flags, setterName(propertyDescriptor.getName()), signature, null, null);
if (!isTrait || kind instanceof OwnerKind.DelegateKind) {
mv.visitCode();
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java b/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java
index 7938e019941..88badb3e2b8 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/StackValue.java
@@ -96,8 +96,8 @@ public abstract class StackValue {
return new InstanceField(type, owner, name);
}
- public static StackValue property(String name, String owner, Type type, boolean isStatic, boolean isInterface, Method getter, Method setter) {
- return new Property(name, owner, getter, setter, isStatic, isInterface, type);
+ public static StackValue property(String name, String owner, Type type, boolean isStatic, boolean isInterface, boolean isSuper, Method getter, Method setter) {
+ return new Property(name, owner, getter, setter, isStatic, isInterface, isSuper, type);
}
public static StackValue expression(Type type, JetExpression expression, ExpressionCodegen generator) {
@@ -623,8 +623,9 @@ public abstract class StackValue {
private final String owner;
private final boolean isStatic;
private final boolean isInterface;
+ private boolean isSuper;
- public Property(String name, String owner, Method getter, Method setter, boolean aStatic, boolean isInterface, Type type) {
+ public Property(String name, String owner, Method getter, Method setter, boolean aStatic, boolean isInterface, boolean isSuper, Type type) {
super(type);
this.name = name;
this.owner = owner;
@@ -632,26 +633,37 @@ public abstract class StackValue {
this.setter = setter;
isStatic = aStatic;
this.isInterface = isInterface;
+ this.isSuper = isSuper;
}
@Override
public void put(Type type, InstructionAdapter v) {
- if (getter == null) {
- v.visitFieldInsn(isStatic ? Opcodes.GETSTATIC : Opcodes.GETFIELD, owner, name, this.type.getDescriptor());
+ if(isSuper && isInterface) {
+ v.visitMethodInsn(Opcodes.INVOKESTATIC, owner + "$$TImpl", getter.getName(), getter.getDescriptor().replace("(","(L" + owner + ";"));
}
else {
- v.visitMethodInsn(isStatic ? Opcodes.INVOKESTATIC : isInterface ? Opcodes.INVOKEINTERFACE : Opcodes.INVOKEVIRTUAL, owner, getter.getName(), getter.getDescriptor());
+ if (getter == null) {
+ v.visitFieldInsn(isStatic ? Opcodes.GETSTATIC : Opcodes.GETFIELD, owner, name, this.type.getDescriptor());
+ }
+ else {
+ v.visitMethodInsn(isStatic ? Opcodes.INVOKESTATIC : isSuper ? Opcodes.INVOKESPECIAL : isInterface ? Opcodes.INVOKEINTERFACE : Opcodes.INVOKEVIRTUAL, owner, getter.getName(), getter.getDescriptor());
+ }
}
coerce(type, v);
}
@Override
public void store(InstructionAdapter v) {
- if (setter == null) {
- v.visitFieldInsn(isStatic ? Opcodes.PUTSTATIC : Opcodes.PUTFIELD, owner, name, this.type.getDescriptor());
+ if(isSuper && isInterface) {
+ v.visitMethodInsn(Opcodes.INVOKESTATIC, owner + "$$TImpl", setter.getName(), setter.getDescriptor().replace("(","(L" + owner + ";"));
}
else {
- v.visitMethodInsn(isStatic ? Opcodes.INVOKESTATIC : isInterface ? Opcodes.INVOKEINTERFACE : Opcodes.INVOKEVIRTUAL, owner, setter.getName(), setter.getDescriptor());
+ if (setter == null) {
+ v.visitFieldInsn(isStatic ? Opcodes.PUTSTATIC : Opcodes.PUTFIELD, owner, name, this.type.getDescriptor());
+ }
+ else {
+ v.visitMethodInsn(isStatic ? Opcodes.INVOKESTATIC : isSuper ? Opcodes.INVOKESPECIAL : isInterface ? Opcodes.INVOKEINTERFACE : Opcodes.INVOKEVIRTUAL, owner, setter.getName(), setter.getDescriptor());
+ }
}
}
diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/TraitImplBodyCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/TraitImplBodyCodegen.java
index 1f084b731dc..6856689b2de 100644
--- a/compiler/backend/src/org/jetbrains/jet/codegen/TraitImplBodyCodegen.java
+++ b/compiler/backend/src/org/jetbrains/jet/codegen/TraitImplBodyCodegen.java
@@ -46,7 +46,7 @@ public class TraitImplBodyCodegen extends ClassBodyCodegen {
@Override
protected void generateDeclaration() {
v.defineClass(Opcodes.V1_6,
- Opcodes.ACC_PUBLIC | Opcodes.ACC_FINAL,
+ Opcodes.ACC_PUBLIC | Opcodes.ACC_FINAL/*| Opcodes.ACC_SUPER*/,
jvmName(),
null,
"java/lang/Object",
diff --git a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java
index 607bad3bd4e..cd92630c416 100644
--- a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java
+++ b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java
@@ -4,10 +4,13 @@ import com.intellij.openapi.Disposable;
import com.intellij.openapi.application.PathManager;
import com.intellij.openapi.util.Disposer;
import com.intellij.openapi.util.io.FileUtil;
+import com.intellij.openapi.util.text.StringUtil;
import com.intellij.openapi.vfs.VirtualFile;
+import com.intellij.util.Function;
import com.intellij.util.Processor;
import jet.modules.IModuleBuilder;
import jet.modules.IModuleSetBuilder;
+import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.JetCoreEnvironment;
import org.jetbrains.jet.codegen.ClassFileFactory;
import org.jetbrains.jet.codegen.GeneratedClassLoader;
@@ -40,7 +43,7 @@ public class CompileEnvironment {
myEnvironment = new JetCoreEnvironment(myRootDisposable);
}
- public void setMyErrorStream(PrintStream errorStream) {
+ public void setErrorStream(PrintStream errorStream) {
myErrorStream = errorStream;
}
@@ -86,7 +89,35 @@ public class CompileEnvironment {
myEnvironment.addToClasspath(rtJarPath);
}
- public static File findActiveRtJar() {
+ public static File findRtJar(boolean failOnError) {
+ String javaHome = System.getenv("JAVA_HOME");
+ File rtJar;
+ if (javaHome == null) {
+ rtJar = findActiveRtJar(failOnError);
+
+ if(rtJar == null && failOnError) {
+ throw new CompileEnvironmentException("JAVA_HOME environment variable needs to be defined");
+ }
+ }
+ else {
+ rtJar = findRtJar(javaHome);
+ }
+
+ if ((rtJar == null || !rtJar.exists()) && failOnError) {
+ throw new CompileEnvironmentException("No rt.jar found under JAVA_HOME=" + javaHome);
+ }
+ return rtJar;
+ }
+
+ private static File findRtJar(String javaHome) {
+ File rtJar = new File(javaHome, "jre/lib/rt.jar");
+ if (rtJar.exists()) {
+ return rtJar;
+ }
+ return null;
+ }
+
+ public static File findActiveRtJar(boolean failOnError) {
ClassLoader systemClassLoader = ClassLoader.getSystemClassLoader();
if (systemClassLoader instanceof URLClassLoader) {
URLClassLoader loader = (URLClassLoader) systemClassLoader;
@@ -100,6 +131,17 @@ public class CompileEnvironment {
}
}
}
+ if (failOnError) {
+ throw new CompileEnvironmentException("Could not find rt.jar in system class loader: " + StringUtil.join(loader.getURLs(), new Function() {
+ @Override
+ public String fun(URL url) {
+ return url.toString();
+ }
+ }, ", "));
+ }
+ }
+ else if (failOnError) {
+ throw new CompileEnvironmentException("System class loader is not an URLClassLoader: " + systemClassLoader);
}
return null;
}
@@ -113,7 +155,12 @@ public class CompileEnvironment {
final String directory = new File(moduleFile).getParent();
for (IModuleBuilder moduleBuilder : moduleSetBuilder.getModules()) {
ClassFileFactory moduleFactory = compileModule(moduleBuilder, directory);
- writeToJar(moduleFactory, new File(directory, moduleBuilder.getModuleName() + ".jar").getPath(), null, true);
+ final String path = new File(directory, moduleBuilder.getModuleName() + ".jar").getPath();
+ try {
+ writeToJar(moduleFactory, new FileOutputStream(path), null, true);
+ } catch (FileNotFoundException e) {
+ throw new CompileEnvironmentException("Invalid jar path " + path, e);
+ }
}
}
@@ -191,7 +238,7 @@ public class CompileEnvironment {
return new File(PathManager.getResourceRoot(CompileEnvironment.class, "/org/jetbrains/jet/compiler/CompileEnvironment.class")).getParentFile().getParentFile().getParent();
}
- public static void writeToJar(ClassFileFactory factory, String jar, String mainClass, boolean includeRuntime) {
+ public static void writeToJar(ClassFileFactory factory, final OutputStream fos, @Nullable String mainClass, boolean includeRuntime) {
try {
Manifest manifest = new Manifest();
final Attributes mainAttributes = manifest.getMainAttributes();
@@ -200,7 +247,6 @@ public class CompileEnvironment {
if (mainClass != null) {
mainAttributes.putValue("Main-Class", mainClass);
}
- FileOutputStream fos = new FileOutputStream(jar);
JarOutputStream stream = new JarOutputStream(fos, manifest);
try {
for (String file : factory.files()) {
@@ -286,7 +332,11 @@ public class CompileEnvironment {
ClassFileFactory factory = session.generate();
if (jar != null) {
- writeToJar(factory, jar, mainClass, true);
+ try {
+ writeToJar(factory, new FileOutputStream(jar), mainClass, true);
+ } catch (FileNotFoundException e) {
+ throw new CompileEnvironmentException("Invalid jar path " + jar, e);
+ }
}
else if (outputDir != null) {
writeToOutputDirectory(factory, outputDir);
diff --git a/compiler/backend/src/org/jetbrains/jet/compiler/CompileSession.java b/compiler/backend/src/org/jetbrains/jet/compiler/CompileSession.java
index c166906ed87..7f643b90d14 100644
--- a/compiler/backend/src/org/jetbrains/jet/compiler/CompileSession.java
+++ b/compiler/backend/src/org/jetbrains/jet/compiler/CompileSession.java
@@ -5,6 +5,7 @@ import com.intellij.openapi.vfs.VirtualFile;
import com.intellij.psi.PsiFile;
import com.intellij.psi.PsiManager;
import org.jetbrains.jet.JetCoreEnvironment;
+import org.jetbrains.jet.codegen.ClassBuilderFactory;
import org.jetbrains.jet.codegen.ClassFileFactory;
import org.jetbrains.jet.codegen.GenerationState;
import org.jetbrains.jet.lang.cfg.pseudocode.JetControlFlowDataTraceFactory;
@@ -93,7 +94,7 @@ public class CompileSession {
}
public ClassFileFactory generate() {
- GenerationState generationState = new GenerationState(myEnvironment.getProject(), false);
+ GenerationState generationState = new GenerationState(myEnvironment.getProject(), ClassBuilderFactory.BINARIES);
generationState.compileCorrectNamespaces(myBindingContext, mySourceFileNamespaces);
return generationState.getFactory();
}
diff --git a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java
index 22a1f6bc346..3de270c6583 100644
--- a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java
+++ b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java
@@ -5,8 +5,6 @@ import com.sampullara.cli.Argument;
import org.jetbrains.jet.compiler.CompileEnvironment;
import org.jetbrains.jet.compiler.CompileEnvironmentException;
-import java.io.File;
-
/**
* @author yole
* @author alex.tkachman
@@ -38,11 +36,8 @@ public class KotlinCompiler {
CompileEnvironment environment = new CompileEnvironment();
- File rtJar = initJdk();
- if (rtJar == null) return;
-
try {
- environment.setJavaRuntime(rtJar);
+ environment.setJavaRuntime(CompileEnvironment.findRtJar(true));
if (!environment.initializeKotlinRuntime()) {
System.out.println("No runtime library found");
return;
@@ -60,33 +55,4 @@ public class KotlinCompiler {
}
}
- private static File initJdk() {
- String javaHome = System.getenv("JAVA_HOME");
- File rtJar;
- if (javaHome == null) {
- rtJar = CompileEnvironment.findActiveRtJar();
-
- if(rtJar == null) {
- System.out.println("JAVA_HOME environment variable needs to be defined");
- return null;
- }
- }
- else {
- rtJar = findRtJar(javaHome);
- }
-
- if (rtJar == null || !rtJar.exists()) {
- System.out.print("No rt.jar found under JAVA_HOME=" + javaHome);
- return null;
- }
- return rtJar;
- }
-
- private static File findRtJar(String javaHome) {
- File rtJar = new File(javaHome, "jre/lib/rt.jar");
- if (rtJar.exists()) {
- return rtJar;
- }
- return null;
- }
}
diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/diagnostics/Errors.java b/compiler/frontend/src/org/jetbrains/jet/lang/diagnostics/Errors.java
index 8a9ccc2a60e..52b22dbcb3c 100644
--- a/compiler/frontend/src/org/jetbrains/jet/lang/diagnostics/Errors.java
+++ b/compiler/frontend/src/org/jetbrains/jet/lang/diagnostics/Errors.java
@@ -240,6 +240,8 @@ public interface Errors {
SimpleDiagnosticFactory SUPERTYPE_APPEARS_TWICE = SimpleDiagnosticFactory.create(ERROR, "A supertype appears twice");
SimpleDiagnosticFactory FINAL_SUPERTYPE = SimpleDiagnosticFactory.create(ERROR, "This type is final, so it cannot be inherited from");
+ ParameterizedDiagnosticFactory1 ILLEGAL_SELECTOR = ParameterizedDiagnosticFactory1.create(ERROR, "Expression ''{0}'' cannot be a selector (occur after a dot)");
+
SimpleDiagnosticFactory REF_PARAMETER_WITH_VAL_OR_VAR = SimpleDiagnosticFactory.create(ERROR, "'val' and 'var' are not allowed on ref-parameters");
SimpleDiagnosticFactory VALUE_PARAMETER_WITH_NO_TYPE_ANNOTATION = SimpleDiagnosticFactory.create(ERROR, "A type annotation is required on a value parameter");
SimpleDiagnosticFactory BREAK_OR_CONTINUE_OUTSIDE_A_LOOP = SimpleDiagnosticFactory.create(ERROR, "'break' and 'continue' are only allowed inside a loop");
diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/psi/JetCallExpression.java b/compiler/frontend/src/org/jetbrains/jet/lang/psi/JetCallExpression.java
index 79eef89077e..987a7481529 100644
--- a/compiler/frontend/src/org/jetbrains/jet/lang/psi/JetCallExpression.java
+++ b/compiler/frontend/src/org/jetbrains/jet/lang/psi/JetCallExpression.java
@@ -1,9 +1,12 @@
package org.jetbrains.jet.lang.psi;
import com.intellij.lang.ASTNode;
+import com.intellij.psi.PsiElement;
+import com.intellij.util.SmartList;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.jetbrains.jet.JetNodeTypes;
+import org.jetbrains.jet.lexer.JetTokens;
import java.util.Collections;
import java.util.List;
@@ -46,7 +49,32 @@ public class JetCallExpression extends JetExpression implements JetCallElement {
@Override
@NotNull
public List getFunctionLiteralArguments() {
- return findChildrenByType(JetNodeTypes.FUNCTION_LITERAL_EXPRESSION);
+ JetExpression calleeExpression = getCalleeExpression();
+ ASTNode node;
+ if (calleeExpression instanceof JetFunctionLiteralExpression) {
+ node = calleeExpression.getNode().getTreeNext();
+ }
+ else {
+ node = getNode().getFirstChildNode();
+ }
+ List result = new SmartList();
+ while (node != null) {
+ PsiElement psi = node.getPsi();
+ if (psi instanceof JetFunctionLiteralExpression) {
+ result.add((JetFunctionLiteralExpression) psi);
+ }
+ else if (psi instanceof JetPrefixExpression) {
+ JetPrefixExpression prefixExpression = (JetPrefixExpression) psi;
+ if (JetTokens.LABELS.contains(prefixExpression.getOperationSign().getReferencedNameElementType())) {
+ JetExpression labeledExpression = prefixExpression.getBaseExpression();
+ if (labeledExpression instanceof JetFunctionLiteralExpression) {
+ result.add(labeledExpression);
+ }
+ }
+ }
+ node = node.getTreeNext();
+ }
+ return result;
}
@Override
diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallResolver.java b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallResolver.java
index 231bf7a3e0f..86fa17c15b9 100644
--- a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallResolver.java
+++ b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/CallResolver.java
@@ -177,7 +177,7 @@ public class CallResolver {
else if (calleeExpression != null) {
// Here we handle the case where the callee expression must be something of type function, e.g. (foo.bar())(1, 2)
ExpressionTypingServices typingServices = new ExpressionTypingServices(semanticServices, trace);
- JetType calleeType = typingServices.safeGetType(scope, calleeExpression, NO_EXPECTED_TYPE);// We are actually expecting a function, but there seems to be no easy way of expressing this
+ JetType calleeType = typingServices.safeGetType(scope, calleeExpression, NO_EXPECTED_TYPE); // We are actually expecting a function, but there seems to be no easy way of expressing this
if (!JetStandardClasses.isFunctionType(calleeType)) {
checkTypesWithNoCallee(trace, scope, call);
@@ -187,13 +187,17 @@ public class CallResolver {
return null;
}
- FunctionDescriptorImpl functionDescriptor = new FunctionDescriptorImpl(scope.getContainingDeclaration(), Collections.emptyList(), "for expression " + calleeExpression.getText());
+ FunctionDescriptorImpl functionDescriptor = new FunctionDescriptorImpl(scope.getContainingDeclaration(), Collections.emptyList(), "[for expression " + calleeExpression.getText() + "]");
FunctionDescriptorUtil.initializeFromFunctionType(functionDescriptor, calleeType);
ResolvedCallImpl resolvedCall = ResolvedCallImpl.create(functionDescriptor);
+ resolvedCall.setReceiverArgument(call.getExplicitReceiver());
prioritizedTasks = Collections.singletonList(new ResolutionTask(
Collections.singleton(resolvedCall), call, dataFlowInfo));
- functionReference = new JetReferenceExpression(calleeExpression.getNode()) {
- };
+
+ // strictly speaking, this is a hack:
+ // we need to pass a reference, but there's no reference in the PSI,
+ // so we wrap what we have into a fake reference and pass it on (unwrap on the other end)
+ functionReference = new JetFakeReference(calleeExpression);
}
else {
checkTypesWithNoCallee(trace, scope, call);
@@ -238,9 +242,17 @@ public class CallResolver {
// trace.record(REFERENCE_TARGET, reference, variableAsFunctionDescriptor.getVariableDescriptor());
// }
// else {
- trace.record(REFERENCE_TARGET, reference, descriptor);
// }
- trace.record(RESOLVED_CALL, reference, resolvedCall);
+ if (reference instanceof JetFakeReference) {
+ // This means that the callable being invoked was represented by an expression
+ // rather than a reference expression
+ JetFakeReference fakeReference = (JetFakeReference) reference;
+ trace.record(RESOLVED_CALL, fakeReference.getActualElement(), resolvedCall);
+ }
+ else {
+ trace.record(RESOLVED_CALL, reference, resolvedCall);
+ trace.record(REFERENCE_TARGET, reference, descriptor);
+ }
}
@Override
@@ -471,23 +483,18 @@ public class CallResolver {
else {
// Explicit type arguments passed
- for (JetTypeProjection typeArgument : jetTypeArguments) {
- if (typeArgument.getProjectionKind() != JetProjectionKind.NONE) {
-// temporaryTrace.getErrorHandler().genericError(typeArgument.getNode(), "Projections are not allowed on type parameters for methods"); // TODO : better positioning
- temporaryTrace.report(PROJECTION_ON_NON_CLASS_TYPE_ARGUMENT.on(typeArgument));
+ List typeArguments = new ArrayList();
+ for (JetTypeProjection projection : jetTypeArguments) {
+ if (projection.getProjectionKind() != JetProjectionKind.NONE) {
+ temporaryTrace.report(PROJECTION_ON_NON_CLASS_TYPE_ARGUMENT.on(projection));
+ }
+ JetTypeReference typeReference = projection.getTypeReference();
+ if (typeReference != null) {
+ typeArguments.add(new TypeResolver(semanticServices, temporaryTrace, true).resolveType(scope, typeReference));
}
}
-
int expectedTypeArgumentCount = candidate.getTypeParameters().size();
if (expectedTypeArgumentCount == jetTypeArguments.size()) {
- List typeArguments = new ArrayList();
- for (JetTypeProjection projection : jetTypeArguments) {
- // TODO : check that there's no projection
- JetTypeReference typeReference = projection.getTypeReference();
- if (typeReference != null) {
- typeArguments.add(new TypeResolver(semanticServices, temporaryTrace, true).resolveType(scope, typeReference));
- }
- }
checkGenericBoundsInAFunctionCall(jetTypeArguments, typeArguments, candidate, temporaryTrace);
diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/JetFakeReference.java b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/JetFakeReference.java
new file mode 100644
index 00000000000..73d372d2868
--- /dev/null
+++ b/compiler/frontend/src/org/jetbrains/jet/lang/resolve/calls/JetFakeReference.java
@@ -0,0 +1,24 @@
+package org.jetbrains.jet.lang.resolve.calls;
+
+import org.jetbrains.annotations.NotNull;
+import org.jetbrains.jet.lang.psi.JetElement;
+import org.jetbrains.jet.lang.psi.JetReferenceExpression;
+
+/**
+ *
+ * This class is used to wrap an expression that occurs in a reference position, such as a function literal, into a reference expression
+ *
+ * @author abreslav
+ */
+public class JetFakeReference extends JetReferenceExpression {
+ private final JetElement actualElement;
+
+ public JetFakeReference(@NotNull JetElement actualElement) {
+ super(actualElement.getNode());
+ this.actualElement = actualElement;
+ }
+
+ public JetElement getActualElement() {
+ return actualElement;
+ }
+}
diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/BasicExpressionTypingVisitor.java b/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/BasicExpressionTypingVisitor.java
index 2255ebe885d..f00ecc3cce7 100644
--- a/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/BasicExpressionTypingVisitor.java
+++ b/compiler/frontend/src/org/jetbrains/jet/lang/types/expressions/BasicExpressionTypingVisitor.java
@@ -525,8 +525,7 @@ public class BasicExpressionTypingVisitor extends ExpressionTypingVisitor {
}
}
else {
- // TODO : not a simple name -> resolve in scope, expect property type or a function type
- context.trace.report(UNSUPPORTED.on(selectorExpression, "getSelectorReturnType"));
+ context.trace.report(ILLEGAL_SELECTOR.on(selectorExpression, selectorExpression.getText()));
}
return null;
}
diff --git a/compiler/testData/checkerWithErrorTypes/quick/FunctionCalleeExpressions.jet b/compiler/testData/checkerWithErrorTypes/quick/FunctionCalleeExpressions.jet
index 581493762d3..15acd8ec22c 100644
--- a/compiler/testData/checkerWithErrorTypes/quick/FunctionCalleeExpressions.jet
+++ b/compiler/testData/checkerWithErrorTypes/quick/FunctionCalleeExpressions.jet
@@ -47,4 +47,36 @@ fun main(args : Array) {
1()
1{}
1(){}
+}
+
+fun f() : fun Int.() : Unit = {}
+
+fun main1(args : Array) {
+ 1.{Int.() => 1}();
+ {1}()
+ {(x : Int) => x}(1)
+ 1.{Int.(x : Int) => x}(1)
+ @l{1}()
+ 1.({Int.() => 1})()
+ 1.(f())()
+ 1.if(true){f()}else{f()}()
+ 1.if(true){Int.() => 1}else{f()}()
+ 1.if(true){Int.() => 1}else{Int.() => 1}()
+
+ 1."sdf"()
+
+ 1."sdf"
+ 1.{}
+ 1.if (true) {}
+}
+
+fun test() {
+ {(x : Int) => 1}()
+ {Int.() => 1}()
+ "sd".{Int.() => 1}()
+ val i : Int? = null
+ i.{Int.() => 1}()
+ {}()
+ 1?.{Int.() => 1}()
+ 1.{}()
}
\ No newline at end of file
diff --git a/compiler/testData/checkerWithErrorTypes/quick/ProjectionOnFunctionArgumentErrror.jet b/compiler/testData/checkerWithErrorTypes/quick/ProjectionOnFunctionArgumentErrror.jet
new file mode 100644
index 00000000000..d509e83f5ad
--- /dev/null
+++ b/compiler/testData/checkerWithErrorTypes/quick/ProjectionOnFunctionArgumentErrror.jet
@@ -0,0 +1,4 @@
+fun test() {
+ fun foo(){}
+ foo<in Int>()
+}
\ No newline at end of file
diff --git a/compiler/testData/checkerWithErrorTypes/quick/regressions/kt439.jet b/compiler/testData/checkerWithErrorTypes/quick/regressions/kt439.jet
new file mode 100644
index 00000000000..49bd3b8b550
--- /dev/null
+++ b/compiler/testData/checkerWithErrorTypes/quick/regressions/kt439.jet
@@ -0,0 +1,7 @@
+// KT-439 Support labeled function lliterals in call arguments
+
+inline fun run1(body : fun() : T) : T = body()
+
+fun main1(args : Array) {
+ run1 @l{ 1 } // should not be an error
+}
diff --git a/compiler/testData/codegen/super/basicmethod.jet b/compiler/testData/codegen/super/basicmethod.jet
new file mode 100644
index 00000000000..ab735673036
--- /dev/null
+++ b/compiler/testData/codegen/super/basicmethod.jet
@@ -0,0 +1,13 @@
+class N() : java.util.ArrayList() {
+ override fun add(el: String) : Boolean {
+ super.add(el)
+ return super.add(el + el)
+ }
+}
+
+fun box(): String {
+ val n = N()
+ n.add("239")
+ if (n.get(0) == "239" && n.get(1) == "239239") return "OK";
+ return "fail";
+}
\ No newline at end of file
diff --git a/compiler/testData/codegen/super/basicproperty.jet b/compiler/testData/codegen/super/basicproperty.jet
new file mode 100644
index 00000000000..196ed3f40b0
--- /dev/null
+++ b/compiler/testData/codegen/super/basicproperty.jet
@@ -0,0 +1,22 @@
+open class M() {
+ open var b: Int = 0
+}
+
+class N() : M() {
+ val a : Int
+ get() {
+ super.b = super.b + 1
+ return super.b + 1
+ }
+ override var b: Int = a + 1
+
+ val superb : Int
+ get() = super.b
+}
+
+fun box(): String {
+ val n = N()
+ System.out?.println("a: " + n.a + " b: " + n.b + " superb: " + n.superb)
+ if (n.b == 3 && n.a == 4 && n.superb == 3) return "OK";
+ return "fail";
+}
\ No newline at end of file
diff --git a/compiler/testData/codegen/super/traitproperty.jet b/compiler/testData/codegen/super/traitproperty.jet
new file mode 100644
index 00000000000..962f71c5dc9
--- /dev/null
+++ b/compiler/testData/codegen/super/traitproperty.jet
@@ -0,0 +1,29 @@
+trait M {
+ var backingB : Int
+ var b : Int
+ get() = backingB
+ set(value: Int) {
+ backingB = value
+ }
+}
+
+class N() : M {
+ override var backingB : Int = 0
+
+ val a : Int
+ get() {
+ super.b = super.b + 1
+ return super.b + 1
+ }
+ override var b: Int = a + 1
+
+ val superb : Int
+ get() = super.b
+}
+
+fun box(): String {
+ val n = N()
+ System.out?.println("a: " + n.a + " b: " + n.b + " superb: " + n.superb)
+ if (n.b == 3 && n.a == 4 && n.superb == 3) return "OK";
+ return "fail";
+}
\ No newline at end of file
diff --git a/compiler/tests/org/jetbrains/jet/JetTestCaseBuilder.java b/compiler/tests/org/jetbrains/jet/JetTestCaseBuilder.java
index 0698cdbac4b..0fcc6c82e8c 100644
--- a/compiler/tests/org/jetbrains/jet/JetTestCaseBuilder.java
+++ b/compiler/tests/org/jetbrains/jet/JetTestCaseBuilder.java
@@ -16,7 +16,7 @@ import java.util.List;
* @author abreslav
*/
public abstract class JetTestCaseBuilder {
- private static FilenameFilter emptyFilter = new FilenameFilter() {
+ public static FilenameFilter emptyFilter = new FilenameFilter() {
@Override
public boolean accept(File file, String name) {
return true;
@@ -43,6 +43,11 @@ public abstract class JetTestCaseBuilder {
@NotNull
public static TestSuite suiteForDirectory(String baseDataDir, @NotNull final String dataPath, boolean recursive, final FilenameFilter filter, @NotNull NamedTestFactory factory) {
TestSuite suite = new TestSuite(dataPath);
+ appendTestsInDirectory(baseDataDir, dataPath, recursive, filter, factory, suite);
+ return suite;
+ }
+
+ public static void appendTestsInDirectory(String baseDataDir, String dataPath, boolean recursive, final FilenameFilter filter, NamedTestFactory factory, TestSuite suite) {
final String extensionJet = ".jet";
final String extensionKt = ".kt";
final FilenameFilter extensionFilter = new FilenameFilter() {
@@ -76,7 +81,7 @@ public abstract class JetTestCaseBuilder {
List subdirs = Arrays.asList(files);
Collections.sort(subdirs);
for (File subdir : subdirs) {
- suite.addTest(suiteForDirectory(baseDataDir, dataPath + "/" + subdir.getName(), recursive, filter, factory));
+ appendTestsInDirectory(baseDataDir, dataPath + "/" + subdir.getName(), recursive, filter, factory, suite);
}
}
List files = Arrays.asList(dir.listFiles(resultFilter));
@@ -87,6 +92,5 @@ public abstract class JetTestCaseBuilder {
String extension = fileName.endsWith(extensionJet) ? extensionJet : extensionKt;
suite.addTest(factory.createTest(dataPath, fileName.substring(0, fileName.length() - extension.length())));
}
- return suite;
}
}
diff --git a/compiler/tests/org/jetbrains/jet/codegen/CodegenTestCase.java b/compiler/tests/org/jetbrains/jet/codegen/CodegenTestCase.java
index e6ec1009270..4bff106d65b 100644
--- a/compiler/tests/org/jetbrains/jet/codegen/CodegenTestCase.java
+++ b/compiler/tests/org/jetbrains/jet/codegen/CodegenTestCase.java
@@ -98,7 +98,7 @@ public abstract class CodegenTestCase extends JetLiteFixture {
}
protected String generateToText() {
- GenerationState state = new GenerationState(getProject(), true);
+ GenerationState state = new GenerationState(getProject(), ClassBuilderFactory.TEXT);
AnalyzingUtils.checkForSyntacticErrors(myFile);
state.compile(myFile);
@@ -152,7 +152,7 @@ public abstract class CodegenTestCase extends JetLiteFixture {
protected ClassFileFactory generateClassesInFile() {
try {
- GenerationState state = new GenerationState(getProject(), false);
+ GenerationState state = new GenerationState(getProject(), ClassBuilderFactory.BINARIES);
AnalyzingUtils.checkForSyntacticErrors(myFile);
state.compile(myFile);
diff --git a/compiler/tests/org/jetbrains/jet/codegen/FunctionGenTest.java b/compiler/tests/org/jetbrains/jet/codegen/FunctionGenTest.java
index 1bbef086700..0a3a3950b4c 100644
--- a/compiler/tests/org/jetbrains/jet/codegen/FunctionGenTest.java
+++ b/compiler/tests/org/jetbrains/jet/codegen/FunctionGenTest.java
@@ -80,4 +80,55 @@ public class FunctionGenTest extends CodegenTestCase {
public void testKt395 () {
blackBoxFile("regressions/kt395.jet");
}
+/*
+ public void testFunction () throws InvocationTargetException, IllegalAccessException {
+ loadText("fun Any.foo() : fun(): String {\n" +
+ " return { \"239\" + this }\n" +
+ "}\n" +
+ "fun box() : String {\n" +
+ " return if((10.foo())() == \"23910\") \"OK\" else \"fail\"" +
+ "}" +
+ "");
+ System.out.println(generateToText());
+ Method foo = generateFunction();
+ assertTrue((Boolean) foo.invoke(null, "lala"));
+ assertFalse((Boolean) foo.invoke(null, "mama"));
+ }
+
+fun Any.foo() : fun() : Unit {
+ return {}
+}
+
+fun Any.foo1() : fun(i : Int) : Unit {
+ return {}
+}
+
+fun foo2() : fun(i : fun()) : Unit {
+ return {}
+}
+
+fun fooT1(t : T) : fun() : T {
+ return {t}
+}
+
+fun fooT2() : fun(t : T) : T {
+ return {it}
+}
+
+fun main(args : Array) {
+ args.foo()()
+
+ args.foo1()(1)
+
+ foo2()({})
+ (foo2()){}
+
+ val a = fooT1(1)()
+ a : Int
+
+ val b = fooT2()(1)
+ b : Int
+ fooT2()(1) // : Any?
+}
+ */
}
diff --git a/compiler/tests/org/jetbrains/jet/codegen/SuperGenTest.java b/compiler/tests/org/jetbrains/jet/codegen/SuperGenTest.java
new file mode 100644
index 00000000000..45bf1a6c19b
--- /dev/null
+++ b/compiler/tests/org/jetbrains/jet/codegen/SuperGenTest.java
@@ -0,0 +1,18 @@
+package org.jetbrains.jet.codegen;
+
+public class SuperGenTest extends CodegenTestCase {
+ public void testBasicProperty () {
+ blackBoxFile("/super/basicproperty.jet");
+ System.out.println(generateToText());
+ }
+
+ public void testTraitProperty () {
+ blackBoxFile("/super/traitproperty.jet");
+ System.out.println(generateToText());
+ }
+
+ public void testBasicMethod () {
+ blackBoxFile("/super/basicmethod.jet");
+ System.out.println(generateToText());
+ }
+}
diff --git a/compiler/tests/org/jetbrains/jet/compiler/CompileEnvironmentTest.java b/compiler/tests/org/jetbrains/jet/compiler/CompileEnvironmentTest.java
index de0a6ecf2fa..4b01efe9efd 100644
--- a/compiler/tests/org/jetbrains/jet/compiler/CompileEnvironmentTest.java
+++ b/compiler/tests/org/jetbrains/jet/compiler/CompileEnvironmentTest.java
@@ -6,6 +6,15 @@ import junit.framework.TestCase;
import org.jetbrains.jet.codegen.ClassFileFactory;
import org.jetbrains.jet.parsing.JetParsingTest;
+import java.io.ByteArrayInputStream;
+import java.io.ByteArrayOutputStream;
+import java.io.File;
+import java.io.IOException;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.jar.JarEntry;
+import java.util.jar.JarInputStream;
+
/**
* @author yole
*/
@@ -23,8 +32,9 @@ public class CompileEnvironmentTest extends TestCase {
super.tearDown();
}
- public void testSmoke() {
- environment.setJavaRuntime(CompileEnvironment.findActiveRtJar());
+ public void testSmoke() throws IOException {
+ final File activeRtJar = CompileEnvironment.findRtJar(true);
+ environment.setJavaRuntime(activeRtJar);
environment.initializeKotlinRuntime();
final String testDataDir = JetParsingTest.getTestDataDir() + "/compiler/smoke/";
final IModuleSetBuilder setBuilder = environment.loadModuleScript(testDataDir + "Smoke.kts");
@@ -33,5 +43,23 @@ public class CompileEnvironmentTest extends TestCase {
final ClassFileFactory factory = environment.compileModule(moduleBuilder, testDataDir);
assertNotNull(factory);
assertNotNull(factory.asBytes("Smoke/namespace.class"));
+
+ ByteArrayOutputStream baos = new ByteArrayOutputStream();
+ CompileEnvironment.writeToJar(factory, baos, null, false);
+ JarInputStream is = new JarInputStream(new ByteArrayInputStream(baos.toByteArray()));
+ final List entries = listEntries(is);
+ assertTrue(entries.contains("Smoke/namespace.class"));
+ }
+
+ private List listEntries(JarInputStream is) throws IOException {
+ List entries = new ArrayList();
+ while (true) {
+ final JarEntry jarEntry = is.getNextJarEntry();
+ if (jarEntry == null) {
+ break;
+ }
+ entries.add(jarEntry.getName());
+ }
+ return entries;
}
}
diff --git a/examples/src/netty/netty.kt b/examples/src/netty/netty.kt
new file mode 100644
index 00000000000..4068072d7ec
--- /dev/null
+++ b/examples/src/netty/netty.kt
@@ -0,0 +1,141 @@
+import java.util.concurrent.Executors
+import java.net.InetSocketAddress
+import java.net.URLDecoder
+import java.io.*
+
+import org.jboss.netty.bootstrap.ServerBootstrap
+import org.jboss.netty.channel.socket.nio.NioServerSocketChannelFactory
+import org.jboss.netty.channel.*
+import org.jboss.netty.handler.codec.http.*
+import org.jboss.netty.handler.stream.ChunkedWriteHandler
+import org.jboss.netty.handler.codec.frame.TooLongFrameException
+import org.jboss.netty.buffer.ChannelBuffers
+import org.jboss.netty.util.CharsetUtil
+import org.jboss.netty.handler.codec.http.HttpResponseStatus.*
+
+import netty.*
+import jlstring.*
+
+namespace jlstring {
+ fun String.replace(c: Char, by: Char) : String = (this as java.lang.String).replace(c, by) as String
+
+ fun String.contains(s: String) : Boolean = (this as java.lang.String).contains(s as java.lang.CharSequence)
+
+ fun java.lang.String.plus(s: Any?) : String = (this as String) + s.toString()
+}
+
+namespace netty {
+ fun ChannelPipeline.with(op: fun ChannelPipeline.() ) : ChannelPipeline {
+ this.op()
+ return this
+ }
+
+ fun HttpResponse.set(header: String, value: Any?) : Unit {
+ setHeader(header, value)
+ }
+
+ fun HttpResponse.setContent(content: Any?) : Unit {
+ setContent(ChannelBuffers.copiedBuffer(content.toString() as java.lang.String, CharsetUtil.UTF_8))
+ }
+
+ fun ChannelHandlerContext.sendError(status: HttpResponseStatus?) {
+ val response = DefaultHttpResponse(HttpVersion.HTTP_1_1, status)
+ response["Content-Type"] = "text/plain; charset=UTF-8"
+ response.setContent("Failure: " + status.toString() + "\r\n")
+
+ // Close the connection as soon as the error message is sent.
+ this.getChannel()?.write(response)?.addListener(ChannelFutureListener.CLOSE)
+ }
+
+ fun String.decodeURI(encoding : String) : String? {
+ try {
+ return URLDecoder.decode(this, encoding)
+ }
+ catch (e : UnsupportedEncodingException) {
+ return null
+ }
+ }
+
+ fun String.sanitizeUri() : String? {
+ val path = decodeURI("UTF-8") ?: decodeURI("ISO-8859-1")
+ if (path == null)
+ throw Error()
+
+ val localizedPath : String = path.replace('/', File.separatorChar)
+ return if (localizedPath.contains(File.separator + ".") ||
+ localizedPath.contains("." + File.separator) ||
+ localizedPath.startsWith(".") || endsWith("."))
+ null
+ else
+ localizedPath
+ }
+
+ class StandardPipelineFactory(val config: fun ChannelPipeline.():Unit) : ChannelPipelineFactory {
+ override fun getPipeline() : ChannelPipeline {
+ val pipeline = DefaultChannelPipeline().with {
+ addLast("decoder", HttpRequestDecoder())
+ addLast("aggregator", HttpChunkAggregator(65536))
+ addLast("encoder", HttpResponseEncoder())
+ addLast("chunkedWriter", ChunkedWriteHandler())
+ }
+ pipeline.config () // can not move it inside with{} because of codegen bug
+ return pipeline
+ }
+ }
+
+ fun ServerBootstrap.configPipeline(config: fun ChannelPipeline.(): Unit) =
+ setPipelineFactory(
+ StandardPipelineFactory(config)
+ )
+}
+
+fun main(args : Array) {
+ val bootstrap = ServerBootstrap(
+ NioServerSocketChannelFactory(
+ Executors.newCachedThreadPool(),
+ Executors.newCachedThreadPool()
+ )
+ )
+ bootstrap.configPipeline {
+ addLast("handler", HttpStaticFileServerHandler(args[0]))
+ }
+ bootstrap.bind(InetSocketAddress(8080))
+}
+
+class HttpStaticFileServerHandler(val rootDir: String) : SimpleChannelUpstreamHandler() {
+
+ fun messageReceived(ctx : ChannelHandlerContext, e : MessageEvent) {
+ val request = e.getMessage() as HttpRequest
+ if (request.getMethod() != HttpMethod.GET) {
+ ctx.sendError(METHOD_NOT_ALLOWED);
+ return;
+ }
+
+ val path = request.getUri()?.sanitizeUri()
+ if (path == null) {
+ ctx.sendError(FORBIDDEN);
+ return;
+ }
+
+ val file = File(rootDir + File.separator + path)
+ if (file.isHidden() || !file.exists()) {
+ ctx.sendError(NOT_FOUND)
+ return
+ }
+ if (!file.isFile()) {
+ ctx.sendError(FORBIDDEN)
+ return
+ }
+
+ var raf = RandomAccessFile(file, "r")
+
+ val fileLength = raf.length()
+
+ val response = DefaultHttpResponse(HttpVersion.HTTP_1_1, OK)
+ response["Content-Length"] = fileLength
+
+ val ch = e.getChannel()
+ ch?.write(response)
+ ch?.write(DefaultFileRegion(raf.getChannel(), 0, fileLength))
+ }
+}
diff --git a/idea/src/org/jetbrains/jet/plugin/compiler/JetCompiler.java b/idea/src/org/jetbrains/jet/plugin/compiler/JetCompiler.java
index 7327491ec3c..162d97555e2 100644
--- a/idea/src/org/jetbrains/jet/plugin/compiler/JetCompiler.java
+++ b/idea/src/org/jetbrains/jet/plugin/compiler/JetCompiler.java
@@ -16,6 +16,7 @@ import com.intellij.psi.PsiFile;
import com.intellij.psi.PsiManager;
import com.intellij.util.Chunk;
import org.jetbrains.annotations.NotNull;
+import org.jetbrains.jet.codegen.ClassBuilderFactory;
import org.jetbrains.jet.codegen.ClassFileFactory;
import org.jetbrains.jet.codegen.GenerationState;
import org.jetbrains.jet.lang.cfg.pseudocode.JetControlFlowDataTraceFactory;
@@ -69,7 +70,7 @@ public class JetCompiler implements TranslatingCompiler {
public void run() {
VirtualFile[] allFiles = compileContext.getCompileScope().getFiles(null, true);
- GenerationState generationState = new GenerationState(compileContext.getProject(), false);
+ GenerationState generationState = new GenerationState(compileContext.getProject(), ClassBuilderFactory.BINARIES);
List namespaces = Lists.newArrayList();
for (VirtualFile virtualFile : allFiles) {
PsiFile psiFile = PsiManager.getInstance(compileContext.getProject()).findFile(virtualFile);
diff --git a/idea/tests/org/jetbrains/jet/checkers/JetPsiCheckerTest.java b/idea/tests/org/jetbrains/jet/checkers/JetPsiCheckerTest.java
index 608022b4a54..c99444a9fb9 100644
--- a/idea/tests/org/jetbrains/jet/checkers/JetPsiCheckerTest.java
+++ b/idea/tests/org/jetbrains/jet/checkers/JetPsiCheckerTest.java
@@ -55,27 +55,27 @@ public class JetPsiCheckerTest extends LightDaemonAnalyzerTestCase {
public static Test suite() {
TestSuite suite = new TestSuite();
- suite.addTest(JetTestCaseBuilder.suiteForDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/", false, new JetTestCaseBuilder.NamedTestFactory() {
+ JetTestCaseBuilder.appendTestsInDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/", false, JetTestCaseBuilder.emptyFilter, new JetTestCaseBuilder.NamedTestFactory() {
@NotNull
@Override
public Test createTest(@NotNull String dataPath, @NotNull String name) {
return new JetPsiCheckerTest(dataPath, name);
}
- }));
- suite.addTest(JetTestCaseBuilder.suiteForDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/regression/", false, new JetTestCaseBuilder.NamedTestFactory() {
+ }, suite);
+ JetTestCaseBuilder.appendTestsInDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/regression/", false, JetTestCaseBuilder.emptyFilter, new JetTestCaseBuilder.NamedTestFactory() {
@NotNull
@Override
public Test createTest(@NotNull String dataPath, @NotNull String name) {
return new JetPsiCheckerTest(dataPath, name);
}
- }));
- suite.addTest(JetTestCaseBuilder.suiteForDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/infos/", false, new JetTestCaseBuilder.NamedTestFactory() {
+ }, suite);
+ JetTestCaseBuilder.appendTestsInDirectory(PluginTestCaseBase.getTestDataPathBase(), "/checker/infos/", false, JetTestCaseBuilder.emptyFilter, new JetTestCaseBuilder.NamedTestFactory() {
@NotNull
@Override
public Test createTest(@NotNull String dataPath, @NotNull String name) {
return new JetPsiCheckerTest(dataPath, name).setCheckInfos(true);
}
- }));
+ }, suite);
return suite;
}
}
diff --git a/stdlib/ktSrc/StandardLibrary.kt b/stdlib/ktSrc/StandardLibrary.kt
index bd0fab6b7d9..adc863dd482 100644
--- a/stdlib/ktSrc/StandardLibrary.kt
+++ b/stdlib/ktSrc/StandardLibrary.kt
@@ -13,10 +13,7 @@ namespace io {
fun print(message : Float) { System.out?.print(message) }
fun print(message : Double) { System.out?.print(message) }
- fun println(message : Any?) {
- System.out?.println(message)
- }
-
+ fun println(message : Any?) { System.out?.println(message) }
fun println(message : Int) { System.out?.println(message) }
fun println(message : Long) { System.out?.println(message) }
fun println(message : Byte) { System.out?.println(message) }