PageLanguageDetectionTest has the failure rate of 5 - 6% on XP/Vista. Mark it
[chromium-blink-merge.git] / base / thread_local_unittest.cc
blob9653e151edee825576b0b276e3f61503c896d8bc
1 // Copyright (c) 2006-2008 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "base/logging.h"
6 #include "base/simple_thread.h"
7 #include "base/thread_local.h"
8 #include "base/waitable_event.h"
9 #include "testing/gtest/include/gtest/gtest.h"
11 namespace {
13 class ThreadLocalTesterBase : public base::DelegateSimpleThreadPool::Delegate {
14 public:
15 typedef base::ThreadLocalPointer<ThreadLocalTesterBase> TLPType;
17 ThreadLocalTesterBase(TLPType* tlp, base::WaitableEvent* done)
18 : tlp_(tlp), done_(done) { }
19 ~ThreadLocalTesterBase() { }
21 protected:
22 TLPType* tlp_;
23 base::WaitableEvent* done_;
26 class SetThreadLocal : public ThreadLocalTesterBase {
27 public:
28 SetThreadLocal(TLPType* tlp, base::WaitableEvent* done)
29 : ThreadLocalTesterBase(tlp, done), val_(NULL) { }
30 ~SetThreadLocal() { }
32 void set_value(ThreadLocalTesterBase* val) { val_ = val; }
34 virtual void Run() {
35 DCHECK(!done_->IsSignaled());
36 tlp_->Set(val_);
37 done_->Signal();
40 private:
41 ThreadLocalTesterBase* val_;
44 class GetThreadLocal : public ThreadLocalTesterBase {
45 public:
46 GetThreadLocal(TLPType* tlp, base::WaitableEvent* done)
47 : ThreadLocalTesterBase(tlp, done), ptr_(NULL) { }
48 ~GetThreadLocal() { }
50 void set_ptr(ThreadLocalTesterBase** ptr) { ptr_ = ptr; }
52 virtual void Run() {
53 DCHECK(!done_->IsSignaled());
54 *ptr_ = tlp_->Get();
55 done_->Signal();
58 private:
59 ThreadLocalTesterBase** ptr_;
62 } // namespace
64 // In this test, we start 2 threads which will access a ThreadLocalPointer. We
65 // make sure the default is NULL, and the pointers are unique to the threads.
66 TEST(ThreadLocalTest, Pointer) {
67 base::DelegateSimpleThreadPool tp1("ThreadLocalTest tp1", 1);
68 base::DelegateSimpleThreadPool tp2("ThreadLocalTest tp1", 1);
69 tp1.Start();
70 tp2.Start();
72 base::ThreadLocalPointer<ThreadLocalTesterBase> tlp;
74 static ThreadLocalTesterBase* const kBogusPointer =
75 reinterpret_cast<ThreadLocalTesterBase*>(0x1234);
77 ThreadLocalTesterBase* tls_val;
78 base::WaitableEvent done(true, false);
80 GetThreadLocal getter(&tlp, &done);
81 getter.set_ptr(&tls_val);
83 // Check that both threads defaulted to NULL.
84 tls_val = kBogusPointer;
85 done.Reset();
86 tp1.AddWork(&getter);
87 done.Wait();
88 EXPECT_EQ(static_cast<ThreadLocalTesterBase*>(NULL), tls_val);
90 tls_val = kBogusPointer;
91 done.Reset();
92 tp2.AddWork(&getter);
93 done.Wait();
94 EXPECT_EQ(static_cast<ThreadLocalTesterBase*>(NULL), tls_val);
97 SetThreadLocal setter(&tlp, &done);
98 setter.set_value(kBogusPointer);
100 // Have thread 1 set their pointer value to kBogusPointer.
101 done.Reset();
102 tp1.AddWork(&setter);
103 done.Wait();
105 tls_val = NULL;
106 done.Reset();
107 tp1.AddWork(&getter);
108 done.Wait();
109 EXPECT_EQ(kBogusPointer, tls_val);
111 // Make sure thread 2 is still NULL
112 tls_val = kBogusPointer;
113 done.Reset();
114 tp2.AddWork(&getter);
115 done.Wait();
116 EXPECT_EQ(static_cast<ThreadLocalTesterBase*>(NULL), tls_val);
118 // Set thread 2 to kBogusPointer + 1.
119 setter.set_value(kBogusPointer + 1);
121 done.Reset();
122 tp2.AddWork(&setter);
123 done.Wait();
125 tls_val = NULL;
126 done.Reset();
127 tp2.AddWork(&getter);
128 done.Wait();
129 EXPECT_EQ(kBogusPointer + 1, tls_val);
131 // Make sure thread 1 is still kBogusPointer.
132 tls_val = NULL;
133 done.Reset();
134 tp1.AddWork(&getter);
135 done.Wait();
136 EXPECT_EQ(kBogusPointer, tls_val);
138 tp1.JoinAll();
139 tp2.JoinAll();
142 TEST(ThreadLocalTest, Boolean) {
144 base::ThreadLocalBoolean tlb;
145 EXPECT_EQ(false, tlb.Get());
147 tlb.Set(false);
148 EXPECT_EQ(false, tlb.Get());
150 tlb.Set(true);
151 EXPECT_EQ(true, tlb.Get());
154 // Our slot should have been freed, we're all reset.
156 base::ThreadLocalBoolean tlb;
157 EXPECT_EQ(false, tlb.Get());