1 //===-- Tests for pthread_exit --------------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "src/pthread/pthread_create.h" 10 #include "src/pthread/pthread_exit.h" 11 #include "src/pthread/pthread_join.h" 12 #include "utils/IntegrationTest/test.h" 13 14 #include <pthread.h> 15 16 bool dtor_called = false; 17 18 class A { 19 int val; 20 21 public: 22 A(int i) { val = i; } 23 24 void set(int i) { val = i; } 25 26 ~A() { 27 val = 0; 28 dtor_called = true; 29 } 30 }; 31 32 thread_local A thread_local_a(123); 33 34 void *func(void *) { 35 // Touch the thread local variable so that it gets initialized and a callback 36 // for its destructor gets registered with __cxa_thread_atexit. 37 thread_local_a.set(321); 38 __llvm_libc::pthread_exit(nullptr); 39 return nullptr; 40 } 41 42 TEST_MAIN() { 43 pthread_t th; 44 void *retval; 45 46 ASSERT_EQ(__llvm_libc::pthread_create(&th, nullptr, func, nullptr), 0); 47 ASSERT_EQ(__llvm_libc::pthread_join(th, &retval), 0); 48 49 ASSERT_TRUE(dtor_called); 50 __llvm_libc::pthread_exit(nullptr); 51 return 0; 52 } 53 54 extern "C" { 55 56 using Destructor = void(void *); 57 58 int __cxa_thread_atexit_impl(Destructor *, void *, void *); 59 60 // We do not link integration tests to C++ runtime pieces like the libcxxabi. 61 // So, we provide our own simple __cxa_thread_atexit implementation. 62 int __cxa_thread_atexit(Destructor *dtor, void *obj, void *) { 63 return __cxa_thread_atexit_impl(dtor, obj, nullptr); 64 } 65 } 66