Repository: yt-project/yt

Issue:
Compiling yt with old gcc versions
### Bug report

**Bug summary**

The code base passes `-std=c++14` to gcc when compiling C++ files. This flag is however only supported on GCC 5 and later. For earlier version, it seems we could escape by passing `-std=c++1y` instead, but I don't know what implication that would have (if any).



Discussion:

Resolving patch:
diff --git a/setup.py b/setup.py
--- a/setup.py
+++ b/setup.py
@@ -9,6 +9,7 @@
 from setuptools import Distribution, find_packages, setup
 
 from setupext import (
+    check_CPP14_flags,
     check_for_openmp,
     check_for_pyembree,
     create_build_ext,
@@ -38,11 +39,10 @@
     long_description = file.read()
 
 CPP14_CONFIG = defaultdict(
-    lambda: ["-std=c++14"], {"unix": ["-std=c++14"], "msvc": ["/std:c++14"]}
-)
-CPP03_CONFIG = defaultdict(
-    lambda: ["-std=c++03"], {"unix": ["-std=c++03"], "msvc": ["/std:c++03"]}
+    lambda: check_CPP14_flags(["-std=c++14", "-std=c++1y", "-std=gnu++0x"]),
+    {"msvc": ["/std:c++14"]},
 )
+CPP03_CONFIG = defaultdict(lambda: ["-std=c++03"], {"msvc": ["/std:c++03"]})
 
 _COMPILER = get_default_compiler()
 
diff --git a/setupext.py b/setupext.py
--- a/setupext.py
+++ b/setupext.py
@@ -19,17 +19,6 @@
 from setuptools.command.build_ext import build_ext as _build_ext
 from setuptools.command.sdist import sdist as _sdist
 
-CCODE = """
-#include <omp.h>
-#include <stdio.h>
-int main() {
-  omp_set_num_threads(2);
-  #pragma omp parallel
-  printf("nthreads=%d\\n", omp_get_num_threads());
-  return 0;
-}
-"""
-
 
 @contextlib.contextmanager
 def stdchannel_redirected(stdchannel, dest_filename):
@@ -73,6 +62,17 @@ def check_for_openmp():
     tmp_dir = tempfile.mkdtemp()
     start_dir = os.path.abspath(".")
 
+    CCODE = """
+    #include <omp.h>
+    #include <stdio.h>
+    int main() {
+        omp_set_num_threads(2);
+        #pragma omp parallel
+        printf("nthreads=%d\\n", omp_get_num_threads());
+        return 0;
+    }
+    """
+
     # TODO: test more known compilers:
     # MinGW, AppleClang with libomp, MSVC, ICC, XL, PGI, ...
     if os.name == "nt":
@@ -145,6 +145,61 @@ def check_for_openmp():
         return [], []
 
 
+def check_CPP14_flag(compile_flags):
+    # Create a temporary directory
+    ccompiler = new_compiler()
+    customize_compiler(ccompiler)
+
+    tmp_dir = tempfile.mkdtemp()
+    start_dir = os.path.abspath(".")
+
+    # Note: This code requires C++14 functionalities (also required to compile yt)
+    # It compiles on gcc 4.7.4 (together with the entirety of yt) with the flag "-std=gnu++0x".
+    # It does not compile on gcc 4.6.4 (neither does yt).
+    CPPCODE = """
+    #include <vector>
+
+    struct node {
+        std::vector<int> vic;
+        bool visited = false;
+    };
+
+    int main() {
+        return 0;
+    }
+    """
+
+    os.chdir(tmp_dir)
+    try:
+        with open("test_cpp14.cpp", "w") as f:
+            f.write(CPPCODE)
+
+        os.mkdir("objects")
+
+        # Compile, link, and run test program
+        with stdchannel_redirected(sys.stderr, os.devnull):
+            ccompiler.compile(
+                ["test_cpp14.cpp"], output_dir="objects", extra_postargs=compile_flags
+            )
+        return True
+    except CompileError:
+        return False
+    finally:
+        os.chdir(start_dir)
+
+
+def check_CPP14_flags(possible_compile_flags):
+    for flags in possible_compile_flags:
+        if check_CPP14_flag([flags]):
+            return flags
+
+    log.warn(
+        "Your compiler seems to be too old to support C++14. "
+        "yt may not be able to compile. Please use a newer version."
+    )
+    return []
+
+
 def check_for_pyembree(std_libs):
     embree_libs = []
     embree_aliases = {}


Test patch: