Skip to content

Commit

Permalink
Dispatch of to_text, is_a & co. on intersection types (#12192)
Browse files Browse the repository at this point in the history
  • Loading branch information
JaroslavTulach authored Feb 12, 2025
1 parent f815f49 commit 595e0a8
Show file tree
Hide file tree
Showing 44 changed files with 814 additions and 400 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
package org.enso.interpreter.node.expression.builtin.number.decimal;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThrows;

import java.math.BigInteger;
import org.enso.interpreter.runtime.data.EnsoMultiValue;
import org.enso.interpreter.runtime.data.Type;
import org.enso.interpreter.runtime.error.PanicException;
import org.enso.interpreter.runtime.number.EnsoBigInteger;
import org.enso.interpreter.test.WrappedPrimitive;
import org.enso.test.utils.ContextUtils;
import org.enso.test.utils.TestRootNode;
import org.graalvm.polyglot.Context;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;

/** Tests Truffle nodes for integer operations. */
public class FloatTest {

private static AbsNode absNode;
private static AddNode addNode;
private static TestRootNode root;
private static Context ctx;

@BeforeClass
public static void setup() {
ctx = ContextUtils.createDefaultContext();
ContextUtils.executeInContext(
ctx,
() -> {
absNode = AbsNode.build();
addNode = AddNode.build();

root = new TestRootNode();
root.insertChildren(absNode, addNode);
return null;
});
}

@AfterClass
public static void teardown() {
ctx.close();
ctx = null;
}

private static final EnsoBigInteger bigInt =
new EnsoBigInteger(new BigInteger("1000000000000000000000000000000000000"));
private static final EnsoBigInteger bigIntNegative =
new EnsoBigInteger(new BigInteger("-1000000000000000000000000000000000000"));

@Test
public void testAbs23() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23.1, absNode.execute(23.1), 0.01);
assertEquals(23.1, absNode.execute(-23.1), 0.01);
return null;
});
}

@Test
public void testAdd21And1Point0() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23.1, addNode.execute(22.0, 1.1), 0.01);
return null;
});
}

@Test
public void testAdd21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23.1, addNode.execute(22.1, 1L), 0.01);
return null;
});
}

@Test
public void testAddMulti21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
var nn = EnsoMultiValue.NewNode.getUncached();
var leak = ContextUtils.leakContext(ctx);
var floatType = leak.getBuiltins().number().getFloat();
var textType = leak.getBuiltins().text();
var both = new Type[] {floatType, textType};
var twentyTwoHello = nn.newValue(both, 2, 0, new Object[] {22.1, "Hello"});
assertEquals(23.2, addNode.execute(1.1, twentyTwoHello), 0.01);
return null;
});
}

@Test
public void testAddInterop21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
var twentyOne = new WrappedPrimitive(21.1);
assertEquals(23.1, addNode.execute(2.0, twentyOne), 0.01);
return null;
});
}

@Test
public void testAddDoubleAndText() {
ContextUtils.executeInContext(
ctx,
() -> {
assertThrows(PanicException.class, () -> addNode.execute(23.1, "Hello"));
return null;
});
}
}
Original file line number Diff line number Diff line change
@@ -1,28 +1,28 @@
package org.enso.interpreter.test;
package org.enso.interpreter.node.expression.builtin.number.integer;

import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertThrows;
import static org.junit.Assert.assertTrue;

import java.math.BigInteger;
import org.enso.interpreter.node.expression.builtin.number.integer.AbsNode;
import org.enso.interpreter.node.expression.builtin.number.integer.AddNode;
import org.enso.interpreter.runtime.data.EnsoMultiValue;
import org.enso.interpreter.runtime.data.Type;
import org.enso.interpreter.runtime.error.PanicException;
import org.enso.interpreter.runtime.number.EnsoBigInteger;
import org.enso.interpreter.test.WrappedPrimitive;
import org.enso.test.utils.ContextUtils;
import org.enso.test.utils.TestRootNode;
import org.graalvm.polyglot.Context;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;
import org.junit.experimental.theories.Theories;
import org.junit.runner.RunWith;

/** Tests Truffle nodes for integer operations. */
@RunWith(Theories.class)
public class IntegerTest {

private static AbsNode absNode;
private static AddNode addNode;
private static TestRootNode root;
private static Context ctx;

@BeforeClass
Expand All @@ -33,6 +33,9 @@ public static void setup() {
() -> {
absNode = AbsNode.build();
addNode = AddNode.build();

root = new TestRootNode();
root.insertChildren(absNode, addNode);
return null;
});
}
Expand All @@ -49,15 +52,33 @@ public static void teardown() {
new EnsoBigInteger(new BigInteger("-1000000000000000000000000000000000000"));

@Test
public void testAbs() {
public void testAbs23() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23L, absNode.execute(23L));
assertEquals(23L, absNode.execute(-23L));
return null;
});
}

@Test
public void testAbsBig() {
ContextUtils.executeInContext(
ctx,
() -> {
assertTrue(absNode.execute(Long.MIN_VALUE) instanceof EnsoBigInteger);
assertEquals(bigInt, absNode.execute(bigInt));
assertEquals(bigInt, absNode.execute(bigIntNegative));
return null;
});
}

@Test
public void testAbsPanic() {
ContextUtils.executeInContext(
ctx,
() -> {
assertThrows(
"Decimals are not supported", PanicException.class, () -> absNode.execute(23.0));
assertThrows(
Expand All @@ -67,11 +88,57 @@ public void testAbs() {
}

@Test
public void testAdd() {
public void testAdd21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23L, addNode.execute(22L, 1L));
return null;
});
}

@Test
public void testAdd21And1Point0() {
ContextUtils.executeInContext(
ctx,
() -> {
assertEquals(23.1, ((Number) addNode.execute(22L, 1.1)).doubleValue(), 0.01);
return null;
});
}

@Test
public void testAddMulti21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
var nn = EnsoMultiValue.NewNode.getUncached();
var leak = ContextUtils.leakContext(ctx);
var intType = leak.getBuiltins().number().getInteger();
var textType = leak.getBuiltins().text();
var both = new Type[] {intType, textType};
var twentyTwoHello = nn.newValue(both, 2, 0, new Object[] {22L, "Hello"});
assertEquals(23L, addNode.execute(twentyTwoHello, 1L));
return null;
});
}

@Test
public void testAddInterop21And1() {
ContextUtils.executeInContext(
ctx,
() -> {
var twentyOne = new WrappedPrimitive(21L);
assertEquals(23L, addNode.execute(twentyOne, 2L));
return null;
});
}

@Test
public void testAddLongAndText() {
ContextUtils.executeInContext(
ctx,
() -> {
assertThrows(PanicException.class, () -> addNode.execute(23L, "Hello"));
return null;
});
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
package org.enso.interpreter.test;

import static org.junit.Assert.assertEquals;

import org.enso.interpreter.runtime.EnsoContext;
import org.enso.interpreter.runtime.data.EnsoMultiValue;
import org.enso.interpreter.runtime.data.Type;
import org.enso.test.utils.ContextUtils;
import org.graalvm.polyglot.Context;
import org.junit.AfterClass;
import org.junit.BeforeClass;
import org.junit.Test;

public class CaseOfTest {
private static Context ctx;
private static EnsoContext leak;

@BeforeClass
public static void initCtx() throws Exception {
ctx = ContextUtils.createDefaultContext();
leak = ContextUtils.leakContext(ctx);
}

@AfterClass
public static void closeCtx() {
ctx.close();
ctx = null;
leak = null;
}

@Test
public void caseOfBoolean() {
doCaseOfBoolean(true, false);
}

@Test
public void caseOfInteropBoolean() {
var t = new WrappedPrimitive(true);
var f = new WrappedPrimitive(false);
doCaseOfBoolean(t, f);
}

@Test
public void caseOfMultiValueBoolean() {
var n = EnsoMultiValue.NewNode.getUncached();

var bAndT =
new Type[] {leak.getBuiltins().bool().getType(), leak.getBuiltins().number().getInteger()};
var t = n.newValue(bAndT, 2, 0, new Object[] {true, 300});
var f = n.newValue(bAndT, 2, 0, new Object[] {false, 200});
doCaseOfBoolean(t, f);
}

private void doCaseOfBoolean(Object t, Object f) {
var code =
"""
from Standard.Base import True, False
choose v = case v of
True -> 1
False -> 2
_ -> 3
""";

var choose = ContextUtils.evalModule(ctx, code, "choose.enso", "choose");

var one = choose.execute(t);
assertEquals("With " + t + " we should get 1", 1, one.asInt());
var two = choose.execute(f);
assertEquals("With " + f + " we should get 2", 2, two.asInt());
}
}
Loading

0 comments on commit 595e0a8

Please sign in to comment.