diff --git a/cmake/CMakeLists.txt b/cmake/CMakeLists.txt index 4dd079eaae..3dea0db8b0 100644 --- a/cmake/CMakeLists.txt +++ b/cmake/CMakeLists.txt @@ -229,16 +229,7 @@ pkg_depends(USER-SCAFACOS MPI) find_package(OpenMP QUIET) -# TODO: this is a temporary workaround until a better solution is found. AK 2019-05-30 -# GNU GCC 9.x uses settings incompatible with our use of 'default(none)' in OpenMP pragmas -# where we assume older GCC semantics. For the time being, we disable OpenMP by default -# for GCC 9.x and beyond. People may manually turn it on, but need to run the script -# src/USER-OMP/hack_openmp_for_pgi_gcc9.sh on all sources to make it compatible with gcc 9. -if ((CMAKE_CXX_COMPILER_ID STREQUAL "GNU") AND (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 8.99.9)) - option(BUILD_OMP "Build with OpenMP support" OFF) -else() - option(BUILD_OMP "Build with OpenMP support" ${OpenMP_FOUND}) -endif() +option(BUILD_OMP "Build with OpenMP support" ${OpenMP_FOUND}) if(BUILD_OMP) find_package(OpenMP REQUIRED) @@ -248,6 +239,13 @@ if(BUILD_OMP) endif() set (CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${OpenMP_C_FLAGS}") set (CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${OpenMP_CXX_FLAGS}") + + if ((CMAKE_CXX_COMPILER_ID STREQUAL "GNU") AND (CMAKE_CXX_COMPILER_VERSION VERSION_GREATER 8.99.9)) + # GCC 9.x strictly implements OpenMP 4.0 semantics for consts. + add_definitions(-DLMP_OMP_COMPAT=4) + else() + add_definitions(-DLMP_OMP_COMPAT=3) + endif() endif() if(PKG_MSCG OR PKG_USER-ATC OR PKG_USER-AWPMD OR PKG_USER-QUIP OR PKG_LATTE) diff --git a/doc/src/Build_basics.rst b/doc/src/Build_basics.rst index 8ad48b0810..96bc0f5bd1 100644 --- a/doc/src/Build_basics.rst +++ b/doc/src/Build_basics.rst @@ -145,11 +145,9 @@ Some compilers do not fully support the ``default(none)`` directive and others (e.g. GCC version 9 and beyond) may implement OpenMP 4.0 semantics, which are incompatible with the OpenMP 3.1 semantics used in LAMMPS (for maximal compatibility with compiler versions in use). -In those case, all ``default(none)`` directives (which aid in detecting -incorrect and unwanted sharing) can be replaced with ``default(shared)`` -while dropping all ``shared()`` directives. The script -'src/USER-OMP/hack_openmp_for_pgi_gcc9.sh' can be used to automate -this conversion. +LAMMPS will try to detect compilers that use OpenMP 4.0 semantics and +change the directives accordingly, but if your compiler is not +detected, you may set the CMake variable ``-D LMP_OMP_COMPAT=4``. ---------- diff --git a/src/USER-OMP/README b/src/USER-OMP/README index 46f63f646b..0aef853bca 100644 --- a/src/USER-OMP/README +++ b/src/USER-OMP/README @@ -9,11 +9,3 @@ doc/Section_accelerate.html, sub-section 5.2 The person who created this package is Axel Kohlmeyer at Temple U (akohlmey at gmail.com). Contact him directly if you have questions. --------------------------- - -This directory also contains a shell script: - -hack_openmp_for_pgi.sh - -which will convert OpenMP directives in src files -into a form compatible with the PGI compiler. diff --git a/src/USER-OMP/hack_openmp_for_pgi_gcc9.sh b/src/USER-OMP/hack_openmp_for_pgi_gcc9.sh deleted file mode 100755 index 6f9f30cedd..0000000000 --- a/src/USER-OMP/hack_openmp_for_pgi_gcc9.sh +++ /dev/null @@ -1,12 +0,0 @@ -#!/bin/sh - -# convert default(none) directives for OpenMP pragmas to default(shared) and remove shared() directive -# this allows compiling OpenMP pragmas in LAMMPS with compilers that don't support default(none) properly -# or require backward incompatible OpenMP 4 and OpenMP 5 semantics - -for f in *.h *.cpp -do \ - sed -e '/#pragma omp/s/^\(.*default\)(none)\(.*\)$/\1(shared)\2/' \ - -e '/#pragma omp/s/shared([a-z0-9,_]\+)//' \ - -i.bak $f -done diff --git a/src/omp_compat.h b/src/omp_compat.h new file mode 100644 index 0000000000..8abf1c54bc --- /dev/null +++ b/src/omp_compat.h @@ -0,0 +1,35 @@ +/* -*- c++ -*- ---------------------------------------------------------- + LAMMPS - Large-scale Atomic/Molecular Massively Parallel Simulator + http://lammps.sandia.gov, Sandia National Laboratories + Steve Plimpton, sjplimp@sandia.gov + + Copyright (2020) Sandia Corporation. Under the terms of Contract + DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government retains + certain rights in this software. This software is distributed under + the GNU General Public License. + + See the README file in the top-level LAMMPS directory. +------------------------------------------------------------------------- */ + +// There is no way to annotate an OpenMP construct that +// (a) accesses const variables, (b) has default(none), +// and (c) is valid in both OpenMP 3.0 and 4.0. +// +// (in OpenMP 3.0, the const variables have a predetermined +// sharing attribute and are *forbidden* from being declared +// in the omp construct. In OpenMP 4.0, this predetermined +// sharing attribute is removed, and thus they are *required* +// to be declared in the omp construct) +// +// To date, most compilers still accept the OpenMP 3.0 form, +// so this is what LAMMPS primarily uses. For those compilers +// that strictly implement OpenMP 4.0 (such as GCC 9.0), we +// give up default(none). +#if LMP_OMP_COMPAT == 4 +# define LMP_SHARED(...) +# define LMP_DEFAULT_NONE default(shared) +#else +# define LMP_SHARED(...) shared(__VA_ARGS__) +# define LMP_DEFAULT_NONE default(none) +#endif +