aboutsummaryrefslogtreecommitdiff
path: root/build2/b.cxx
diff options
context:
space:
mode:
authorKaren Arutyunov <karen@codesynthesis.com>2018-01-17 09:40:27 +0300
committerKaren Arutyunov <karen@codesynthesis.com>2018-01-17 09:40:27 +0300
commit14b295bdb00305370ec0aaad7f4319bad55ad6e9 (patch)
tree5c27b654f29856f322ed86551ae605de63dccde9 /build2/b.cxx
parenta5a12af675e5db81d2b36b7d879949e896ae4746 (diff)
Add workaround for data race in libstdc++'s ctype<char>::narrow()
Diffstat (limited to 'build2/b.cxx')
-rw-r--r--build2/b.cxx20
1 files changed, 20 insertions, 0 deletions
diff --git a/build2/b.cxx b/build2/b.cxx
index c7219f0..1106031 100644
--- a/build2/b.cxx
+++ b/build2/b.cxx
@@ -10,6 +10,10 @@
#include <stdlib.h> // getenv() _putenv()(_WIN32)
+#ifdef __GLIBCXX__
+# include <locale>
+#endif
+
#include <sstream>
#include <cstring> // strcmp(), strchr()
#include <typeinfo>
@@ -152,6 +156,22 @@ main (int argc, char* argv[])
}
#endif
+// A data race happens in the libstdc++ (as of GCC 7.2) implementation of the
+// ctype<char>::narrow() function (bug #77704). The issue is easily triggered
+// by the testscript runner that indirectly (via regex) uses ctype<char> facet
+// of the global locale (and can potentially be triggered by other locale-
+// aware code). We work around this by pre-initializing the global locale
+// facet internal cache.
+//
+#ifdef __GLIBCXX__
+ {
+ const ctype<char>& ct (use_facet<ctype<char>> (locale ()));
+
+ for (size_t i (0); i != 256; ++i)
+ ct.narrow (static_cast<char> (i), '\0');
+ }
+#endif
+
try
{
// On POSIX ignore SIGPIPE which is signaled to a pipe-writing process if