Hi Paul,

> I attempted to reproduce Tom Christensen's first problem listed here:
> 
> https://lists.gnu.org/r/bug-gnulib/2020-11/msg00062.html
> 
> on Solaris 10 sparc, by running this:
> 
> ./gnulib-tool --create-testdir --dir foo getumask
> 
> and then on Solaris:
> 
> ./configure
> make
> make check
> 
> This failed as follows:
> 
> depbase=`echo asyncsafe-spin.o | sed 's|[^/]*$|.deps/&|;s|\.o$||'`;\
> gcc -std=gnu99 -DHAVE_CONFIG_H -I. -I..  -DGNULIB_STRICT_CHECKING=1 
> -D_REENTRANT 
>   -g -O2 -MT asyncsafe-spin.o -MD -MP -MF $depbase.Tpo -c -o asyncsafe-spin.o 
> asyncsafe-spin.c &&\
> mv -f $depbase.Tpo $depbase.Po
> /usr/ccs/bin/as: "/tmp/ccK0uCIY.s", line 19: error: cannot use v8plus 
> instructions in a non-v8plus target binary
> /usr/ccs/bin/as: "/tmp/ccK0uCIY.s", line 39: error: cannot use v8plus 
> instructions in a non-v8plus target binary
> 
> These diagnostics come from these instructions:
> 
>           cas [%o0],%o1,%o2
>           ...
>           membar 2
> 
> which come from asm directives in lib/asyncsafe-spin.c. These instructions 
> are 
> not portable to SPARC v8 processors (32-bit only); they assume SPARC v8+ or 
> SPARC v9.
> 
> I worked around the problem by configuring this way:
> 
> ./configure CC='gcc -mcpu=v9 -m32'
> 
> to compile for SPARC v9, which is fine for my hardware (a production Sun Fire 
> 280R with an UltraSPARC III). I doubt whether anybody outside of computer 
> museums cares about SPARC v8 hardware any more, but it would be nice if 
> 'configure; make' just worked on Solaris 10 sparc so perhaps the 
> asyncsafe-spin 
> module should add the '-mcpu=v9 -m32' options on this platform, or maybe 
> asyncsafe-spin.c could simply omit the relevant instructions on 32-bit sparc 
> platforms.

While it can be worked around by the person who builds the GNU package, I agree
with you that it should better work out-of-the-box.

> I doubt whether anybody outside of computer 
> museums cares about SPARC v8 hardware any more

Yes. SPARC v9 was released in 1993, that is, 27 years ago.

> maybe asyncsafe-spin.c could simply omit the relevant instructions on 32-bit
> sparc platforms.

Better not, since often binaries built for older platforms are run on newer
platforms. I surely still have binaries from 2000 that I run on hardware from
2017.

On my way to reproduce the issue, I picked the 'unstable9s' machine on
opencsw.org, with CC="gcc -mno-v8plus -O2", and encountered this error:

gcc -O2 -std=gnu99  -g -O2  -L/home/haible/prefix-sparc32/lib -o 
test-asyncsafe-spin1 test-asyncsafe-spin1.o libtests.a ../gllib/libgnu.a 
libtests.a ../gllib/libgnu.a libtests.a  
Undefined                       first referenced
 symbol                             in file
__sync_val_compare_and_swap_4       ../gllib/libgnu.a(asyncsafe-spin.o)
ld: fatal: Symbol referencing errors. No output written to test-asyncsafe-spin1
collect2: ld returned 1 exit status

This is a GCC 4.6.4, and it apparently does not implement the library
functions for GCC built-ins that are supposedly implemented since GCC 4.1.

The first patch deals with that.

Then, I do reproduce your error, with a slightly different assembler message:

/var/tmp//ccUF6VQS.s: Assembler messages:
/var/tmp//ccUF6VQS.s:19: Error: Architecture mismatch on "membar".
/var/tmp//ccUF6VQS.s:19:  (Requires v9|v9a|v9b; requested architecture is v8.)
/var/tmp//ccUF6VQS.s:67: Error: Architecture mismatch on "cas".
/var/tmp//ccUF6VQS.s:67:  (Requires leon|v9|v9a|v9b; requested architecture is 
v8.)
/var/tmp//ccUF6VQS.s:103: Error: Architecture mismatch on "cas".
/var/tmp//ccUF6VQS.s:103:  (Requires leon|v9|v9a|v9b; requested architecture is 
v8.)
*** Error code 1

So, with this assembler, we need to turn on v9 support; v8+ support is not
sufficient. The second patch does this.


2020-11-28  Bruno Haible  <br...@clisp.org>

        asyncsafe-spin: Fix compilation error with GCC on 32-bit SPARC.
        Reported by Paul Eggert in
        <https://lists.gnu.org/archive/html/bug-gnulib/2020-11/msg00066.html>.
        * m4/sparcv8+.m4: New file.
        * modules/sparcv8+: New file.
        * modules/asyncsafe-spin (Depends-on): Add sparcv8+.

2020-11-28  Bruno Haible  <br...@clisp.org>

        asyncsafe-spin: Fix build error with GCC on 32-bit SPARC.
        * lib/asyncsafe-spin.c: Don't use GCC >= 4.1 primitives on SPARC.

>From 406ab5ee052addba6b801b7e1357e90fbcd546d1 Mon Sep 17 00:00:00 2001
From: Bruno Haible <br...@clisp.org>
Date: Sat, 28 Nov 2020 12:03:36 +0100
Subject: [PATCH 1/2] asyncsafe-spin: Fix build error with GCC on 32-bit SPARC.

* lib/asyncsafe-spin.c: Don't use GCC >= 4.1 primitives on SPARC.
---
 ChangeLog            | 5 +++++
 lib/asyncsafe-spin.c | 6 ++++--
 2 files changed, 9 insertions(+), 2 deletions(-)

diff --git a/ChangeLog b/ChangeLog
index 22a26e7..5505379 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,10 @@
 2020-11-28  Bruno Haible  <br...@clisp.org>
 
+	asyncsafe-spin: Fix build error with GCC on 32-bit SPARC.
+	* lib/asyncsafe-spin.c: Don't use GCC >= 4.1 primitives on SPARC.
+
+2020-11-28  Bruno Haible  <br...@clisp.org>
+
 	windows-spawn: New module.
 	* lib/windows-spawn.h: Renamed from lib/w32spawn.h. Remove
 	implementations.
diff --git a/lib/asyncsafe-spin.c b/lib/asyncsafe-spin.c
index 98d4fad..db70e50 100644
--- a/lib/asyncsafe-spin.c
+++ b/lib/asyncsafe-spin.c
@@ -131,10 +131,12 @@ do_unlock (asyncsafe_spinlock_t *lock)
 
 #   endif
 
-#  elif (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 1) \
+#  elif (((__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ >= 1)) \
+          && !defined __sparc__) \
          || __clang_major__ >= 3) \
         && !defined __ibmxl__
-/* Use GCC built-ins (available in GCC >= 4.1 and clang >= 3.0).
+/* Use GCC built-ins (available in GCC >= 4.1, except on SPARC, and
+   clang >= 3.0).
    Documentation:
    <https://gcc.gnu.org/onlinedocs/gcc-4.1.2/gcc/Atomic-Builtins.html>  */
 
-- 
2.7.4

>From 25a731a154380065d9fe92683c64d30f44bd3d6c Mon Sep 17 00:00:00 2001
From: Bruno Haible <br...@clisp.org>
Date: Sat, 28 Nov 2020 12:04:47 +0100
Subject: [PATCH 2/2] asyncsafe-spin: Fix compilation error with GCC on 32-bit
 SPARC.

Reported by Paul Eggert in
<https://lists.gnu.org/archive/html/bug-gnulib/2020-11/msg00066.html>.

* m4/sparcv8+.m4: New file.
* modules/sparcv8+: New file.
* modules/asyncsafe-spin (Depends-on): Add sparcv8+.
---
 ChangeLog              |  9 +++++++++
 m4/sparcv8+.m4         | 42 ++++++++++++++++++++++++++++++++++++++++++
 modules/asyncsafe-spin |  1 +
 modules/sparcv8+       | 22 ++++++++++++++++++++++
 4 files changed, 74 insertions(+)
 create mode 100644 m4/sparcv8+.m4
 create mode 100644 modules/sparcv8+

diff --git a/ChangeLog b/ChangeLog
index 5505379..fa21e9c 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,5 +1,14 @@
 2020-11-28  Bruno Haible  <br...@clisp.org>
 
+	asyncsafe-spin: Fix compilation error with GCC on 32-bit SPARC.
+	Reported by Paul Eggert in
+	<https://lists.gnu.org/archive/html/bug-gnulib/2020-11/msg00066.html>.
+	* m4/sparcv8+.m4: New file.
+	* modules/sparcv8+: New file.
+	* modules/asyncsafe-spin (Depends-on): Add sparcv8+.
+
+2020-11-28  Bruno Haible  <br...@clisp.org>
+
 	asyncsafe-spin: Fix build error with GCC on 32-bit SPARC.
 	* lib/asyncsafe-spin.c: Don't use GCC >= 4.1 primitives on SPARC.
 
diff --git a/m4/sparcv8+.m4 b/m4/sparcv8+.m4
new file mode 100644
index 0000000..2dbb8a9
--- /dev/null
+++ b/m4/sparcv8+.m4
@@ -0,0 +1,42 @@
+# sparcv8+.m4 serial 1
+dnl Copyright (C) 2020 Free Software Foundation, Inc.
+dnl This file is free software; the Free Software Foundation
+dnl gives unlimited permission to copy and/or distribute it,
+dnl with or without modifications, as long as this notice is preserved.
+
+dnl When compiling for SPARC in 32-bit mode, make sure that instructions for
+dnl SPARC v8+ are accepted.  This is necessary for multiprocessing (for
+dnl instructions like 'membar' or 'cas').  All SPARC CPUs made since 1993
+dnl support this instruction set.  But GCC in its default configuration, in
+dnl 32-bit mode (64-bit mode assumes SPARC v9 or newer), still defaults to
+dnl SPARC v7 instruction set: "By default (unless configured otherwise), GCC
+dnl generates code for the V7 variant of the SPARC architecture."  See
+dnl <https://gcc.gnu.org/onlinedocs/gcc-4.6.4/gcc/SPARC-Options.html>
+dnl <https://gcc.gnu.org/onlinedocs/gcc-10.2.0/gcc/SPARC-Options.html>
+
+AC_DEFUN([gl_SPARC_V8PLUS],
+[
+  AC_REQUIRE([AC_CANONICAL_HOST])
+
+  case "$host_cpu" in
+    sparc*)
+      if test -n "$GCC"; then
+        AC_CACHE_CHECK([whether SPARC v8+ instructions are supported],
+          [gl_cv_sparc_v8plus],
+          [AC_COMPILE_IFELSE(
+             [AC_LANG_PROGRAM(
+                [[]],
+                [[asm volatile ("membar 2");]])],
+             [gl_cv_sparc_v8plus=yes],
+             [gl_cv_sparc_v8plus=no])
+          ])
+        if test $gl_cv_sparc_v8plus = no; then
+          dnl Strangely enough, '-mv8plus' does not have the desired effect.
+          dnl But '-mcpu=v9' does.
+          CC="$CC -mcpu=v9"
+          CXX="$CXX -mcpu=v9"
+        fi
+      fi
+      ;;
+  esac
+])
diff --git a/modules/asyncsafe-spin b/modules/asyncsafe-spin
index fa27b08..fc73492 100644
--- a/modules/asyncsafe-spin
+++ b/modules/asyncsafe-spin
@@ -10,6 +10,7 @@ signal-h
 stdbool
 sigprocmask
 windows-spin
+sparcv8+
 
 configure.ac:
 AC_REQUIRE([AC_C_INLINE])
diff --git a/modules/sparcv8+ b/modules/sparcv8+
new file mode 100644
index 0000000..a4e38a8
--- /dev/null
+++ b/modules/sparcv8+
@@ -0,0 +1,22 @@
+Description:
+When compiling for SPARC, assume SPARC v8+ or newer.
+
+Files:
+m4/sparcv8+.m4
+
+Depends-on:
+
+configure.ac-early:
+gl_SPARC_V8PLUS
+
+configure.ac:
+
+Makefile.am:
+
+Include:
+
+License:
+LGPLv2+
+
+Maintainer:
+all
-- 
2.7.4

Reply via email to