From 1d2e2373129a33692f9e8dec0c2a5c6c64b14646 Mon Sep 17 00:00:00 2001 From: Alex Tkachman Date: Fri, 6 Jan 2012 13:11:44 +0200 Subject: [PATCH 01/10] KT-925 step methods for integral ranges --- .../jet/codegen/ExpressionCodegen.java | 13 +- .../codegen/intrinsics/IntrinsicMethods.java | 1 + .../codegen/intrinsics/IteratorIterator.java | 21 ++ .../jet/codegen/intrinsics/RangeTo.java | 17 +- compiler/frontend/src/jet/Library.jet | 32 +- .../testData/codegen/regressions/kt925.kt | 54 ++++ .../jet/codegen/PrimitiveTypesTest.java | 4 + stdlib/src/jet/ByteRange.java | 18 +- stdlib/src/jet/CharRange.java | 18 +- stdlib/src/jet/IntRange.java | 18 +- stdlib/src/jet/LongRange.java | 31 +- stdlib/src/jet/ShortRange.java | 18 +- stdlib/src/jet/runtime/Ranges.java | 277 ++++++++++++++++++ 13 files changed, 467 insertions(+), 55 deletions(-) create mode 100644 compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IteratorIterator.java create mode 100644 compiler/testData/codegen/regressions/kt925.kt create mode 100644 stdlib/src/jet/runtime/Ranges.java diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java index cb4a2600153..da59861265d 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/ExpressionCodegen.java @@ -1046,11 +1046,10 @@ public class ExpressionCodegen extends JetVisitor { isInterface = CodegenUtil.isInterface(containingDeclaration); } else { - if(containingDeclaration instanceof ClassDescriptor && ((ClassDescriptor) containingDeclaration).getKind() == ClassKind.OBJECT) - isInterface = false; + if(containingDeclaration instanceof ClassDescriptor && ((ClassDescriptor) containingDeclaration).getKind() == ClassKind.TRAIT) + isInterface = true; else { - JetClass jetClass = (JetClass) bindingContext.get(BindingContext.DESCRIPTOR_TO_DECLARATION, containingDeclaration); - isInterface = jetClass == null || jetClass.isTrait(); + isInterface = false; } } } @@ -2768,7 +2767,11 @@ If finally block is present, its last expression is the value of try expression. JetType jetType = bindingContext.get(BindingContext.EXPRESSION_TYPE, rangeExpression); assert jetType != null; final DeclarationDescriptor descriptor = jetType.getConstructor().getDeclarationDescriptor(); - if (isClass(descriptor, "IntRange")) { + if (isClass(descriptor, "IntRange") || + isClass(descriptor, "CharRange") || + isClass(descriptor, "ByteRange") || + isClass(descriptor, "LongRange") || + isClass(descriptor, "ShortRange")) { return true; } } diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IntrinsicMethods.java b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IntrinsicMethods.java index 15da00768dd..2939e4ba879 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IntrinsicMethods.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IntrinsicMethods.java @@ -92,6 +92,7 @@ public class IntrinsicMethods { declareOverload(myStdLib.getLibraryScope().getFunctions("Array"), 1, new NewArray()); declareOverload(myStdLib.getLibraryScope().getFunctions("sure"), 0, new Sure()); declareOverload(myStdLib.getLibraryScope().getFunctions("synchronized"), 1, new StupidSync()); + declareOverload(myStdLib.getLibraryScope().getFunctions("iterator"), 0, new IteratorIterator()); declareIntrinsicFunction("ByteIterator", "next", 0, ITERATOR_NEXT); declareIntrinsicFunction("ShortIterator", "next", 0, ITERATOR_NEXT); diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IteratorIterator.java b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IteratorIterator.java new file mode 100644 index 00000000000..53a62983440 --- /dev/null +++ b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/IteratorIterator.java @@ -0,0 +1,21 @@ +package org.jetbrains.jet.codegen.intrinsics; + +import com.intellij.psi.PsiElement; +import org.jetbrains.annotations.Nullable; +import org.jetbrains.jet.codegen.ExpressionCodegen; +import org.jetbrains.jet.codegen.StackValue; +import org.jetbrains.jet.lang.psi.JetExpression; +import org.objectweb.asm.Type; +import org.objectweb.asm.commons.InstructionAdapter; + +import java.util.List; + +/** + * @author alex.tkachman + */ +public class IteratorIterator implements IntrinsicMethod { + @Override + public StackValue generate(ExpressionCodegen codegen, InstructionAdapter v, Type expectedType, @Nullable PsiElement element, @Nullable List arguments, StackValue receiver) { + return receiver; + } +} diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java index c742cd0d633..7ed14f5bbef 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java @@ -19,19 +19,22 @@ public class RangeTo implements IntrinsicMethod { @Override public StackValue generate(ExpressionCodegen codegen, InstructionAdapter v, Type expectedType, PsiElement element, List arguments, StackValue receiver) { if(arguments.size()==1) { + final Type leftType = receiver.type; + final Type rightType = codegen.expressionType(arguments.get(0)); receiver.put(Type.INT_TYPE, v); - codegen.gen(arguments.get(0), Type.INT_TYPE); - v.invokestatic("jet/IntRange", "rangeTo", "(II)Ljet/IntRange;"); - return StackValue.onStack(JetTypeMapper.TYPE_INT_RANGE); + codegen.gen(arguments.get(0), rightType); + v.invokestatic("jet/runtime/Ranges", "rangeTo", "(" + receiver.type.getDescriptor() + leftType.getDescriptor() + ")" + expectedType.getDescriptor()); + return StackValue.onStack(expectedType); } else { JetBinaryExpression expression = (JetBinaryExpression) element; final Type leftType = codegen.expressionType(expression.getLeft()); + final Type rightType = codegen.expressionType(expression.getRight()); if (JetTypeMapper.isIntPrimitive(leftType)) { - codegen.gen(expression.getLeft(), Type.INT_TYPE); - codegen.gen(expression.getRight(), Type.INT_TYPE); - v.invokestatic(expectedType.getInternalName(), "rangeTo", "(" + leftType.getDescriptor() + leftType.getDescriptor() + ")" + expectedType.getDescriptor()); - return StackValue.onStack(JetTypeMapper.TYPE_INT_RANGE); + codegen.gen(expression.getLeft(), leftType); + codegen.gen(expression.getRight(), rightType); + v.invokestatic("jet/runtime/Ranges", "rangeTo", "(" + leftType.getDescriptor() + rightType.getDescriptor() + ")" + expectedType.getDescriptor()); + return StackValue.onStack(expectedType); } else { throw new UnsupportedOperationException("ranges are only supported for int objects"); diff --git a/compiler/frontend/src/jet/Library.jet b/compiler/frontend/src/jet/Library.jet index 48e139cbb96..520ab070b0c 100644 --- a/compiler/frontend/src/jet/Library.jet +++ b/compiler/frontend/src/jet/Library.jet @@ -22,53 +22,71 @@ fun T?.sure() : T fun String?.plus(other: Any?) : String +fun Iterator.iterator() : Iterator + trait Iterator { fun next() : T val hasNext : Boolean } +fun ByteIterator.iterator() : ByteIterator + abstract open class ByteIterator() : Iterator { abstract open fun nextByte() : Byte override fun next() : Byte } +fun ShortIterator.iterator() : ShortIterator + abstract open class ShortIterator() : Iterator { abstract open fun nextShort() : Short override fun next() : Short } +fun CharIterator.iterator() : CharIterator + abstract open class CharIterator() : Iterator { abstract open fun nextChar() : Char override fun next() : Char } +fun IntIterator.iterator() : IntIterator + abstract open class IntIterator() : Iterator { abstract open fun nextInt() : Int override fun next() : Int } +fun LongIterator.iterator() : LongIterator + abstract open class LongIterator() : Iterator { abstract open fun nextLong() : Long override fun next() : Long } +fun FloatIterator.iterator() : FloatIterator + abstract open class FloatIterator() : Iterator { abstract open fun nextFloat() : Float override fun next() : Float } +fun DoubleIterator.iterator() : DoubleIterator + abstract open class DoubleIterator() : Iterator { abstract open fun nextDouble() : Double override fun next() : Double } +fun BooleanIterator.iterator() : BooleanIterator + abstract open class BooleanIterator() : Iterator { abstract open fun nextBoolean() : Boolean @@ -247,7 +265,7 @@ class IntRange(val start : Int, val size : Int, val isReversed : Boolean = false fun minus() : IntRange - fun step(step: Int) : IntIterable + fun step(step: Int) : IntIterator } class LongRange(val start : Long, val size : Long, val isReversed : Boolean = false) : Range, LongIterable { @@ -259,7 +277,7 @@ class LongRange(val start : Long, val size : Long, val isReversed : Boolean = fa fun minus() : LongRange - fun step(step: Long) : LongIterable + fun step(step: Long) : LongIterator } class ByteRange(val start : Byte, val size : Int, val isReversed : Boolean = false) : Range, ByteIterable { @@ -271,7 +289,7 @@ class ByteRange(val start : Byte, val size : Int, val isReversed : Boolean = fal fun minus() : ByteRange - fun step(step: Int) : ByteIterable + fun step(step: Int) : ByteIterator } class ShortRange(val start : Short, val size : Int, val isReversed : Boolean = false) : Range, ShortIterable { @@ -283,7 +301,7 @@ class ShortRange(val start : Short, val size : Int, val isReversed : Boolean = f fun minus() : ShortRange - fun step(step: Int) : ShortIterable + fun step(step: Int) : ShortIterator } class CharRange(val start : Char, val size : Int, val isReversed : Boolean = false) : Range, CharIterable { @@ -295,7 +313,7 @@ class CharRange(val start : Char, val size : Int, val isReversed : Boolean = fal fun minus() : CharRange - fun step(step: Int) : CharIterable + fun step(step: Int) : CharIterator } abstract class Number : Hashable { @@ -635,8 +653,8 @@ class Char : Number, Comparable { fun rangeTo(other : Float) : Range fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : IntRange - fun rangeTo(other : Short) : IntRange - fun rangeTo(other : Byte) : IntRange + fun rangeTo(other : Short) : ShortRange + fun rangeTo(other : Byte) : CharRange fun rangeTo(other : Char) : CharRange fun inc() : Char diff --git a/compiler/testData/codegen/regressions/kt925.kt b/compiler/testData/codegen/regressions/kt925.kt new file mode 100644 index 00000000000..2db14c16b4b --- /dev/null +++ b/compiler/testData/codegen/regressions/kt925.kt @@ -0,0 +1,54 @@ +fun test1() : Boolean { + val r1 = 1..10 + var s1 = 0 + for(e in r1 step 2) { + s1 += e + } + return s1 == 25 +} + +fun test2() : Boolean { + val r1 = 1.byt..10.byt + var s1 = 0 + for(e in r1 step 2) { + s1 += e + } + return s1 == 25 +} + +fun test3() : Boolean { + val r1 = 1.byt..10.lng + var s1 = 0.lng + for(e in r1 step 2) { + s1 += e + } + return s1 == 25.lng +} + +fun test4() : Boolean { + val r1 = 1.byt..10.sht + var s1 = 0.sht + for(e in r1 step 2) { + s1 += e + } + return s1 == 25.sht +} + +fun test5() : Boolean { + val r1 = 'a'..'h' + var s1 = 0 + for(e in r1 step 2) { + s1 ++ + } + return s1 == 4 +} + +fun box() : String { + if(test1().not()) return "test1 failed" + if(test2().not()) return "test2 failed" + if(test3().not()) return "test3 failed" + if(test4().not()) return "test4 failed" + if(test5().not()) return "test4 failed" + + return "OK" +} \ No newline at end of file diff --git a/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java b/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java index 6275a968154..d9bafd599bf 100644 --- a/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java +++ b/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java @@ -367,4 +367,8 @@ public class PrimitiveTypesTest extends CodegenTestCase { public void testKt821 () { blackBoxFile("regressions/kt821.kt"); } + + public void testKt925 () { + blackBoxFile("regressions/kt925.kt"); + } } diff --git a/stdlib/src/jet/ByteRange.java b/stdlib/src/jet/ByteRange.java index 754445a4459..8a1d94ca3cd 100644 --- a/stdlib/src/jet/ByteRange.java +++ b/stdlib/src/jet/ByteRange.java @@ -44,13 +44,17 @@ public final class ByteRange implements Range, ByteIterable, JetObject { return count < 0 ? -count : count; } + public ByteIterator step(int step) { + return new MyIterator(start, count, step); + } + public ByteRange minus() { return new ByteRange(getEnd(), -count); } @Override public ByteIterator iterator() { - return new MyIterator(start, count); + return new MyIterator(start, count, 1); } @Override @@ -80,12 +84,14 @@ public final class ByteRange implements Range, ByteIterable, JetObject { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); private byte cur; + private int step; private int count; private final boolean reversed; - public MyIterator(byte startValue, int count) { + public MyIterator(byte startValue, int count, int step) { cur = startValue; + this.step = step; reversed = count < 0; this.count = reversed ? -count : count; } @@ -97,12 +103,14 @@ public final class ByteRange implements Range, ByteIterable, JetObject { @Override public byte nextByte() { - count--; + count -= step; if(reversed) { - return cur--; + cur -= step; + return (byte) (cur + step); } else { - return cur++; + cur += step; + return (byte) (cur - step); } } diff --git a/stdlib/src/jet/CharRange.java b/stdlib/src/jet/CharRange.java index e295795527e..357fa08dd14 100644 --- a/stdlib/src/jet/CharRange.java +++ b/stdlib/src/jet/CharRange.java @@ -48,9 +48,13 @@ public final class CharRange implements Range, CharIterable, JetObjec return new CharRange(getEnd(), -count); } + public CharIterator step(int step) { + return new MyIterator(start, count, step); + } + @Override public CharIterator iterator() { - return new MyIterator(start, count); + return new MyIterator(start, count, 1); } @Override @@ -80,12 +84,14 @@ public final class CharRange implements Range, CharIterable, JetObjec private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); private char cur; + private int step; private int count; private final boolean reversed; - public MyIterator(char startValue, int count) { + public MyIterator(char startValue, int count, int step) { cur = startValue; + this.step = step; reversed = count < 0; this.count = reversed ? -count : count; } @@ -97,12 +103,14 @@ public final class CharRange implements Range, CharIterable, JetObjec @Override public char nextChar() { - count--; + count -= step; if(reversed) { - return cur--; + cur -= step; + return (char) (cur + step); } else { - return cur++; + cur += step; + return (char) (cur - step); } } diff --git a/stdlib/src/jet/IntRange.java b/stdlib/src/jet/IntRange.java index 646a095e842..595ab2aef54 100644 --- a/stdlib/src/jet/IntRange.java +++ b/stdlib/src/jet/IntRange.java @@ -28,6 +28,10 @@ public final class IntRange implements Range, IntIterable, JetObject { return item <= start && item > start + count; } + public IntIterator step(int step) { + return new MyIterator(start, count, step); + } + public boolean getIsReversed() { return count < 0; } @@ -50,7 +54,7 @@ public final class IntRange implements Range, IntIterable, JetObject { @Override public IntIterator iterator() { - return new MyIterator(start, count); + return new MyIterator(start, count, 1); } @Override @@ -80,12 +84,14 @@ public final class IntRange implements Range, IntIterable, JetObject { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); private int cur; + private int step; private int count; private final boolean reversed; - public MyIterator(int startValue, int count) { + public MyIterator(int startValue, int count, int step) { cur = startValue; + this.step = step; reversed = count < 0; this.count = reversed ? -count : count; } @@ -97,12 +103,14 @@ public final class IntRange implements Range, IntIterable, JetObject { @Override public int nextInt() { - count--; + count -= step; if(reversed) { - return cur--; + cur -= step; + return cur + step; } else { - return cur++; + cur += step; + return cur - step; } } diff --git a/stdlib/src/jet/LongRange.java b/stdlib/src/jet/LongRange.java index 3a047c7b65f..0d8224105d7 100644 --- a/stdlib/src/jet/LongRange.java +++ b/stdlib/src/jet/LongRange.java @@ -19,6 +19,10 @@ public final class LongRange implements Range, LongIterable, JetObject { this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); } + public LongIterator step(long step) { + return new MyIterator(start, count, step); + } + @Override public boolean contains(Long item) { if (item == null) return false; @@ -50,7 +54,7 @@ public final class LongRange implements Range, LongIterable, JetObject { @Override public LongIterator iterator() { - return new MyIterator(start, count); + return new MyIterator(start, count, 1); } @Override @@ -63,29 +67,22 @@ public final class LongRange implements Range, LongIterable, JetObject { return null; } - public static IntRange count(int length) { - return new IntRange(0, length); - } - - public static IntRange rangeTo(int from, int to) { - if(from > to) { - return new IntRange(to, from-to+1, true); - } - else { - return new IntRange(from, to-from+1); - } + public static LongRange count(int length) { + return new LongRange(0, length); } private static class MyIterator extends LongIterator { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); private long cur; + private long step; private long count; private final boolean reversed; - public MyIterator(long startValue, long count) { + public MyIterator(long startValue, long count, long step) { cur = startValue; + this.step = step; reversed = count < 0; this.count = reversed ? -count : count; } @@ -97,12 +94,14 @@ public final class LongRange implements Range, LongIterable, JetObject { @Override public long nextLong() { - count--; + count -= step; if(reversed) { - return cur--; + cur -= step; + return (cur + step); } else { - return cur++; + cur += step; + return (cur - step); } } diff --git a/stdlib/src/jet/ShortRange.java b/stdlib/src/jet/ShortRange.java index 0d96d652d88..a12e7ba032e 100644 --- a/stdlib/src/jet/ShortRange.java +++ b/stdlib/src/jet/ShortRange.java @@ -19,6 +19,10 @@ public final class ShortRange implements Range, ShortIterable, JetObject this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); } + public ShortIterator step(int step) { + return new MyIterator(start, count, step); + } + @Override public boolean contains(Short item) { if (item == null) return false; @@ -50,7 +54,7 @@ public final class ShortRange implements Range, ShortIterable, JetObject @Override public ShortIterator iterator() { - return new MyIterator(start, count); + return new MyIterator(start, count, 1); } @Override @@ -80,12 +84,14 @@ public final class ShortRange implements Range, ShortIterable, JetObject private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); private short cur; + private int step; private int count; private final boolean reversed; - public MyIterator(short startValue, int count) { + public MyIterator(short startValue, int count, int step) { cur = startValue; + this.step = step; reversed = count < 0; this.count = reversed ? -count : count; } @@ -97,12 +103,14 @@ public final class ShortRange implements Range, ShortIterable, JetObject @Override public short nextShort() { - count--; + count -= step; if(reversed) { - return cur--; + cur -= step; + return (short) (cur + step); } else { - return cur++; + cur += step; + return (short) (cur - step); } } diff --git a/stdlib/src/jet/runtime/Ranges.java b/stdlib/src/jet/runtime/Ranges.java new file mode 100644 index 00000000000..8258615078b --- /dev/null +++ b/stdlib/src/jet/runtime/Ranges.java @@ -0,0 +1,277 @@ +package jet.runtime; + +import jet.*; + +import java.util.Arrays; +import java.util.List; + +/** +* @author alex.tkachman +*/ +public class Ranges { + private Ranges() { + } + + public static ByteRange rangeTo(byte from, byte to) { + if(from > to) { + return new ByteRange(to, from-to+1, true); + } + else { + return new ByteRange(from, to-from+1); + } + } + + public static ShortRange rangeTo(byte from, short to) { + if(from > to) { + return new ShortRange(to, from-to+1, true); + } + else { + return new ShortRange(from, to-from+1); + } + } + + public static IntRange rangeTo(byte from, int to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static LongRange rangeTo(byte from, long to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static CharRange rangeTo(byte from, char to) { + if(from > to) { + return new CharRange(to, from-to+1, true); + } + else { + return new CharRange((char) from, to-from+1); + } + } + + public static ShortRange rangeTo(short from, byte to) { + if(from > to) { + return new ShortRange(to, from-to+1, true); + } + else { + return new ShortRange(from, to-from+1); + } + } + + public static ShortRange rangeTo(short from, short to) { + if(from > to) { + return new ShortRange(to, from-to+1, true); + } + else { + return new ShortRange(from, to-from+1); + } + } + + public static IntRange rangeTo(short from, int to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static LongRange rangeTo(short from, long to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static ShortRange rangeTo(short from, char to) { + if(from > to) { + return new ShortRange((short) to, from-to+1, true); + } + else { + return new ShortRange(from, to-from+1); + } + } + + public static IntRange rangeTo(int from, byte to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static IntRange rangeTo(int from, short to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static IntRange rangeTo(int from, int to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static LongRange rangeTo(int from, long to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static IntRange rangeTo(int from, char to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static LongRange rangeTo(long from, byte to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static LongRange rangeTo(long from, short to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static LongRange rangeTo(long from, int to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static LongRange rangeTo(long from, long to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static LongRange rangeTo(long from, char to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static CharRange rangeTo(char from, byte to) { + if(from > to) { + return new CharRange((char) to, from-to+1, true); + } + else { + return new CharRange(from, to-from+1); + } + } + + public static ShortRange rangeTo(char from, short to) { + if(from > to) { + return new ShortRange(to, from-to+1, true); + } + else { + return new ShortRange((short) from, to-from+1); + } + } + + public static IntRange rangeTo(char from, int to) { + if(from > to) { + return new IntRange(to, from-to+1, true); + } + else { + return new IntRange(from, to-from+1); + } + } + + public static LongRange rangeTo(char from, long to) { + if(from > to) { + return new LongRange(to, from-to+1, true); + } + else { + return new LongRange(from, to-from+1); + } + } + + public static CharRange rangeTo(char from, char to) { + if(from > to) { + return new CharRange(to, from-to+1, true); + } + else { + return new CharRange(from, to-from+1); + } + } + + public static void main(String[] args) { + List strings = Arrays.asList("byte", "short", "int", "long", /*"float", "double",*/ "char"); + for(String t1 : strings) + for(String t2 : strings) { + String resType; + if(t1.equals("double") || t2.equals("double")) { + resType = "DoubleRange"; + } + else if(t1.equals("float") || t2.equals("float")) { + resType = "FloatRange"; + } + else if(t1.equals("long") || t2.equals("long")) { + resType = "LongRange"; + } + else if(t1.equals("int") || t2.equals("int")) { + resType = "IntRange"; + } + else if(t1.equals("short") || t2.equals("short")) { + resType = "ShortRange"; + } + else if(t1.equals("char") || t2.equals("char")) { + resType = "CharRange"; + } + else { + resType = "ByteRange"; + } + + System.out.println("\npublic static " + resType + " rangeTo(" + t1 + " from, " + t2 + " to) {" + + "\n if(from > to) {\n" + + " return new " + resType + "(to, from-to+1, true);\n" + + " }\n" + + " else {\n" + + " return new " + resType + "(from, to-from+1);\n" + + " }\n" + + "}"); + } + } +} From 22afbed9096906292ab950689f8b8febb7548c2c Mon Sep 17 00:00:00 2001 From: Alex Tkachman Date: Fri, 6 Jan 2012 14:22:02 +0200 Subject: [PATCH 02/10] fixing stupid bug introduced in previous commit simplification of api --- compiler/frontend/src/jet/Library.jet | 20 +++++-- .../testData/codegen/regressions/kt821.kt | 12 ----- stdlib/src/jet/ByteRange.java | 17 ------ stdlib/src/jet/CharRange.java | 17 ------ stdlib/src/jet/IntRange.java | 28 ++++------ stdlib/src/jet/LongRange.java | 8 --- stdlib/src/jet/ShortRange.java | 17 ------ stdlib/src/jet/runtime/Ranges.java | 52 +++++++++---------- 8 files changed, 50 insertions(+), 121 deletions(-) diff --git a/compiler/frontend/src/jet/Library.jet b/compiler/frontend/src/jet/Library.jet index 520ab070b0c..cdbbde0740f 100644 --- a/compiler/frontend/src/jet/Library.jet +++ b/compiler/frontend/src/jet/Library.jet @@ -256,7 +256,7 @@ trait Range> { fun contains(item : T) : Boolean } -class IntRange(val start : Int, val size : Int, val isReversed : Boolean = false) : Range, IntIterable { +class IntRange(val start : Int, val size : Int) : Range, IntIterable { fun iterator () : IntIterator fun contains (elem: Int) : Boolean @@ -266,9 +266,11 @@ class IntRange(val start : Int, val size : Int, val isReversed : Boolean = false fun minus() : IntRange fun step(step: Int) : IntIterator + + val isReversed : Boolean } -class LongRange(val start : Long, val size : Long, val isReversed : Boolean = false) : Range, LongIterable { +class LongRange(val start : Long, val size : Long) : Range, LongIterable { fun iterator () : LongIterator fun contains (elem: Long) : Boolean @@ -278,9 +280,11 @@ class LongRange(val start : Long, val size : Long, val isReversed : Boolean = fa fun minus() : LongRange fun step(step: Long) : LongIterator + + val isReversed : Boolean } -class ByteRange(val start : Byte, val size : Int, val isReversed : Boolean = false) : Range, ByteIterable { +class ByteRange(val start : Byte, val size : Int) : Range, ByteIterable { fun iterator () : ByteIterator fun contains (elem: Byte) : Boolean @@ -290,9 +294,11 @@ class ByteRange(val start : Byte, val size : Int, val isReversed : Boolean = fal fun minus() : ByteRange fun step(step: Int) : ByteIterator + + val isReversed : Boolean } -class ShortRange(val start : Short, val size : Int, val isReversed : Boolean = false) : Range, ShortIterable { +class ShortRange(val start : Short, val size : Int) : Range, ShortIterable { fun iterator () : ShortIterator fun contains (elem: Byte) : Boolean @@ -302,9 +308,11 @@ class ShortRange(val start : Short, val size : Int, val isReversed : Boolean = f fun minus() : ShortRange fun step(step: Int) : ShortIterator + + val isReversed : Boolean } -class CharRange(val start : Char, val size : Int, val isReversed : Boolean = false) : Range, CharIterable { +class CharRange(val start : Char, val size : Int) : Range, CharIterable { fun iterator () : CharIterator fun contains (elem: Char) : Boolean @@ -314,6 +322,8 @@ class CharRange(val start : Char, val size : Int, val isReversed : Boolean = fal fun minus() : CharRange fun step(step: Int) : CharIterator + + val isReversed : Boolean } abstract class Number : Hashable { diff --git a/compiler/testData/codegen/regressions/kt821.kt b/compiler/testData/codegen/regressions/kt821.kt index c9eea791ac6..47b7d3f465f 100644 --- a/compiler/testData/codegen/regressions/kt821.kt +++ b/compiler/testData/codegen/regressions/kt821.kt @@ -2,9 +2,6 @@ fun box() : String { val r1 = IntRange(1, 4) if(r1.end != 4 || r1.isReversed || r1.size != 4) return "fail" - val r2 = IntRange(1, 4, true) - if(r2.end != -2 || !r2.isReversed || r2.size != 4) return "fail" - val r3 = -(0..5) if(r3.start != 5 || r3.end != 0 || !r3.isReversed || r3.size != 6) return "fail" @@ -14,9 +11,6 @@ fun box() : String { val r5 = ByteRange(1, 4) if(r5.end != 4.byt || r5.isReversed || r5.size != 4) return "fail" - val r6 = ByteRange(1, 4, true) - if(r6.end != -2.byt || !r6.isReversed) return "fail" - val r7 = -(0.byt..5.byt) if(r7.start != 5.byt || r7.end != 0.byt || !r7.isReversed) return "fail" @@ -26,9 +20,6 @@ fun box() : String { val r10 = ShortRange(1, 4) if(r10.end != 4.sht || r10.isReversed || r10.size != 4) return "fail" - val r11 = ShortRange(1, 4, true) - if(r11.end != -2.sht || !r11.isReversed) return "fail" - val r12 = -(0.sht..5.sht) if(r12.start != 5.sht || r12.end != 0.sht || !r12.isReversed) return "fail" @@ -38,9 +29,6 @@ fun box() : String { val r14 = CharRange('a', 4) if(r14.end != 'd' || r14.isReversed || r14.size != 4) return "fail" - val r15 = CharRange('D', 4, true) - if(r15.end != 'A' || !r15.isReversed) return "fail" - val r16 = -('a'..'e') if(r16.start != 'e' || r16.end != 'a' || !r16.isReversed) return "fail" diff --git a/stdlib/src/jet/ByteRange.java b/stdlib/src/jet/ByteRange.java index 8a1d94ca3cd..b61679c79e7 100644 --- a/stdlib/src/jet/ByteRange.java +++ b/stdlib/src/jet/ByteRange.java @@ -11,14 +11,6 @@ public final class ByteRange implements Range, ByteIterable, JetObject { this.count = count; } - public ByteRange(byte startValue, int count, boolean reversed) { - this(startValue, reversed ? -count : count); - } - - public ByteRange(byte startValue, int count, boolean reversed, int defaultMask) { - this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); - } - @Override public boolean contains(Byte item) { if (item == null) return false; @@ -71,15 +63,6 @@ public final class ByteRange implements Range, ByteIterable, JetObject { return new ByteRange((byte) 0, length); } - public static ByteRange rangeTo(byte from, byte to) { - if(from > to) { - return new ByteRange(to, from-to+1, true); - } - else { - return new ByteRange(from, to-from+1); - } - } - private static class MyIterator extends ByteIterator { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); diff --git a/stdlib/src/jet/CharRange.java b/stdlib/src/jet/CharRange.java index 357fa08dd14..ff94c99239c 100644 --- a/stdlib/src/jet/CharRange.java +++ b/stdlib/src/jet/CharRange.java @@ -11,14 +11,6 @@ public final class CharRange implements Range, CharIterable, JetObjec this.count = count; } - public CharRange(char startValue, int count, boolean reversed) { - this(startValue, reversed ? -count : count); - } - - public CharRange(char startValue, int count, boolean reversed, int defaultMask) { - this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); - } - @Override public boolean contains(Character item) { if (item == null) return false; @@ -71,15 +63,6 @@ public final class CharRange implements Range, CharIterable, JetObjec return new CharRange((char) 0, length); } - public static CharRange rangeTo(char from, char to) { - if(from > to) { - return new CharRange(to, from-to+1, true); - } - else { - return new CharRange(from, to-from+1); - } - } - private static class MyIterator extends CharIterator { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); diff --git a/stdlib/src/jet/IntRange.java b/stdlib/src/jet/IntRange.java index 595ab2aef54..9b722639436 100644 --- a/stdlib/src/jet/IntRange.java +++ b/stdlib/src/jet/IntRange.java @@ -11,14 +11,6 @@ public final class IntRange implements Range, IntIterable, JetObject { this.count = count; } - public IntRange(int startValue, int count, boolean reversed) { - this(startValue, reversed ? -count : count); - } - - public IntRange(int startValue, int count, boolean reversed, int defaultMask) { - this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); - } - @Override public boolean contains(Integer item) { if (item == null) return false; @@ -71,15 +63,6 @@ public final class IntRange implements Range, IntIterable, JetObject { return new IntRange(0, length); } - public static IntRange rangeTo(int from, int to) { - if(from > to) { - return new IntRange(to, from-to+1, true); - } - else { - return new IntRange(from, to-from+1); - } - } - private static class MyIterator extends IntIterator { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); @@ -92,8 +75,15 @@ public final class IntRange implements Range, IntIterable, JetObject { public MyIterator(int startValue, int count, int step) { cur = startValue; this.step = step; - reversed = count < 0; - this.count = reversed ? -count : count; + if(count < 0) { + reversed = count < 0; + count = -count; + startValue += count; + } + else { + reversed = false; + } + this.count = count; } @Override diff --git a/stdlib/src/jet/LongRange.java b/stdlib/src/jet/LongRange.java index 0d8224105d7..abcb921ca87 100644 --- a/stdlib/src/jet/LongRange.java +++ b/stdlib/src/jet/LongRange.java @@ -11,14 +11,6 @@ public final class LongRange implements Range, LongIterable, JetObject { this.count = count; } - public LongRange(long startValue, long count, boolean reversed) { - this(startValue, reversed ? -count : count); - } - - public LongRange(int startValue, int count, boolean reversed, int defaultMask) { - this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); - } - public LongIterator step(long step) { return new MyIterator(start, count, step); } diff --git a/stdlib/src/jet/ShortRange.java b/stdlib/src/jet/ShortRange.java index a12e7ba032e..79428f90702 100644 --- a/stdlib/src/jet/ShortRange.java +++ b/stdlib/src/jet/ShortRange.java @@ -11,14 +11,6 @@ public final class ShortRange implements Range, ShortIterable, JetObject this.count = count; } - public ShortRange(short startValue, int count, boolean reversed) { - this(startValue, reversed ? -count : count); - } - - public ShortRange(short startValue, int count, boolean reversed, int defaultMask) { - this(startValue, reversed ? -count : count, (defaultMask & 4) == 0); - } - public ShortIterator step(int step) { return new MyIterator(start, count, step); } @@ -71,15 +63,6 @@ public final class ShortRange implements Range, ShortIterable, JetObject return new ShortRange((byte) 0, length); } - public static ShortRange rangeTo(short from, short to) { - if(from > to) { - return new ShortRange(to, from-to+1, true); - } - else { - return new ShortRange(from, to-from+1); - } - } - private static class MyIterator extends ShortIterator { private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); diff --git a/stdlib/src/jet/runtime/Ranges.java b/stdlib/src/jet/runtime/Ranges.java index 8258615078b..19d20293a12 100644 --- a/stdlib/src/jet/runtime/Ranges.java +++ b/stdlib/src/jet/runtime/Ranges.java @@ -14,7 +14,7 @@ public class Ranges { public static ByteRange rangeTo(byte from, byte to) { if(from > to) { - return new ByteRange(to, from-to+1, true); + return new ByteRange(from, to-from-1); } else { return new ByteRange(from, to-from+1); @@ -23,7 +23,7 @@ public class Ranges { public static ShortRange rangeTo(byte from, short to) { if(from > to) { - return new ShortRange(to, from-to+1, true); + return new ShortRange(from, to-from-1); } else { return new ShortRange(from, to-from+1); @@ -32,7 +32,7 @@ public class Ranges { public static IntRange rangeTo(byte from, int to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -41,7 +41,7 @@ public class Ranges { public static LongRange rangeTo(byte from, long to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -50,7 +50,7 @@ public class Ranges { public static CharRange rangeTo(byte from, char to) { if(from > to) { - return new CharRange(to, from-to+1, true); + return new CharRange((char) from, to-from-1); } else { return new CharRange((char) from, to-from+1); @@ -59,7 +59,7 @@ public class Ranges { public static ShortRange rangeTo(short from, byte to) { if(from > to) { - return new ShortRange(to, from-to+1, true); + return new ShortRange(from, to-from-1); } else { return new ShortRange(from, to-from+1); @@ -68,7 +68,7 @@ public class Ranges { public static ShortRange rangeTo(short from, short to) { if(from > to) { - return new ShortRange(to, from-to+1, true); + return new ShortRange(from, to-from-1); } else { return new ShortRange(from, to-from+1); @@ -77,7 +77,7 @@ public class Ranges { public static IntRange rangeTo(short from, int to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -86,7 +86,7 @@ public class Ranges { public static LongRange rangeTo(short from, long to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -95,7 +95,7 @@ public class Ranges { public static ShortRange rangeTo(short from, char to) { if(from > to) { - return new ShortRange((short) to, from-to+1, true); + return new ShortRange(from, to-from-1); } else { return new ShortRange(from, to-from+1); @@ -104,7 +104,7 @@ public class Ranges { public static IntRange rangeTo(int from, byte to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -113,7 +113,7 @@ public class Ranges { public static IntRange rangeTo(int from, short to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -122,7 +122,7 @@ public class Ranges { public static IntRange rangeTo(int from, int to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -131,7 +131,7 @@ public class Ranges { public static LongRange rangeTo(int from, long to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -140,7 +140,7 @@ public class Ranges { public static IntRange rangeTo(int from, char to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -149,7 +149,7 @@ public class Ranges { public static LongRange rangeTo(long from, byte to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -158,7 +158,7 @@ public class Ranges { public static LongRange rangeTo(long from, short to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -167,7 +167,7 @@ public class Ranges { public static LongRange rangeTo(long from, int to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -176,7 +176,7 @@ public class Ranges { public static LongRange rangeTo(long from, long to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -185,7 +185,7 @@ public class Ranges { public static LongRange rangeTo(long from, char to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -194,7 +194,7 @@ public class Ranges { public static CharRange rangeTo(char from, byte to) { if(from > to) { - return new CharRange((char) to, from-to+1, true); + return new CharRange(from, to-from-1); } else { return new CharRange(from, to-from+1); @@ -203,7 +203,7 @@ public class Ranges { public static ShortRange rangeTo(char from, short to) { if(from > to) { - return new ShortRange(to, from-to+1, true); + return new ShortRange((short) from, to-from-1); } else { return new ShortRange((short) from, to-from+1); @@ -212,7 +212,7 @@ public class Ranges { public static IntRange rangeTo(char from, int to) { if(from > to) { - return new IntRange(to, from-to+1, true); + return new IntRange(from, to-from-1); } else { return new IntRange(from, to-from+1); @@ -221,7 +221,7 @@ public class Ranges { public static LongRange rangeTo(char from, long to) { if(from > to) { - return new LongRange(to, from-to+1, true); + return new LongRange(from, to-from-1); } else { return new LongRange(from, to-from+1); @@ -230,7 +230,7 @@ public class Ranges { public static CharRange rangeTo(char from, char to) { if(from > to) { - return new CharRange(to, from-to+1, true); + return new CharRange(from, to-from-1); } else { return new CharRange(from, to-from+1); @@ -266,7 +266,7 @@ public class Ranges { System.out.println("\npublic static " + resType + " rangeTo(" + t1 + " from, " + t2 + " to) {" + "\n if(from > to) {\n" + - " return new " + resType + "(to, from-to+1, true);\n" + + " return new " + resType + "(from, to-from-1);\n" + " }\n" + " else {\n" + " return new " + resType + "(from, to-from+1);\n" + From eba343dd849fbbe014127c57741a5c09df6b6681 Mon Sep 17 00:00:00 2001 From: Alex Tkachman Date: Fri, 6 Jan 2012 14:32:14 +0200 Subject: [PATCH 03/10] negative steps supported --- stdlib/src/jet/ByteRange.java | 5 ++++- stdlib/src/jet/CharRange.java | 5 ++++- stdlib/src/jet/IntRange.java | 5 ++++- stdlib/src/jet/LongRange.java | 5 ++++- stdlib/src/jet/ShortRange.java | 5 ++++- 5 files changed, 20 insertions(+), 5 deletions(-) diff --git a/stdlib/src/jet/ByteRange.java b/stdlib/src/jet/ByteRange.java index b61679c79e7..4210b7d9f5f 100644 --- a/stdlib/src/jet/ByteRange.java +++ b/stdlib/src/jet/ByteRange.java @@ -37,7 +37,10 @@ public final class ByteRange implements Range, ByteIterable, JetObject { } public ByteIterator step(int step) { - return new MyIterator(start, count, step); + if(step < 0) + return new MyIterator(getEnd(), -count, -step); + else + return new MyIterator(start, count, step); } public ByteRange minus() { diff --git a/stdlib/src/jet/CharRange.java b/stdlib/src/jet/CharRange.java index ff94c99239c..53b41a5d542 100644 --- a/stdlib/src/jet/CharRange.java +++ b/stdlib/src/jet/CharRange.java @@ -41,7 +41,10 @@ public final class CharRange implements Range, CharIterable, JetObjec } public CharIterator step(int step) { - return new MyIterator(start, count, step); + if(step < 0) + return new MyIterator(getEnd(), -count, -step); + else + return new MyIterator(start, count, step); } @Override diff --git a/stdlib/src/jet/IntRange.java b/stdlib/src/jet/IntRange.java index 9b722639436..0bc52ada3c5 100644 --- a/stdlib/src/jet/IntRange.java +++ b/stdlib/src/jet/IntRange.java @@ -21,7 +21,10 @@ public final class IntRange implements Range, IntIterable, JetObject { } public IntIterator step(int step) { - return new MyIterator(start, count, step); + if(step < 0) + return new MyIterator(getEnd(), -count, -step); + else + return new MyIterator(start, count, step); } public boolean getIsReversed() { diff --git a/stdlib/src/jet/LongRange.java b/stdlib/src/jet/LongRange.java index abcb921ca87..6785f9ecded 100644 --- a/stdlib/src/jet/LongRange.java +++ b/stdlib/src/jet/LongRange.java @@ -12,7 +12,10 @@ public final class LongRange implements Range, LongIterable, JetObject { } public LongIterator step(long step) { - return new MyIterator(start, count, step); + if(step < 0) + return new MyIterator(getEnd(), -count, -step); + else + return new MyIterator(start, count, step); } @Override diff --git a/stdlib/src/jet/ShortRange.java b/stdlib/src/jet/ShortRange.java index 79428f90702..a3c95dd7258 100644 --- a/stdlib/src/jet/ShortRange.java +++ b/stdlib/src/jet/ShortRange.java @@ -12,7 +12,10 @@ public final class ShortRange implements Range, ShortIterable, JetObject } public ShortIterator step(int step) { - return new MyIterator(start, count, step); + if(step < 0) + return new MyIterator(getEnd(), -count, -step); + else + return new MyIterator(start, count, step); } @Override From dba41c2e88524f1ee6d17e8f2c79c157f3830c23 Mon Sep 17 00:00:00 2001 From: Alex Tkachman Date: Fri, 6 Jan 2012 15:55:27 +0200 Subject: [PATCH 04/10] float/double ranges --- .../jet/codegen/intrinsics/RangeTo.java | 10 +- compiler/frontend/src/jet/Library.jet | 72 +++++++---- .../testData/codegen/regressions/kt765.kt | 13 ++ .../jet/codegen/PrimitiveTypesTest.java | 4 + stdlib/src/jet/ByteRange.java | 11 +- stdlib/src/jet/CharRange.java | 11 +- stdlib/src/jet/DoubleRange.java | 117 +++++++++++++++++ stdlib/src/jet/FloatRange.java | 117 +++++++++++++++++ stdlib/src/jet/IntRange.java | 2 +- stdlib/src/jet/LongRange.java | 11 +- stdlib/src/jet/ShortRange.java | 11 +- stdlib/src/jet/runtime/Ranges.java | 121 ++++++++++++++++-- 12 files changed, 453 insertions(+), 47 deletions(-) create mode 100644 compiler/testData/codegen/regressions/kt765.kt create mode 100644 stdlib/src/jet/DoubleRange.java create mode 100644 stdlib/src/jet/FloatRange.java diff --git a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java index 7ed14f5bbef..3dc18b19361 100644 --- a/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java +++ b/compiler/backend/src/org/jetbrains/jet/codegen/intrinsics/RangeTo.java @@ -30,15 +30,15 @@ public class RangeTo implements IntrinsicMethod { JetBinaryExpression expression = (JetBinaryExpression) element; final Type leftType = codegen.expressionType(expression.getLeft()); final Type rightType = codegen.expressionType(expression.getRight()); - if (JetTypeMapper.isIntPrimitive(leftType)) { +// if (JetTypeMapper.isIntPrimitive(leftType)) { codegen.gen(expression.getLeft(), leftType); codegen.gen(expression.getRight(), rightType); v.invokestatic("jet/runtime/Ranges", "rangeTo", "(" + leftType.getDescriptor() + rightType.getDescriptor() + ")" + expectedType.getDescriptor()); return StackValue.onStack(expectedType); - } - else { - throw new UnsupportedOperationException("ranges are only supported for int objects"); - } +// } +// else { +// throw new UnsupportedOperationException("ranges are only supported for int objects"); +// } } } } diff --git a/compiler/frontend/src/jet/Library.jet b/compiler/frontend/src/jet/Library.jet index cdbbde0740f..f782b5e0473 100644 --- a/compiler/frontend/src/jet/Library.jet +++ b/compiler/frontend/src/jet/Library.jet @@ -326,6 +326,30 @@ class CharRange(val start : Char, val size : Int) : Range, CharIterable { val isReversed : Boolean } +class FloatRange(val start : Float, val size : Float) : Range { + fun contains (elem: Float) : Boolean + + val end : Float + + fun minus() : FloatRange + + fun step(step: Float) : FloatIterator + + val isReversed : Boolean +} + +class DoubleRange(val start : Double, val size : Double) : Range { + fun contains (elem: Double) : Boolean + + val end : Double + + fun minus() : DoubleRange + + fun step(step: Double) : DoubleIterator + + val isReversed : Boolean +} + abstract class Number : Hashable { abstract val dbl : Double abstract val flt : Float @@ -391,13 +415,13 @@ class Double : Number, Comparable { fun mod(other : Short) : Double fun mod(other : Byte) : Double - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range - fun rangeTo(other : Long) : Range - fun rangeTo(other : Int) : Range - fun rangeTo(other : Short) : Range - fun rangeTo(other : Byte) : Range - fun rangeTo(other : Char) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : DoubleRange + fun rangeTo(other : Long) : DoubleRange + fun rangeTo(other : Int) : DoubleRange + fun rangeTo(other : Short) : DoubleRange + fun rangeTo(other : Byte) : DoubleRange + fun rangeTo(other : Char) : DoubleRange fun inc() : Double fun dec() : Double @@ -454,13 +478,13 @@ class Float : Number, Comparable { fun mod(other : Byte) : Float fun mod(other : Char) : Float - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range - fun rangeTo(other : Long) : Range - fun rangeTo(other : Int) : Range - fun rangeTo(other : Short) : Range - fun rangeTo(other : Byte) : Range - fun rangeTo(other : Char) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange + fun rangeTo(other : Long) : DoubleRange + fun rangeTo(other : Int) : DoubleRange + fun rangeTo(other : Short) : FloatRange + fun rangeTo(other : Byte) : FloatRange + fun rangeTo(other : Char) : FloatRange fun inc() : Float fun dec() : Float @@ -517,8 +541,8 @@ class Long : Number, Comparable { fun mod(other : Byte) : Long fun mod(other : Char) : Long - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : LongRange fun rangeTo(other : Short) : LongRange @@ -588,8 +612,8 @@ class Int : Number, Comparable { fun mod(other : Byte) : Int fun mod(other : Char) : Int - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : IntRange fun rangeTo(other : Short) : IntRange @@ -659,8 +683,8 @@ class Char : Number, Comparable { fun mod(other : Byte) : Int // fun mod(other : Char) : Int - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : IntRange fun rangeTo(other : Short) : ShortRange @@ -722,8 +746,8 @@ class Short : Number, Comparable { fun mod(other : Byte) : Int fun mod(other : Char) : Int - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : IntRange fun rangeTo(other : Short) : ShortRange @@ -785,8 +809,8 @@ class Byte : Number, Comparable { fun mod(other : Byte) : Int fun mod(other : Char) : Int - fun rangeTo(other : Double) : Range - fun rangeTo(other : Float) : Range + fun rangeTo(other : Double) : DoubleRange + fun rangeTo(other : Float) : FloatRange fun rangeTo(other : Long) : LongRange fun rangeTo(other : Int) : IntRange fun rangeTo(other : Short) : ShortRange diff --git a/compiler/testData/codegen/regressions/kt765.kt b/compiler/testData/codegen/regressions/kt765.kt new file mode 100644 index 00000000000..e2869f81853 --- /dev/null +++ b/compiler/testData/codegen/regressions/kt765.kt @@ -0,0 +1,13 @@ +fun box() : String { + System.out?.println(System.out?.println(10.flt..11.flt)) + + for(f in 10.flt..11.flt step 0.3.flt) { + System.out?.println(f) + } + + for(f in 10.dbl..11.dbl step 0.3.dbl) { + System.out?.println(f) + } + + return "OK" +} \ No newline at end of file diff --git a/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java b/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java index d9bafd599bf..261e4450425 100644 --- a/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java +++ b/compiler/tests/org/jetbrains/jet/codegen/PrimitiveTypesTest.java @@ -371,4 +371,8 @@ public class PrimitiveTypesTest extends CodegenTestCase { public void testKt925 () { blackBoxFile("regressions/kt925.kt"); } + + public void testKt765 () { + blackBoxFile("regressions/kt765.kt"); + } } diff --git a/stdlib/src/jet/ByteRange.java b/stdlib/src/jet/ByteRange.java index 4210b7d9f5f..bb81716170e 100644 --- a/stdlib/src/jet/ByteRange.java +++ b/stdlib/src/jet/ByteRange.java @@ -78,8 +78,15 @@ public final class ByteRange implements Range, ByteIterable, JetObject { public MyIterator(byte startValue, int count, int step) { cur = startValue; this.step = step; - reversed = count < 0; - this.count = reversed ? -count : count; + if(count < 0) { + reversed = true; + count = -count; + startValue += count; + } + else { + reversed = false; + } + this.count = count; } @Override diff --git a/stdlib/src/jet/CharRange.java b/stdlib/src/jet/CharRange.java index 53b41a5d542..f7721fb9140 100644 --- a/stdlib/src/jet/CharRange.java +++ b/stdlib/src/jet/CharRange.java @@ -78,8 +78,15 @@ public final class CharRange implements Range, CharIterable, JetObjec public MyIterator(char startValue, int count, int step) { cur = startValue; this.step = step; - reversed = count < 0; - this.count = reversed ? -count : count; + if(count < 0) { + reversed = true; + count = -count; + startValue += count; + } + else { + reversed = false; + } + this.count = count; } @Override diff --git a/stdlib/src/jet/DoubleRange.java b/stdlib/src/jet/DoubleRange.java new file mode 100644 index 00000000000..8020039f222 --- /dev/null +++ b/stdlib/src/jet/DoubleRange.java @@ -0,0 +1,117 @@ +package jet; + +public final class DoubleRange implements Range, JetObject { + private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(DoubleRange.class, false); + + private final double start; + private final double size; + + public DoubleRange(double startValue, double size) { + this.start = startValue; + this.size = size; + } + + @Override + public boolean contains(Double item) { + if (item == null) return false; + if (size >= 0) { + return item >= start && item < start + size; + } + return item <= start && item > start + size; + } + + public DoubleIterator step(double step) { + if(step < 0) + return new MyIterator(getEnd(), -size, -step); + else + return new MyIterator(start, size, step); + } + + public boolean getIsReversed() { + return size < 0; + } + + public double getStart() { + return start; + } + + public double getEnd() { + return size < 0 ? start + size: start + size; + } + + public double getSize() { + return size < 0 ? -size : size; + } + + public DoubleRange minus() { + return new DoubleRange(getEnd(), -size); + } + + @Override + public TypeInfo getTypeInfo() { + return typeInfo; + } + + @Override + public JetObject getOuterObject() { + return null; + } + + public static DoubleRange count(int length) { + return new DoubleRange(0, length); + } + + private static class MyIterator extends DoubleIterator { + private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); + + private double cur; + private double step; + private final double end; + + private final boolean reversed; + + public MyIterator(double startValue, double size, double step) { + cur = startValue; + this.step = step; + if(size < 0) { + reversed = true; + end = startValue-size; + startValue -= size; + } + else { + reversed = false; + this.end = startValue + size; + } + } + + @Override + public boolean getHasNext() { + if(reversed) + return cur >= end; + else + return cur <= end; + } + + @Override + public double nextDouble() { + if(reversed) { + cur -= step; + return cur + step; + } + else { + cur += step; + return cur - step; + } + } + + @Override + public TypeInfo getTypeInfo() { + return typeInfo; + } + + @Override + public JetObject getOuterObject() { + return null; + } + } +} diff --git a/stdlib/src/jet/FloatRange.java b/stdlib/src/jet/FloatRange.java new file mode 100644 index 00000000000..e6b3b8894b2 --- /dev/null +++ b/stdlib/src/jet/FloatRange.java @@ -0,0 +1,117 @@ +package jet; + +public final class FloatRange implements Range, JetObject { + private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(FloatRange.class, false); + + private final float start; + private final float size; + + public FloatRange(float startValue, float size) { + this.start = startValue; + this.size = size; + } + + @Override + public boolean contains(Float item) { + if (item == null) return false; + if (size >= 0) { + return item >= start && item < start + size; + } + return item <= start && item > start + size; + } + + public FloatIterator step(float step) { + if(step < 0) + return new MyIterator(getEnd(), -size, -step); + else + return new MyIterator(start, size, step); + } + + public boolean getIsReversed() { + return size < 0; + } + + public float getStart() { + return start; + } + + public float getEnd() { + return size < 0 ? start + size: start + size; + } + + public float getSize() { + return size < 0 ? -size : size; + } + + public FloatRange minus() { + return new FloatRange(getEnd(), -size); + } + + @Override + public TypeInfo getTypeInfo() { + return typeInfo; + } + + @Override + public JetObject getOuterObject() { + return null; + } + + public static FloatRange count(int length) { + return new FloatRange(0, length); + } + + private static class MyIterator extends FloatIterator { + private final static TypeInfo typeInfo = TypeInfo.getTypeInfo(MyIterator.class, false); + + private float cur; + private float step; + private final float end; + + private final boolean reversed; + + public MyIterator(float startValue, float size, float step) { + cur = startValue; + this.step = step; + if(size < 0) { + reversed = true; + end = startValue-size; + startValue -= size; + } + else { + reversed = false; + this.end = startValue + size; + } + } + + @Override + public boolean getHasNext() { + if(reversed) + return cur >= end; + else + return cur <= end; + } + + @Override + public float nextFloat() { + if(reversed) { + cur -= step; + return cur + step; + } + else { + cur += step; + return cur - step; + } + } + + @Override + public TypeInfo getTypeInfo() { + return typeInfo; + } + + @Override + public JetObject getOuterObject() { + return null; + } + } +} diff --git a/stdlib/src/jet/IntRange.java b/stdlib/src/jet/IntRange.java index 0bc52ada3c5..68d127ded00 100644 --- a/stdlib/src/jet/IntRange.java +++ b/stdlib/src/jet/IntRange.java @@ -79,7 +79,7 @@ public final class IntRange implements Range, IntIterable, JetObject { cur = startValue; this.step = step; if(count < 0) { - reversed = count < 0; + reversed = true; count = -count; startValue += count; } diff --git a/stdlib/src/jet/LongRange.java b/stdlib/src/jet/LongRange.java index 6785f9ecded..50cf408d53f 100644 --- a/stdlib/src/jet/LongRange.java +++ b/stdlib/src/jet/LongRange.java @@ -78,8 +78,15 @@ public final class LongRange implements Range, LongIterable, JetObject { public MyIterator(long startValue, long count, long step) { cur = startValue; this.step = step; - reversed = count < 0; - this.count = reversed ? -count : count; + if(count < 0) { + reversed = true; + count = -count; + startValue += count; + } + else { + reversed = false; + } + this.count = count; } @Override diff --git a/stdlib/src/jet/ShortRange.java b/stdlib/src/jet/ShortRange.java index a3c95dd7258..b00fab53562 100644 --- a/stdlib/src/jet/ShortRange.java +++ b/stdlib/src/jet/ShortRange.java @@ -78,8 +78,15 @@ public final class ShortRange implements Range, ShortIterable, JetObject public MyIterator(short startValue, int count, int step) { cur = startValue; this.step = step; - reversed = count < 0; - this.count = reversed ? -count : count; + if(count < 0) { + reversed = true; + count = -count; + startValue += count; + } + else { + reversed = false; + } + this.count = count; } @Override diff --git a/stdlib/src/jet/runtime/Ranges.java b/stdlib/src/jet/runtime/Ranges.java index 19d20293a12..ff5952afe03 100644 --- a/stdlib/src/jet/runtime/Ranges.java +++ b/stdlib/src/jet/runtime/Ranges.java @@ -48,6 +48,14 @@ public class Ranges { } } + public static FloatRange rangeTo(byte from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(byte from, double to) { + return new DoubleRange(from, to-from); + } + public static CharRange rangeTo(byte from, char to) { if(from > to) { return new CharRange((char) from, to-from-1); @@ -93,6 +101,14 @@ public class Ranges { } } + public static FloatRange rangeTo(short from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(short from, double to) { + return new DoubleRange(from, to-from); + } + public static ShortRange rangeTo(short from, char to) { if(from > to) { return new ShortRange(from, to-from-1); @@ -138,6 +154,14 @@ public class Ranges { } } + public static FloatRange rangeTo(int from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(int from, double to) { + return new DoubleRange(from, to-from); + } + public static IntRange rangeTo(int from, char to) { if(from > to) { return new IntRange(from, to-from-1); @@ -183,6 +207,14 @@ public class Ranges { } } + public static FloatRange rangeTo(long from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(long from, double to) { + return new DoubleRange(from, to-from); + } + public static LongRange rangeTo(long from, char to) { if(from > to) { return new LongRange(from, to-from-1); @@ -192,6 +224,62 @@ public class Ranges { } } + public static FloatRange rangeTo(float from, byte to) { + return new FloatRange(from, to-from); + } + + public static FloatRange rangeTo(float from, short to) { + return new FloatRange(from, to-from); + } + + public static FloatRange rangeTo(float from, int to) { + return new FloatRange(from, to-from); + } + + public static FloatRange rangeTo(float from, long to) { + return new FloatRange(from, to-from); + } + + public static FloatRange rangeTo(float from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(float from, double to) { + return new DoubleRange(from, to-from); + } + + public static FloatRange rangeTo(float from, char to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, byte to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, short to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, int to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, long to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, float to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, double to) { + return new DoubleRange(from, to-from); + } + + public static DoubleRange rangeTo(double from, char to) { + return new DoubleRange(from, to-from); + } + public static CharRange rangeTo(char from, byte to) { if(from > to) { return new CharRange(from, to-from-1); @@ -228,6 +316,14 @@ public class Ranges { } } + public static FloatRange rangeTo(char from, float to) { + return new FloatRange(from, to-from); + } + + public static DoubleRange rangeTo(char from, double to) { + return new DoubleRange(from, to-from); + } + public static CharRange rangeTo(char from, char to) { if(from > to) { return new CharRange(from, to-from-1); @@ -238,7 +334,7 @@ public class Ranges { } public static void main(String[] args) { - List strings = Arrays.asList("byte", "short", "int", "long", /*"float", "double",*/ "char"); + List strings = Arrays.asList("byte", "short", "int", "long", "float", "double", "char"); for(String t1 : strings) for(String t2 : strings) { String resType; @@ -264,14 +360,21 @@ public class Ranges { resType = "ByteRange"; } - System.out.println("\npublic static " + resType + " rangeTo(" + t1 + " from, " + t2 + " to) {" + - "\n if(from > to) {\n" + - " return new " + resType + "(from, to-from-1);\n" + - " }\n" + - " else {\n" + - " return new " + resType + "(from, to-from+1);\n" + - " }\n" + - "}"); + if(resType.equals("FloatRange") || resType.equals("DoubleRange")) { + System.out.println("\npublic static " + resType + " rangeTo(" + t1 + " from, " + t2 + " to) {\n" + + " return new " + resType + "(from, to-from);\n" + + "}"); + } + else { + System.out.println("\npublic static " + resType + " rangeTo(" + t1 + " from, " + t2 + " to) {" + + "\n if(from > to) {\n" + + " return new " + resType + "(from, to-from-1);\n" + + " }\n" + + " else {\n" + + " return new " + resType + "(from, to-from+1);\n" + + " }\n" + + "}"); + } } } } From 430b973458d98889625b88451a75bc5b691b8d4a Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 21:22:50 +0400 Subject: [PATCH 05/10] better error reporting in commandline compiler --- .../jet/compiler/CompileEnvironment.java | 7 ++++--- .../org/jetbrains/jet/cli/KotlinCompiler.java | 19 +++++++++++++++---- 2 files changed, 19 insertions(+), 7 deletions(-) diff --git a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java index 1eab1a0e29b..277273aa0ee 100644 --- a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java +++ b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java @@ -120,7 +120,7 @@ public class CompileEnvironment { rtJar = findActiveRtJar(failOnError); if ((rtJar == null || !rtJar.exists())) { - throw new CompileEnvironmentException("No rt.jar found under JAVA_HOME=" + javaHome); + throw new CompileEnvironmentException("No JDK rt.jar found under JAVA_HOME=" + javaHome); } } return rtJar; @@ -337,7 +337,7 @@ public class CompileEnvironment { } } - public void compileBunchOfSources(String sourceFileOrDir, String jar, String outputDir, boolean includeRuntime) { + public boolean compileBunchOfSources(String sourceFileOrDir, String jar, String outputDir, boolean includeRuntime) { CompileSession session = new CompileSession(myEnvironment); session.addSources(sourceFileOrDir); session.addStdLibSources(false); @@ -350,7 +350,7 @@ public class CompileEnvironment { } } if (!session.analyze(myErrorStream)) { - return; + return false; } ClassFileFactory factory = session.generate(); @@ -367,6 +367,7 @@ public class CompileEnvironment { else { throw new CompileEnvironmentException("Output directory or jar file is not specified - no files will be saved to the disk"); } + return true; } public static void writeToOutputDirectory(ClassFileFactory factory, final String outputDir) { diff --git a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java index 56db85a522d..e752317b947 100644 --- a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java +++ b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java @@ -33,9 +33,14 @@ public class KotlinCompiler { try { Args.parse(arguments, args); } - catch (Throwable t) { + catch (IllegalArgumentException e) { System.out.println("Usage: KotlinCompiler [-output |-jar ] [-src |-module ] [-includeRuntime]"); + System.exit(1); + return; + } + catch (Throwable t) { t.printStackTrace(); + System.exit(1); return; } @@ -44,7 +49,8 @@ public class KotlinCompiler { try { environment.setJavaRuntime(CompileEnvironment.findRtJar(true)); if (!environment.initializeKotlinRuntime()) { - System.out.println("No runtime library found"); + System.err.println("No Kotlin runtime library found"); + System.exit(1); return; } @@ -53,10 +59,15 @@ public class KotlinCompiler { return; } else { - environment.compileBunchOfSources(arguments.src, arguments.jar, arguments.outputDir, arguments.includeRuntime); + if (!environment.compileBunchOfSources(arguments.src, arguments.jar, arguments.outputDir, arguments.includeRuntime)) { + System.exit(1); + return; + } } } catch (CompileEnvironmentException e) { - System.out.println(e.getMessage()); + System.err.println(e.getMessage()); + System.exit(1); + return; } } From 09d0780fe6aa7cd42f7aee3c0b3aae8aed8429bf Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 21:22:55 +0400 Subject: [PATCH 06/10] developer option to exclude sources to compile stdlib --- build.xml | 1 + .../src/org/jetbrains/jet/compiler/CompileEnvironment.java | 6 ++++-- compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java | 4 +++- 3 files changed, 8 insertions(+), 3 deletions(-) diff --git a/build.xml b/build.xml index 952ccdd3dba..480951def0d 100644 --- a/build.xml +++ b/build.xml @@ -35,6 +35,7 @@ + diff --git a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java index 277273aa0ee..66c129f3ef9 100644 --- a/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java +++ b/compiler/backend/src/org/jetbrains/jet/compiler/CompileEnvironment.java @@ -337,10 +337,12 @@ public class CompileEnvironment { } } - public boolean compileBunchOfSources(String sourceFileOrDir, String jar, String outputDir, boolean includeRuntime) { + public boolean compileBunchOfSources(String sourceFileOrDir, String jar, String outputDir, boolean includeRuntime, boolean includeSources) { CompileSession session = new CompileSession(myEnvironment); session.addSources(sourceFileOrDir); - session.addStdLibSources(false); + if (includeSources) { + session.addStdLibSources(false); + } String mainClass = null; for (JetFile file : session.getSourceFileNamespaces()) { diff --git a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java index e752317b947..8daf27b6cf8 100644 --- a/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java +++ b/compiler/cli/src/org/jetbrains/jet/cli/KotlinCompiler.java @@ -25,6 +25,8 @@ public class KotlinCompiler { public String module; @Argument(value = "includeRuntime", description = "include Kotlin runtime in to resulting jar") public boolean includeRuntime; + @Argument(value = "excludeStdlib", description = "do not load stdlib (to compile stdlib itself)") + public boolean excludeStdlib; } public static void main(String[] args) { @@ -59,7 +61,7 @@ public class KotlinCompiler { return; } else { - if (!environment.compileBunchOfSources(arguments.src, arguments.jar, arguments.outputDir, arguments.includeRuntime)) { + if (!environment.compileBunchOfSources(arguments.src, arguments.jar, arguments.outputDir, arguments.includeRuntime, !arguments.excludeStdlib)) { System.exit(1); return; } From 8336c647878562f10c315461d259fa69abd43e48 Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 21:23:00 +0400 Subject: [PATCH 07/10] bin/kotlin script --- bin/kotlin | 30 ++++++++++++++++++++++++++++++ 1 file changed, 30 insertions(+) create mode 100755 bin/kotlin diff --git a/bin/kotlin b/bin/kotlin new file mode 100755 index 00000000000..dac7f9ffec1 --- /dev/null +++ b/bin/kotlin @@ -0,0 +1,30 @@ +#!/bin/sh -e + +die() { + echo "$@" >&2 + exit 1 +} + +root=`cd $(dirname $0)/..; pwd` + +ideaRoot= +for d in /Applications/Nika-*.app; do + if [ -d "$d/lib" ]; then + ideaRoot="$d" + break + fi +done + +test -n "$ideaRoot" || die "Idea root not found" + +classpath="$root/out/production/cli" +classpath="$classpath:$root/out/production/backend:$root/out/production/frontend:$root/out/production/frontend.java" +classpath="$classpath:$root/out/production/stdlib" +classpath="$classpath:$root/lib/*:$ideaRoot/lib/*:$ideaRoot/lib/rt/*" + +exec java \ + -classpath "$classpath" \ + org.jetbrains.jet.cli.KotlinCompiler \ + "$@" + +# vim: set ts=4 sw=4 et: From 4c3ebe7ea90925641444b244f12a67965b656edb Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 21:23:07 +0400 Subject: [PATCH 08/10] option to override ideaSDK path --- build.xml | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/build.xml b/build.xml index 480951def0d..c6aa63a9a03 100644 --- a/build.xml +++ b/build.xml @@ -2,9 +2,10 @@ + - + @@ -74,7 +75,7 @@ - + From 2338af30a0c1c64fdba384008e7b5203b7840dd5 Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 23:21:31 +0400 Subject: [PATCH 09/10] arrays in signatures: more tests, fix bugs --- .../resolve/java/JavaDescriptorResolver.java | 8 +++---- .../resolve/java/JavaSemanticServices.java | 2 +- .../resolve/java/JavaTypeTransformer.java | 6 +++-- .../java/JetTypeJetSignatureReader.java | 23 +++++++++++++++---- .../jet/lang/types/JetStandardLibrary.java | 8 +++++++ compiler/testData/readClass/type/IntArray.kt | 3 +++ .../writeSignature/ArrayOfCharSequence.kt | 6 +++++ .../testData/writeSignature/ArrayOfInt.kt | 6 +++++ compiler/testData/writeSignature/IntArray.kt | 6 +++++ ...{ListOfString.kt => ListOfCharSequence.kt} | 0 10 files changed, 56 insertions(+), 12 deletions(-) create mode 100644 compiler/testData/readClass/type/IntArray.kt create mode 100644 compiler/testData/writeSignature/ArrayOfCharSequence.kt create mode 100644 compiler/testData/writeSignature/ArrayOfInt.kt create mode 100644 compiler/testData/writeSignature/IntArray.kt rename compiler/testData/writeSignature/{ListOfString.kt => ListOfCharSequence.kt} (100%) diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaDescriptorResolver.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaDescriptorResolver.java index fb9e23b0585..dd239673dfe 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaDescriptorResolver.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaDescriptorResolver.java @@ -138,7 +138,7 @@ public class JavaDescriptorResolver { @Nullable public ClassDescriptor resolveClass(@NotNull PsiClass psiClass) { String qualifiedName = psiClass.getQualifiedName(); - + if (qualifiedName.endsWith(JvmAbi.TRAIT_IMPL_SUFFIX)) { // TODO: only if -$$TImpl class is created by Kotlin return null; @@ -161,7 +161,7 @@ public class JavaDescriptorResolver { @Nullable public ClassDescriptor resolveClass(@NotNull String qualifiedName) { - + if (qualifiedName.endsWith(JvmAbi.TRAIT_IMPL_SUFFIX)) { // TODO: only if -$$TImpl class is created by Kotlin return null; @@ -356,7 +356,7 @@ public class JavaDescriptorResolver { @Override public JetSignatureVisitor visitClassBound() { - return new JetTypeJetSignatureReader(JavaDescriptorResolver.this, semanticServices.getJetSemanticServices().getStandardLibrary(), typeVariableResolver) { + return new JetTypeJetSignatureReader(semanticServices, semanticServices.getJetSemanticServices().getStandardLibrary(), typeVariableResolver) { @Override protected void done(@NotNull JetType jetType) { if (isJavaLangObject(jetType)) { @@ -369,7 +369,7 @@ public class JavaDescriptorResolver { @Override public JetSignatureVisitor visitInterfaceBound() { - return new JetTypeJetSignatureReader(JavaDescriptorResolver.this, semanticServices.getJetSemanticServices().getStandardLibrary(), typeVariableResolver) { + return new JetTypeJetSignatureReader(semanticServices, semanticServices.getJetSemanticServices().getStandardLibrary(), typeVariableResolver) { @Override protected void done(@NotNull JetType jetType) { upperBounds.add(jetType); diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaSemanticServices.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaSemanticServices.java index c4b9053e3a1..ab9b7350f29 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaSemanticServices.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaSemanticServices.java @@ -21,7 +21,7 @@ public class JavaSemanticServices { public JavaSemanticServices(Project project, JetSemanticServices jetSemanticServices, BindingTrace trace) { this.trace = trace; this.descriptorResolver = new JavaDescriptorResolver(project, this); - this.typeTransformer = new JavaTypeTransformer(jetSemanticServices.getStandardLibrary(), descriptorResolver); + this.typeTransformer = new JavaTypeTransformer(this, jetSemanticServices.getStandardLibrary(), descriptorResolver); this.jetSemanticServices = jetSemanticServices; } diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java index 40a6c60b35d..82d923cec66 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java @@ -19,12 +19,14 @@ import java.util.Map; */ public class JavaTypeTransformer { + private final JavaSemanticServices javaSemanticServices; private final JavaDescriptorResolver resolver; private final JetStandardLibrary standardLibrary; private Map primitiveTypesMap; private Map classTypesMap; - public JavaTypeTransformer(JetStandardLibrary standardLibrary, JavaDescriptorResolver resolver) { + public JavaTypeTransformer(JavaSemanticServices javaSemanticServices, JetStandardLibrary standardLibrary, JavaDescriptorResolver resolver) { + this.javaSemanticServices = javaSemanticServices; this.resolver = resolver; this.standardLibrary = standardLibrary; } @@ -61,7 +63,7 @@ public class JavaTypeTransformer { @NotNull public JetType transformToType(@NotNull String kotlinSignature, TypeVariableResolver typeVariableResolver) { final JetType[] r = new JetType[1]; - JetTypeJetSignatureReader reader = new JetTypeJetSignatureReader(resolver, standardLibrary, typeVariableResolver) { + JetTypeJetSignatureReader reader = new JetTypeJetSignatureReader(javaSemanticServices, standardLibrary, typeVariableResolver) { @Override protected void done(@NotNull JetType jetType) { r[0] = jetType; diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java index 520da450766..11d26b269d4 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java @@ -2,7 +2,6 @@ package org.jetbrains.jet.lang.resolve.java; import org.jetbrains.annotations.NotNull; import org.jetbrains.jet.lang.descriptors.ClassDescriptor; -import org.jetbrains.jet.lang.descriptors.TypeParameterDescriptor; import org.jetbrains.jet.lang.descriptors.annotations.AnnotationDescriptor; import org.jetbrains.jet.lang.types.ErrorUtils; import org.jetbrains.jet.lang.types.JetStandardClasses; @@ -24,12 +23,14 @@ import java.util.List; */ public abstract class JetTypeJetSignatureReader extends JetSignatureExceptionsAdapter { + private final JavaSemanticServices javaSemanticServices; private final JavaDescriptorResolver javaDescriptorResolver; private final JetStandardLibrary jetStandardLibrary; private final TypeVariableResolver typeVariableResolver; - public JetTypeJetSignatureReader(JavaDescriptorResolver javaDescriptorResolver, JetStandardLibrary jetStandardLibrary, TypeVariableResolver typeVariableResolver) { - this.javaDescriptorResolver = javaDescriptorResolver; + public JetTypeJetSignatureReader(JavaSemanticServices javaSemanticServices, JetStandardLibrary jetStandardLibrary, TypeVariableResolver typeVariableResolver) { + this.javaSemanticServices = javaSemanticServices; + this.javaDescriptorResolver = javaSemanticServices.getDescriptorResolver(); this.jetStandardLibrary = jetStandardLibrary; this.typeVariableResolver = typeVariableResolver; } @@ -114,7 +115,7 @@ public abstract class JetTypeJetSignatureReader extends JetSignatureExceptionsAd @Override public JetSignatureVisitor visitTypeArgument(final char wildcard) { - return new JetTypeJetSignatureReader(javaDescriptorResolver, jetStandardLibrary, typeVariableResolver) { + return new JetTypeJetSignatureReader(javaSemanticServices, jetStandardLibrary, typeVariableResolver) { @Override protected void done(@NotNull JetType jetType) { @@ -125,7 +126,19 @@ public abstract class JetTypeJetSignatureReader extends JetSignatureExceptionsAd @Override public JetSignatureVisitor visitArrayType(final boolean nullable) { - return new JetTypeJetSignatureReader(javaDescriptorResolver, jetStandardLibrary, typeVariableResolver) { + return new JetTypeJetSignatureReader(javaSemanticServices, jetStandardLibrary, typeVariableResolver) { + @Override + public void visitBaseType(char descriptor, boolean nullable) { + JetType primitiveType = getPrimitiveType(descriptor, nullable); + JetType arrayType; + if (!nullable) { + arrayType = jetStandardLibrary.getPrimitiveArrayType(primitiveType); + } else { + arrayType = TypeUtils.makeNullableAsSpecified(jetStandardLibrary.getArrayType(primitiveType), nullable); + } + JetTypeJetSignatureReader.this.done(arrayType); + } + @Override protected void done(@NotNull JetType jetType) { JetType arrayType = TypeUtils.makeNullableAsSpecified(jetStandardLibrary.getArrayType(jetType), nullable); diff --git a/compiler/frontend/src/org/jetbrains/jet/lang/types/JetStandardLibrary.java b/compiler/frontend/src/org/jetbrains/jet/lang/types/JetStandardLibrary.java index 186e94242d3..6c23f5d6422 100644 --- a/compiler/frontend/src/org/jetbrains/jet/lang/types/JetStandardLibrary.java +++ b/compiler/frontend/src/org/jetbrains/jet/lang/types/JetStandardLibrary.java @@ -504,6 +504,14 @@ public class JetStandardLibrary { initStdClasses(); return doubleArrayType; } + + public JetType getPrimitiveArrayType(JetType jetType) { + if (jetType.equals(getIntType())) { + return getIntArrayType(); + } else { + throw new IllegalStateException("not implemented"); + } + } public ClassDescriptor getByteArrayClass() { initStdClasses(); diff --git a/compiler/testData/readClass/type/IntArray.kt b/compiler/testData/readClass/type/IntArray.kt new file mode 100644 index 00000000000..8fc8ef58b92 --- /dev/null +++ b/compiler/testData/readClass/type/IntArray.kt @@ -0,0 +1,3 @@ +package test + +fun nothing(): IntArray = throw Exception() diff --git a/compiler/testData/writeSignature/ArrayOfCharSequence.kt b/compiler/testData/writeSignature/ArrayOfCharSequence.kt new file mode 100644 index 00000000000..ff263b502d5 --- /dev/null +++ b/compiler/testData/writeSignature/ArrayOfCharSequence.kt @@ -0,0 +1,6 @@ +fun never(): Array = throw Exception() + +// method: namespace::never +// jvm signature: ()[Ljava/lang/CharSequence; +// generic signature: null +// kotlin signature: ()[Ljava/lang/CharSequence; // TODO: need to skip kotlin signature diff --git a/compiler/testData/writeSignature/ArrayOfInt.kt b/compiler/testData/writeSignature/ArrayOfInt.kt new file mode 100644 index 00000000000..934bbb102d6 --- /dev/null +++ b/compiler/testData/writeSignature/ArrayOfInt.kt @@ -0,0 +1,6 @@ +fun never(): Array = throw Exception() + +// method: namespace::never +// jvm signature: ()[Ljava/lang/Integer; +// generic signature: null +// kotlin signature: ()[Ljava/lang/Integer; // TODO: need to skip kotlin signature diff --git a/compiler/testData/writeSignature/IntArray.kt b/compiler/testData/writeSignature/IntArray.kt new file mode 100644 index 00000000000..72062baedde --- /dev/null +++ b/compiler/testData/writeSignature/IntArray.kt @@ -0,0 +1,6 @@ +fun never(): IntArray = throw Exception() + +// method: namespace::never +// jvm signature: ()[I +// generic signature: null +// kotlin signature: ()[I // TODO: need to skip kotlin signature diff --git a/compiler/testData/writeSignature/ListOfString.kt b/compiler/testData/writeSignature/ListOfCharSequence.kt similarity index 100% rename from compiler/testData/writeSignature/ListOfString.kt rename to compiler/testData/writeSignature/ListOfCharSequence.kt From 7ebf1ad43300cb35bf8bc8a83ee4df61e9b2c551 Mon Sep 17 00:00:00 2001 From: Stepan Koltsov Date: Fri, 6 Jan 2012 23:21:35 +0400 Subject: [PATCH 10/10] properly read/write int? --- .../lang/resolve/java/JavaTypeTransformer.java | 18 ++++++++++++++++++ .../java/JetTypeJetSignatureReader.java | 8 +++++++- compiler/testData/readClass/type/Int.kt | 3 +++ compiler/testData/readClass/type/IntQ.kt | 3 +++ .../org/jetbrains/jet/WriteSignatureTest.java | 4 ++-- 5 files changed, 33 insertions(+), 3 deletions(-) create mode 100644 compiler/testData/readClass/type/Int.kt create mode 100644 compiler/testData/readClass/type/IntQ.kt diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java index 82d923cec66..96e64c6f08c 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JavaTypeTransformer.java @@ -24,6 +24,7 @@ public class JavaTypeTransformer { private final JetStandardLibrary standardLibrary; private Map primitiveTypesMap; private Map classTypesMap; + private Map classDescriptorMap; public JavaTypeTransformer(JavaSemanticServices javaSemanticServices, JetStandardLibrary standardLibrary, JavaDescriptorResolver resolver) { this.javaSemanticServices = javaSemanticServices; @@ -199,4 +200,21 @@ public class JavaTypeTransformer { } return classTypesMap; } + + public Map getPrimitiveWrappersClassDescriptorMap() { + if (classDescriptorMap == null) { + classDescriptorMap = new HashMap(); + classDescriptorMap.put("java.lang.Byte", standardLibrary.getByte()); + classDescriptorMap.put("java.lang.Short", standardLibrary.getShort()); + classDescriptorMap.put("java.lang.Character", standardLibrary.getChar()); + classDescriptorMap.put("java.lang.Integer", standardLibrary.getInt()); + classDescriptorMap.put("java.lang.Long", standardLibrary.getLong()); + classDescriptorMap.put("java.lang.Float", standardLibrary.getFloat()); + classDescriptorMap.put("java.lang.Double", standardLibrary.getDouble()); + classDescriptorMap.put("java.lang.Boolean", standardLibrary.getBoolean()); + //classDescriptorMap.put("java.lang.Object", standardLibrary.get + classDescriptorMap.put("java.lang.String", standardLibrary.getString()); + } + return classDescriptorMap; + } } diff --git a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java index 11d26b269d4..0f51cf0df1e 100644 --- a/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java +++ b/compiler/frontend.java/src/org/jetbrains/jet/lang/resolve/java/JetTypeJetSignatureReader.java @@ -96,7 +96,13 @@ public abstract class JetTypeJetSignatureReader extends JetSignatureExceptionsAd @Override public void visitClassType(String name, boolean nullable) { String ourName = name.replace('/', '.'); - this.classDescriptor = javaDescriptorResolver.resolveClass(ourName); + + this.classDescriptor = this.javaSemanticServices.getTypeTransformer().getPrimitiveWrappersClassDescriptorMap().get(ourName); + + if (this.classDescriptor == null) { + this.classDescriptor = javaDescriptorResolver.resolveClass(ourName); + } + if (this.classDescriptor == null) { throw new IllegalStateException("class not found by name: " + ourName); // TODO: wrong exception } diff --git a/compiler/testData/readClass/type/Int.kt b/compiler/testData/readClass/type/Int.kt new file mode 100644 index 00000000000..0a3853f134f --- /dev/null +++ b/compiler/testData/readClass/type/Int.kt @@ -0,0 +1,3 @@ +package test + +fun fff(): Int = 1 diff --git a/compiler/testData/readClass/type/IntQ.kt b/compiler/testData/readClass/type/IntQ.kt new file mode 100644 index 00000000000..8ccad22eeb6 --- /dev/null +++ b/compiler/testData/readClass/type/IntQ.kt @@ -0,0 +1,3 @@ +package test + +fun fff(): Int? = 1 diff --git a/compiler/tests/org/jetbrains/jet/WriteSignatureTest.java b/compiler/tests/org/jetbrains/jet/WriteSignatureTest.java index 278772c9dae..f648e4dc260 100644 --- a/compiler/tests/org/jetbrains/jet/WriteSignatureTest.java +++ b/compiler/tests/org/jetbrains/jet/WriteSignatureTest.java @@ -210,8 +210,8 @@ public class WriteSignatureTest extends TestCaseWithTmpdir { new ClassReader(classInputStream).accept(visitor, ClassReader.SKIP_CODE|ClassReader.SKIP_DEBUG|ClassReader.SKIP_FRAMES); - Assert.assertNotNull(visitor.readSignature); - + Assert.assertNotNull("method not found: " + className + "::" + methodName, visitor.readSignature); + return visitor.readSignature; } finally { Closeables.closeQuietly(classInputStream);