Hi all, hi Joseph & Jakub,

BACKGROUND:

The main reason I am interested in this is offloading where
OpenACC/OpenMP code might run into:
    unresolved symbol __atomic_compare_exchange_16
and it is nontrivial to find out that the solution is:
    -foffload=nvptx-none=-latomic
And the atomic use can appear for innocent looking code.
(The dependency comes via libgomp/config/nvptx/atomic.c
for __sync_val_compare_and_swap_16.)

However, as PR81358 shows, also for normal C (and C++) code
it would be nice as atomics are part of the language.

Target specific: for RISC-V (with -as-needed support only
with pthread, otherwise unconditionally) – and seemingly for RTEMS –
-latomic is already linked via LIB_SPEC.


My initial plan was to add -latomic to libgomp.spec - if built
for that target and using -as-needed if available, cf. last but one
email in the thread
https://gcc.gnu.org/pipermail/gcc-patches/2020-October/thread.html#555298
(my initial RFC question, quoted in the first email, was in September)

However, adding it there was opposed by Jakub as:
"I think for libgomp.spec we should add it solely for the offloading targets,
neither GCC generated code for OpenMP construct nor libgomp itself needs
-latomic on the hosts."
(Albeit for nvptx, see above.)


SOLUTION PART 1: Add configure option --enable-autolink-libatomic

[See attached patch (only configure check)]

Example for an explicit use: enable it for offloading targets
(which enables it for nvptx but not for amdgcn which does not
build libatomic). — And for the host, you may want to enable if
you always install libatomic and -as-needed is supported and
otherwise, you might want to disable it.

QUESTION:
* Should the default of --enable-autolink-libatomic default
  to 'yes' or 'no'?
* Should the default additionally depend on having -as-needed support?
  (Which would exclude nvptx with default settings.)


SOLUTION PART 2: Actually linking libatomic

?

QUESTION: I have no idea where to add the -latomic.

(a) Still do it in libgomp.spec but now with that configure
flag to be able to disable it?

Pro:
+ Solves problem for nvptx, which adds atomic code to
  libgomp/config/nvptx/atomic.c
+ rather minimal invasive and by tuning the config option
  it could be used when needed
Con:
- While OpenMP has atomics, libgomp by itself in general
  does not depend on libatomic for most targets
  - this can be mitigated by using the configure flag
  but it is not ideal, either.
- C code can use atomic directly and thus it would be nice
  if it could be automatically linked. (Especially if the
  target supports the -as-needed linker flag.)


(b) Do it in the driver

Pro:
+ will automatically work for C/C++ atomic code
+ with -as-needed it will only be linked if really needed
  (caveat: lib file has to be present at link time.)
Con:
- If -as-needed is not supported and it is always linked, this
  adds unneccessary dependencies (shared lib) or file size (static lib)
- Adding files for the linker to analyze does not help with
  the compile size
- The file has to be present, even if -as-needed is supported,
  adding a hard dependency on the libatomic library for Linux
  distros

For doing it in the driver, I am not sure when to add it.
Used:
- Direct consumer is C/C++ using atomics.
- For Fortran, it (currently) is only used for with
  nvptx offloading as described above.
- For offloading, the compilation/linking handling is
  slightly different and it needs to work there as well.
- No idea about Ada, D, or other direct or indirect dependencies


RISC-V + RTEMS use LIB_SPEC to add it.

One possibility would be to add it to the init_gcc_specs call,
but that feels like a sledge hammer solution.

Question: Where do you think should it be in the driver?

Other thoughts?

Or is solution (a) better? (That is: previous patch +
new --enable-autolink-libatomic for libgomp, only.)
Which is kind of a complicated nvptx-offloading-only solution?

Tobias

PS: I assume -static-libatomic then has to be added as well when we
add -latomic in the driver.

-----------------
Mentor Graphics (Deutschland) GmbH, Arnulfstraße 201, 80634 München / Germany
Registergericht München HRB 106955, Geschäftsführer: Thomas Heurung, Alexander 
Walter
 gcc/config.in    |  6 ++++++
 gcc/configure    | 38 +++++++++++++++++++++++++++++++++++---
 gcc/configure.ac | 26 +++++++++++++++++++++++++-
 3 files changed, 66 insertions(+), 4 deletions(-)
diff --git a/gcc/configure.ac b/gcc/configure.ac
index 26a5d8e3619..55e29773f98 100644
--- a/gcc/configure.ac
+++ b/gcc/configure.ac
@@ -1102,6 +1102,31 @@ AC_ARG_WITH(multilib-list,
 :,
 with_multilib_list=default)
 
+# If libatomic is available, whether it should be linked automatically
+AC_ARG_ENABLE(autolink-libatomic,
+[AS_HELP_STRING([--enable-autolink-libatomic],
+		[enable or disable the automatic linking of libatomic
+                 if it is available (enabled by default)])],
+[
+  case $enable_autolink_libatomic in
+    yes | no) ;;
+    *) AC_MSG_ERROR(['$enable_autolink_libatomic' is an invalid value for
+--enable-autolink-libatomic.  Valid choices are 'yes' and 'no'.]) ;;
+  esac
+], [enable_autolink_libatomic=''])
+
+if test x$enable_autolink_libatomic != xno; then
+  if echo " ${TARGET_CONFIGDIRS} " | grep " libatomic " > /dev/null 2>&1 ; then
+    AC_DEFINE(ENABLE_AUTOLINK_LIBATOMIC, 1,
+	[Define if libatomic should always be linked.])
+  else
+    if test x$enable_autolink_libatomic = xyes; then
+      AC_MSG_WARN([libatomic is not build for this target, --enable-autolink-libatomic ignored])
+    fi
+  fi
+fi
+
+
 # -------------------------
 # Checks for other programs
 # -------------------------
@@ -7106,4 +7131,3 @@ done
 ], 
 [subdirs='$subdirs'])
 AC_OUTPUT
-
diff --git a/gcc/config.in b/gcc/config.in
index 3657c46f349..ed4fefe35cd 100644
--- a/gcc/config.in
+++ b/gcc/config.in
@@ -106,6 +106,12 @@
 #endif
 
 
+/* Define if libatomic should always be linked. */
+#ifndef USED_FOR_TARGET
+#undef ENABLE_AUTOLINK_LIBATOMIC
+#endif
+
+
 /* Define to 1 to specify that we are using the BID decimal floating point
    format instead of DPD */
 #ifndef USED_FOR_TARGET
diff --git a/gcc/configure b/gcc/configure
index abff47d30eb..4f0b5984544 100755
--- a/gcc/configure
+++ b/gcc/configure
@@ -972,6 +972,7 @@ with_documentation_root_url
 with_changes_root_url
 enable_languages
 with_multilib_list
+enable_autolink_libatomic
 with_zstd
 with_zstd_include
 with_zstd_lib
@@ -1698,6 +1699,9 @@ Optional Features:
   --disable-shared        don't provide a shared libgcc
   --disable-gcov          don't provide libgcov and related host tools
   --enable-languages=LIST specify which front-ends to build
+  --enable-autolink-libatomic
+                          enable or disable the automatic linking of libatomic
+                          if it is available (enabled by default)
   --disable-rpath         do not hardcode runtime library paths
   --enable-sjlj-exceptions
                           arrange to use setjmp/longjmp exception handling
@@ -8002,6 +8006,35 @@ else
 fi
 
 
+# If libatomic is available, whether it should be linked automatically
+# Check whether --enable-autolink-libatomic was given.
+if test "${enable_autolink_libatomic+set}" = set; then :
+  enableval=$enable_autolink_libatomic;
+  case $enable_autolink_libatomic in
+    yes | no) ;;
+    *) as_fn_error $? "'$enable_autolink_libatomic' is an invalid value for
+--enable-autolink-libatomic.  Valid choices are 'yes' and 'no'." "$LINENO" 5 ;;
+  esac
+
+else
+  enable_autolink_libatomic=''
+fi
+
+
+if test x$enable_autolink_libatomic != xno; then
+  if echo " ${TARGET_CONFIGDIRS} " | grep " libatomic " > /dev/null 2>&1 ; then
+
+$as_echo "#define ENABLE_AUTOLINK_LIBATOMIC 1" >>confdefs.h
+
+  else
+    if test x$enable_autolink_libatomic = xyes; then
+      { $as_echo "$as_me:${as_lineno-$LINENO}: WARNING: libatomic is not build for this target, --enable-autolink-libatomic ignored" >&5
+$as_echo "$as_me: WARNING: libatomic is not build for this target, --enable-autolink-libatomic ignored" >&2;}
+    fi
+  fi
+fi
+
+
 # -------------------------
 # Checks for other programs
 # -------------------------
@@ -19018,7 +19051,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 19021 "configure"
+#line 19054 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -19124,7 +19157,7 @@ else
   lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2
   lt_status=$lt_dlunknown
   cat > conftest.$ac_ext <<_LT_EOF
-#line 19127 "configure"
+#line 19160 "configure"
 #include "confdefs.h"
 
 #if HAVE_DLFCN_H
@@ -32715,4 +32748,3 @@ if test -n "$ac_unrecognized_opts" && test "$enable_option_checking" != no; then
 $as_echo "$as_me: WARNING: unrecognized options: $ac_unrecognized_opts" >&2;}
 fi
 
-

Reply via email to