Add a C++11 ThreadPool implementation in LLVM
[oota-llvm.git] / unittests / Support / ThreadPool.cpp
1 //========- unittests/Support/ThreadPools.cpp - ThreadPools.h tests --========//
2 //
3 //                     The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9
10 #include "llvm/Support/ThreadPool.h"
11
12 #include "llvm/ADT/STLExtras.h"
13
14 #include "gtest/gtest.h"
15
16 using namespace llvm;
17 using namespace std::chrono;
18
19 /// Try best to make this thread not progress faster than the main thread
20 static void yield() {
21 #ifdef LLVM_ENABLE_THREADS
22   std::this_thread::yield();
23 #endif
24   std::this_thread::sleep_for(milliseconds(200));
25 #ifdef LLVM_ENABLE_THREADS
26   std::this_thread::yield();
27 #endif
28 }
29
30 TEST(ThreadPoolTest, AsyncBarrier) {
31   // test that async & barrier work together properly.
32
33   std::atomic_int checked_in{0};
34
35   ThreadPool Pool;
36   for (size_t i = 0; i < 5; ++i) {
37     Pool.async([&checked_in, i] {
38       yield();
39       ++checked_in;
40     });
41   }
42   ASSERT_EQ(0, checked_in);
43   Pool.wait();
44   ASSERT_EQ(5, checked_in);
45 }
46
47 TEST(ThreadPoolTest, Async) {
48   ThreadPool Pool;
49   std::atomic_int i{0};
50   // sleep here just to ensure that the not-equal is correct.
51   Pool.async([&i] {
52     yield();
53     ++i;
54   });
55   Pool.async([&i] { ++i; });
56   ASSERT_NE(2, i.load());
57   Pool.wait();
58   ASSERT_EQ(2, i.load());
59 }
60
61 TEST(ThreadPoolTest, GetFuture) {
62   ThreadPool Pool;
63   std::atomic_int i{0};
64   // sleep here just to ensure that the not-equal is correct.
65   Pool.async([&i] {
66     yield();
67     ++i;
68   });
69   // Force the future using get()
70   Pool.async([&i] { ++i; }).get();
71   ASSERT_NE(2, i.load());
72   Pool.wait();
73   ASSERT_EQ(2, i.load());
74 }
75
76 TEST(ThreadPoolTest, PoolDestruction) {
77   // Test that we are waiting on destruction
78   std::atomic_int checked_in{0};
79
80   {
81     ThreadPool Pool;
82     for (size_t i = 0; i < 5; ++i) {
83       Pool.async([&checked_in, i] {
84         yield();
85         ++checked_in;
86       });
87     }
88     ASSERT_EQ(0, checked_in);
89   }
90   ASSERT_EQ(5, checked_in);
91 }