1 //===----------------------------------------------------------------------===//
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 // UNSUPPORTED: no-threads
10 // REQUIRES: libcpp-has-thread-api-pthread
11
12 // notify_all_at_thread_exit(...) requires move semantics to transfer the
13 // unique_lock.
14 // UNSUPPORTED: c++03
15
16 // <condition_variable>
17
18 // void notify_all_at_thread_exit(condition_variable& cond, unique_lock<mutex> lk);
19
20 // Test that this function works with threads that were not created by
21 // std::thread. See https://llvm.org/PR30202
22
23
24 #include <condition_variable>
25 #include <mutex>
26 #include <thread>
27 #include <chrono>
28 #include <cassert>
29 #include <pthread.h>
30
31 #include "test_macros.h"
32
33 std::condition_variable cv;
34 std::mutex mut;
35 bool exited = false;
36
37 typedef std::chrono::milliseconds ms;
38 typedef std::chrono::high_resolution_clock Clock;
39
func(void *)40 void* func(void*)
41 {
42 std::unique_lock<std::mutex> lk(mut);
43 std::notify_all_at_thread_exit(cv, std::move(lk));
44 std::this_thread::sleep_for(ms(300));
45 exited = true;
46 return nullptr;
47 }
48
main(int,char **)49 int main(int, char**)
50 {
51 {
52 std::unique_lock<std::mutex> lk(mut);
53 pthread_t id;
54 int res = pthread_create(&id, 0, &func, nullptr);
55 assert(res == 0);
56 Clock::time_point t0 = Clock::now();
57 assert(exited == false);
58 cv.wait(lk);
59 Clock::time_point t1 = Clock::now();
60 assert(exited);
61 assert(t1-t0 > ms(250));
62 pthread_join(id, 0);
63 }
64 exited = false;
65 {
66 std::unique_lock<std::mutex> lk(mut);
67 std::thread t(&func, nullptr);
68 Clock::time_point t0 = Clock::now();
69 assert(exited == false);
70 cv.wait(lk);
71 Clock::time_point t1 = Clock::now();
72 assert(exited);
73 assert(t1-t0 > ms(250));
74 t.join();
75 }
76
77 return 0;
78 }
79