This is an automated email from the ASF dual-hosted git repository.
jhyde pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/calcite.git
The following commit(s) were added to refs/heads/main by this push:
new cc73aba9b4 [CALCITE-6005] POLYGON string representation is different
on Apple silicon
cc73aba9b4 is described below
commit cc73aba9b4af0c3af5ac96422518a821e951cb9b
Author: Julian Hyde <[email protected]>
AuthorDate: Fri Sep 22 18:00:12 2023 -0700
[CALCITE-6005] POLYGON string representation is different on Apple silicon
Two tests in RelOptRulesTest produce different plans on Apple
Silicon (arm64) than on AMD/Intel (x86_64) because the double
values inside a POLYGON geospatial value differ in their
least significant digits. Perhaps arm64 implements floating
point differently.
In this change we solve the problem by changing replacing the
floating point values with their x86_64 values. After this
change the tests pass on both CPU architectures. If the
problem spreads beyond a couple of tests we can adopt a more
robust solution.
---
.../org/apache/calcite/test/RelOptRulesTest.xml | 4 ++--
.../java/org/apache/calcite/test/RelOptFixture.java | 20 +++++++++++++++++---
2 files changed, 19 insertions(+), 5 deletions(-)
diff --git
a/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
b/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
index c62309fbc3..86edca1ab2 100644
--- a/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
+++ b/core/src/test/resources/org/apache/calcite/test/RelOptRulesTest.xml
@@ -14087,7 +14087,7 @@ LogicalProject(NAME=[$0], LATITUDE=[$1],
LONGITUDE=[$2], CUISINE=[$3], HILBERT=[
<Resource name="planAfter">
<![CDATA[
LogicalProject(NAME=[$0], LATITUDE=[$1], LONGITUDE=[$2], CUISINE=[$3],
HILBERT=[$4])
- LogicalFilter(condition=[AND(SEARCH($4, Sarg[[33033..33035], [33050..33053],
[33055..33080], [33092..33100], [33112..33156], [33164..33176], [33236..33244],
[33252..33254], [36456..36464], [36496..36520]]), ST_CONTAINS(POLYGON ((16 20,
15.884711682419383 18.829458067903232, 15.54327719506772 17.703899405809462,
14.988817673815271 16.666578601882385, 14.242640687119286 15.757359312880716,
13.333421398117615 15.011182326184729, 12.29610059419054 14.45672280493228,
11.17054193209677 14.11 [...]
+ LogicalFilter(condition=[AND(SEARCH($4, Sarg[[33033..33035], [33050..33053],
[33055..33080], [33092..33100], [33112..33156], [33164..33176], [33236..33244],
[33252..33254], [36456..36464], [36496..36520]]), ST_CONTAINS(POLYGON ((16 20,
15.884711682419383 18.829458067903232, 15.54327719506772 17.703899405809462,
14.988817673815271 16.666578601882385, 14.242640687119286 15.757359312880716,
13.333421398117615 15.011182326184729, 12.29610059419054 14.45672280493228,
11.17054193209677 14.11 [...]
LogicalTableScan(table=[[CATALOG, GEO, RESTAURANTS]])
]]>
</Resource>
@@ -14216,7 +14216,7 @@ LogicalProject(B=[ST_BUFFER(ST_POINT(0.0:DECIMAL(2, 1),
0.0:DECIMAL(2, 1)), 1, 4
</Resource>
<Resource name="planAfter">
<![CDATA[
-LogicalProject(B=[CAST(POLYGON ((1 0, 0.9238795325112867 -0.3826834323650898,
0.7071067811865476 -0.7071067811865475, 0.3826834323650898 -0.9238795325112867,
0.0000000000000001 -1, -0.3826834323650897 -0.9238795325112867,
-0.7071067811865475 -0.7071067811865476, -0.9238795325112867
-0.3826834323650899, -1 -0.0000000000000001, -0.9238795325112868
0.3826834323650897, -0.7071067811865477 0.7071067811865475, -0.3826834323650903
0.9238795325112865, -0.0000000000000002 1, 0.38268343236509 0.92 [...]
+LogicalProject(B=[CAST(POLYGON ((1 0, 0.9238795325112867 -0.3826834323650898,
0.7071067811865476 -0.7071067811865475, 0.3826834323650898 -0.9238795325112867,
0.0000000000000001 -1, -0.3826834323650897 -0.9238795325112867,
-0.7071067811865475 -0.7071067811865476, -0.9238795325112867
-0.3826834323650899, -1 -0.0000000000000001, -0.9238795325112867
0.3826834323650897, -0.7071067811865477 0.7071067811865475, -0.3826834323650903
0.9238795325112865, -0.0000000000000002 1, 0.38268343236509 0.92 [...]
LogicalTableScan(table=[[CATALOG, GEO, RESTAURANTS]])
]]>
</Resource>
diff --git a/testkit/src/main/java/org/apache/calcite/test/RelOptFixture.java
b/testkit/src/main/java/org/apache/calcite/test/RelOptFixture.java
index e51bf159bf..fbeda9527d 100644
--- a/testkit/src/main/java/org/apache/calcite/test/RelOptFixture.java
+++ b/testkit/src/main/java/org/apache/calcite/test/RelOptFixture.java
@@ -362,7 +362,7 @@ public class RelOptFixture {
final RelNode relBefore = before.apply(this, r1);
assertThat(relBefore, notNullValue());
- final String planBefore = NL + RelOptUtil.toString(relBefore);
+ final String planBefore = NL + relToString(relBefore);
final DiffRepository diffRepos = diffRepos();
diffRepos.assertEquals("planBefore", "${planBefore}", planBefore);
assertThat(relBefore, relIsValid());
@@ -380,7 +380,7 @@ public class RelOptFixture {
final RelNode r4;
if (lateDecorrelate) {
- final String planMid = NL + RelOptUtil.toString(r3);
+ final String planMid = NL + relToString(r3);
diffRepos.assertEquals("planMid", "${planMid}", planMid);
assertThat(r3, relIsValid());
final RelBuilder relBuilder =
@@ -390,7 +390,7 @@ public class RelOptFixture {
r4 = r3;
}
final RelNode relAfter = after.apply(this, r4);
- final String planAfter = NL + RelOptUtil.toString(relAfter);
+ final String planAfter = NL + relToString(relAfter);
if (unchanged) {
final String expandedPlanAfter = diffRepos.expand("planAfter",
"${planAfter}");
if (!"${planAfter}".equals(expandedPlanAfter)) {
@@ -408,6 +408,20 @@ public class RelOptFixture {
assertThat(relAfter, relIsValid());
}
+ /** Converts a {@code RelNode} to a string, masking differences between
+ * floating point values on Apple Silicon (arm64) and AMD/Intel (x86_64).
+ *
+ * <p>The differences occur in the POLYGON values generated by
+ * {@code RelOptRulesTest#testSpatialReduce} and
+ * {@code testSpatialContainsPoint}, so perhaps there is a bug in the
+ * JTS {@code Geometry.buffer} method. */
+ private static String relToString(RelNode r) {
+ final String s = RelOptUtil.toString(r);
+ return s.replace("-0.9238795325112868", "-0.9238795325112867")
+ .replace("4.456722804932279", "4.45672280493228")
+ .replace("0.3826834323650896", "0.3826834323650897");
+ }
+
public RelOptFixture withVolcanoPlanner(boolean topDown) {
return withVolcanoPlanner(topDown, p ->
RelOptUtil.registerDefaultRules(p, false, false));