# HG changeset patch # User Chris Seaton # Date 1428259906 -3600 # Node ID 65d29fa813977f5ba065559d6c6ebf8afa50948e # Parent f0f725496f2ac47176ec8b4ffc31cf9390c7f124 DSL: add support for hex, oct and binary integer literals. diff -r f0f725496f2a -r 65d29fa81397 graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/IntegerLiteralGuardsTest.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/IntegerLiteralGuardsTest.java Sun Apr 05 19:51:46 2015 +0100 @@ -0,0 +1,117 @@ +/* + * Copyright (c) 2015, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.truffle.api.dsl.test; + +import static com.oracle.truffle.api.dsl.test.TestHelper.*; +import static org.junit.Assert.*; + +import org.junit.*; + +import com.oracle.truffle.api.*; +import com.oracle.truffle.api.dsl.*; +import com.oracle.truffle.api.dsl.test.IntegerLiteralGuardsTestFactory.BinaryLiteralTestFactory; +import com.oracle.truffle.api.dsl.test.IntegerLiteralGuardsTestFactory.DecimalLiteralTestFactory; +import com.oracle.truffle.api.dsl.test.IntegerLiteralGuardsTestFactory.HexLiteralTestFactory; +import com.oracle.truffle.api.dsl.test.IntegerLiteralGuardsTestFactory.OctalLiteralTestFactory; +import com.oracle.truffle.api.dsl.test.TypeSystemTest.ValueNode; + +@SuppressWarnings("unused") +public class IntegerLiteralGuardsTest { + + @Test + public void testDecimalLiteral() { + CallTarget root = createCallTarget(DecimalLiteralTestFactory.getInstance()); + assertEquals("do1", root.call(14)); + } + + @NodeChild + static class DecimalLiteralTest extends ValueNode { + @Specialization(guards = "value == 14") + static String do1(int value) { + return "do1"; + } + + @Specialization + static String do2(int value) { + return "do2"; + } + } + + @Test + public void testHexLiteral() { + CallTarget root = createCallTarget(HexLiteralTestFactory.getInstance()); + assertEquals("do1", root.call(20)); + } + + @NodeChild + static class HexLiteralTest extends ValueNode { + @Specialization(guards = "value == 0x14") + static String do1(int value) { + return "do1"; + } + + @Specialization + static String do2(int value) { + return "do2"; + } + } + + @Test + public void testOctalLiteral() { + CallTarget root = createCallTarget(OctalLiteralTestFactory.getInstance()); + assertEquals("do1", root.call(12)); + } + + @NodeChild + static class OctalLiteralTest extends ValueNode { + @Specialization(guards = "value == 014") + static String do1(int value) { + return "do1"; + } + + @Specialization + static String do2(int value) { + return "do2"; + } + } + + @Test + public void testBinaryLiteral() { + CallTarget root = createCallTarget(BinaryLiteralTestFactory.getInstance()); + assertEquals("do1", root.call(50)); + } + + @NodeChild + static class BinaryLiteralTest extends ValueNode { + @Specialization(guards = "value == 0b110010") + static String do1(int value) { + return "do1"; + } + + @Specialization + static String do2(int value) { + return "do2"; + } + } + +} diff -r f0f725496f2a -r 65d29fa81397 graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/DSLExpressionResolver.java --- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/DSLExpressionResolver.java Sun Apr 05 09:45:58 2015 +0200 +++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/DSLExpressionResolver.java Sun Apr 05 19:51:46 2015 +0100 @@ -226,7 +226,25 @@ public void visitIntLiteral(IntLiteral binary) { try { binary.setResolvedType(context.getType(int.class)); - binary.setResolvedValueInt(Integer.parseInt(binary.getLiteral())); + + final int base; + final String literal; + + if (binary.getLiteral().startsWith("0x")) { + base = 16; + literal = binary.getLiteral().substring(2); + } else if (binary.getLiteral().startsWith("0b")) { + base = 2; + literal = binary.getLiteral().substring(2); + } else if (binary.getLiteral().startsWith("0")) { + base = 8; + literal = binary.getLiteral(); + } else { + base = 10; + literal = binary.getLiteral(); + } + + binary.setResolvedValueInt(Integer.parseInt(literal, base)); } catch (NumberFormatException e) { throw new InvalidExpressionException(String.format("Type mismatch: cannot convert from String '%s' to int", binary.getLiteral())); } diff -r f0f725496f2a -r 65d29fa81397 graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Expression.atg --- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Expression.atg Sun Apr 05 09:45:58 2015 +0200 +++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Expression.atg Sun Apr 05 19:51:46 2015 +0100 @@ -34,11 +34,14 @@ letter = 'A' .. 'Z' + 'a' .. 'z' + '_' + '$'. nonZeroDigit = "123456789". digit = '0' + nonZeroDigit . +hexDigit = "0123456789abcdefABCDEF". +octDigit = "01234567". +binaryDigit = "01". TOKENS identifier = letter {letter | digit}. -numericLiteral = "0" | nonZeroDigit { digit }. +numericLiteral = "0" ( "x" { hexDigit } | "b" { binaryDigit } | { octDigit } ) | nonZeroDigit { digit }. PRAGMAS diff -r f0f725496f2a -r 65d29fa81397 graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Scanner.java --- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Scanner.java Sun Apr 05 09:45:58 2015 +0200 +++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/expression/Scanner.java Sun Apr 05 19:51:46 2015 +0100 @@ -340,17 +340,17 @@ for (int i = 65; i <= 90; ++i) start.set(i, 1); for (int i = 95; i <= 95; ++i) start.set(i, 1); for (int i = 97; i <= 122; ++i) start.set(i, 1); - for (int i = 49; i <= 57; ++i) start.set(i, 2); - start.set(48, 3); - start.set(124, 4); - start.set(60, 15); - start.set(62, 16); - start.set(61, 8); - start.set(33, 17); - start.set(40, 11); - start.set(41, 12); - start.set(44, 13); - start.set(46, 14); + for (int i = 49; i <= 57; ++i) start.set(i, 6); + start.set(48, 2); + start.set(124, 7); + start.set(60, 18); + start.set(62, 19); + start.set(61, 11); + start.set(33, 20); + start.set(40, 14); + start.set(41, 15); + start.set(44, 16); + start.set(46, 17); start.set(Buffer.EOF, -1); } @@ -417,7 +417,7 @@ tval = newBuf; } if (ch != Buffer.EOF) { - tval[tlen++] = (char)ch; + tval[tlen++] = (char)ch; NextCh(); } @@ -435,7 +435,7 @@ } Token NextToken() { - while (ch == ' ' || + while (ch == ' ' || false ) NextCh(); @@ -470,45 +470,61 @@ else {t.kind = 1; break loop;} case 2: recEnd = pos; recKind = 2; - if (ch >= '0' && ch <= '9') {AddCh(); state = 2; break;} + if (ch >= '0' && ch <= '7') {AddCh(); state = 5; break;} + else if (ch == 'x') {AddCh(); state = 3; break;} + else if (ch == 'b') {AddCh(); state = 4; break;} else {t.kind = 2; break loop;} case 3: - {t.kind = 2; break loop;} + recEnd = pos; recKind = 2; + if (ch >= '0' && ch <= '9' || ch >= 'A' && ch <= 'F' || ch >= 'a' && ch <= 'f') {AddCh(); state = 3; break;} + else {t.kind = 2; break loop;} case 4: - if (ch == '|') {AddCh(); state = 5; break;} - else {state = 0; break;} + recEnd = pos; recKind = 2; + if (ch >= '0' && ch <= '1') {AddCh(); state = 4; break;} + else {t.kind = 2; break loop;} case 5: - {t.kind = 3; break loop;} + recEnd = pos; recKind = 2; + if (ch >= '0' && ch <= '7') {AddCh(); state = 5; break;} + else {t.kind = 2; break loop;} case 6: - {t.kind = 5; break loop;} + recEnd = pos; recKind = 2; + if (ch >= '0' && ch <= '9') {AddCh(); state = 6; break;} + else {t.kind = 2; break loop;} case 7: - {t.kind = 7; break loop;} - case 8: - if (ch == '=') {AddCh(); state = 9; break;} + if (ch == '|') {AddCh(); state = 8; break;} else {state = 0; break;} + case 8: + {t.kind = 3; break loop;} case 9: - {t.kind = 8; break loop;} + {t.kind = 5; break loop;} case 10: - {t.kind = 9; break loop;} + {t.kind = 7; break loop;} case 11: - {t.kind = 11; break loop;} + if (ch == '=') {AddCh(); state = 12; break;} + else {state = 0; break;} case 12: - {t.kind = 12; break loop;} + {t.kind = 8; break loop;} case 13: - {t.kind = 13; break loop;} + {t.kind = 9; break loop;} case 14: + {t.kind = 11; break loop;} + case 15: + {t.kind = 12; break loop;} + case 16: + {t.kind = 13; break loop;} + case 17: {t.kind = 14; break loop;} - case 15: + case 18: recEnd = pos; recKind = 4; - if (ch == '=') {AddCh(); state = 6; break;} + if (ch == '=') {AddCh(); state = 9; break;} else {t.kind = 4; break loop;} - case 16: + case 19: recEnd = pos; recKind = 6; - if (ch == '=') {AddCh(); state = 7; break;} + if (ch == '=') {AddCh(); state = 10; break;} else {t.kind = 6; break loop;} - case 17: + case 20: recEnd = pos; recKind = 10; - if (ch == '=') {AddCh(); state = 10; break;} + if (ch == '=') {AddCh(); state = 13; break;} else {t.kind = 10; break loop;} }