Локальное хранилище потоков C++ clang-503.0.40 (Mac OSX)
После того как я объявил переменную таким образом:
#include <thread>
namespace thread_space
{
thread_local int s;
} //etc.
я попытался скомпилировать мой код, используя 'g++ -std= C++0x -pthread [sourcefile]'. Я получаю следующую ошибку:
example.C:6:8: error: thread-local storage is unsupported for the current target
static thread_local int s;
^
1 error generated.
Если я пытаюсь скомпилировать тот же код в Linux с GCC 4.8.1 с теми же флагами, я получаю работающий исполняемый файл. Я использую clang-503.0.40 (тот, который поставляется с Xcode 5.1.1) на MacBook Pro под управлением OSX 10.9.3. Кто-нибудь может объяснить мне, что я делаю не так? Спасибо!!
4 ответа
Пытаться clang++ -stdlib=libc++ -std=c++11
, Устаревшая версия OS X libstdC++ не поддерживает TLS.
редактировать
Хорошо, это работает для нормальной версии clang, но не для версии Xcode.
Я сделал различие против лягушки Apple (503.0.38) и нормального выпущенного и обнаружил следующую разницу:
.Case("cxx_thread_local",
- LangOpts.CPlusPlus11 && PP.getTargetInfo().isTLSSupported() &&
- !PP.getTargetInfo().getTriple().isOSDarwin())
+ LangOpts.CPlusPlus11 && PP.getTargetInfo().isTLSSupported())
Так что я думаю, что это ошибка в версии clang от Apple (или они держали ее там специально - но все же странно, потому что -v
говорит на основе 3.4).
Кроме того, вы можете использовать расширения компилятора, такие как __thread
(GCC/Clang) или __declspec(thread)
(Visual Studio).
Оберните его в макрос, и вы сможете легко перенести код на разные компиляторы и языковые версии:
#if HAS_CXX11_THREAD_LOCAL
#define ATTRIBUTE_TLS thread_local
#elif defined (__GNUC__)
#define ATTRIBUTE_TLS __thread
#elif defined (_MSC_VER)
#define ATTRIBUTE_TLS __declspec(thread)
#else // !C++11 && !__GNUC__ && !_MSC_VER
#error "Define a thread local storage qualifier for your compiler/platform!"
#endif
...
ATTRIBUTE_TLS static unsigned int tls_int;
Компилятор clang, включенный в бета-версии Xcode 8 и GM, поддерживает C++11 thread_local
Ключевое слово с обоими -std=c++11
а также -std=c++14
(а также варианты GCC).
Более ранние версии Xcode, очевидно, поддерживали локальное хранилище потока в стиле C с использованием ключевых слов. __thread
или же _Thread_local
Согласно видео WWDC 2016 "Что нового в LLVM" (см. обсуждение в 5:50).
Похоже, вам может потребоваться установить минимальную версию OS X, на которую вы нацелены, 10,7 или выше.