From tc@||@w@ @end|ng |rom redh@t@com  Thu Dec 12 20:21:10 2019
From: tc@||@w@ @end|ng |rom redh@t@com (Tom Callaway)
Date: Thu, 12 Dec 2019 14:21:10 -0500
Subject: [Rd] Build failure on powerpc64
Message-ID: <CANA0HMYoYiHApzRfswTioi352ELYS4bJwvrW+=su6Mtanq84RQ@mail.gmail.com>

Hi R folks,

Went to build R 3.6.2 for Fedora/EPEL and got failures across the board.

Disabling the test suite for all non-intel architectures resolves most of
the failures, but powerpc64 dies in the compiler, specifically here:

gcc -m64  -I../../src/extra/xdr -I. -I../../src/include -I../../src/include
 -I/usr/local/include -I../../src/nmath -DHAVE_CONFIG_H   -fopenmp -fPIC
 -O2 -g -pipe -Wall -Werror=format-security -Wp,-D_FORTIFY_SOURCE=2
-Wp,-D_GLIBCXX_ASSERTIONS -fexceptions -fstack-protector-strong
-grecord-gcc-switches -specs=/usr/lib/rpm/redhat/redhat-hardened-cc1
-specs=/usr/lib/rpm/redhat/redhat-annobin-cc1 -m64 -mcpu=power8
-mtune=power8 -fasynchronous-unwind-tables -fstack-clash-protection  -c
arithmetic.c -o arithmetic.o
arithmetic.c:180:26: error: initializer element is not constant
  180 | static LDOUBLE q_1_eps = (1 / LDBL_EPSILON);
      |                          ^
make[3]: *** [../../Makeconf:124: arithmetic.o] Error 1

Took me a bit to figure out why, but this is happening because on
powerpc64, gcc is compiled with -mlong-double-128, and the long double
format used on PPC is IBM's 128bit long double which is two doubles added
together. As a result, gcc can't safely do const assignments to long
doubles on ppc64, so it dies there.

The fix is easy enough, do not try to assign a value to a static long
double on ppc64.
--- ./src/main/arithmetic.c.orig        2019-12-12 18:30:12.416334062 +0000
+++ ./src/main/arithmetic.c     2019-12-12 18:30:44.966334062 +0000
@@ -179,7 +179,10 @@ void attribute_hidden InitArithmetic()
 #endif
 }

-#if HAVE_LONG_DOUBLE && (SIZEOF_LONG_DOUBLE > SIZEOF_DOUBLE)
+/* PowerPC 64 (when gcc has -mlong-double-128) breaks here because
+ * of issues constant folding 128bit IBM long doubles.
+ */
+#if HAVE_LONG_DOUBLE && (SIZEOF_LONG_DOUBLE > SIZEOF_DOUBLE) && !__PPC64__
 static LDOUBLE q_1_eps = 1 / LDBL_EPSILON;
 #else
 static double  q_1_eps = 1 / DBL_EPSILON;

Hope that helps someone else.

Tom

	[[alternative HTML version deleted]]



[Rd] Build failure on powerpc64
Tom Callaway