source: webkit/trunk/JavaScriptCore/wtf/ThreadSpecific.h@ 35419

Last change on this file since 35419 was 35194, checked in by [email protected], 17 years ago

Reviewed by Geoff.

Check pthread_key_create return value.

This check was helpful when debugging a crash in run-webkit-tests --threaded that happened
because JSGlobalData objects were not deleted, and we were running out of pthread keys soon.
It also looks useful for production builds.

  • wtf/ThreadSpecific.h: (WTF::::ThreadSpecific):
  • Property svn:eol-style set to native
File size: 3.6 KB
Line 
1/*
2 * Copyright (C) 2008 Apple Inc. All rights reserved.
3 *
4 * Redistribution and use in source and binary forms, with or without
5 * modification, are permitted provided that the following conditions
6 * are met:
7 *
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the
12 * documentation and/or other materials provided with the distribution.
13 * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
14 * its contributors may be used to endorse or promote products derived
15 * from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
18 * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
19 * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
20 * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
21 * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
22 * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
23 * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
24 * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 */
28
29#ifndef WTF_ThreadSpecific_h
30#define WTF_ThreadSpecific_h
31
32#include <wtf/Noncopyable.h>
33
34#if USE(PTHREADS) || PLATFORM(WIN)
35// Windows currently doesn't use pthreads for basic threading, but implementing destructor functions is easier
36// with pthreads, so we use it here.
37#include <pthread.h>
38#endif
39
40namespace WTF {
41
42template<typename T> class ThreadSpecific : Noncopyable {
43public:
44 ThreadSpecific();
45 T* operator->();
46 operator T*();
47 T& operator*();
48 ~ThreadSpecific();
49
50private:
51 T* get();
52 void set(T*);
53 void static destroy(void* ptr);
54
55#if USE(PTHREADS) || PLATFORM(WIN)
56 struct Data : Noncopyable {
57 Data(T* value, ThreadSpecific<T>* owner) : value(value), owner(owner) {}
58
59 T* value;
60 ThreadSpecific<T>* owner;
61 };
62
63 pthread_key_t m_key;
64#endif
65};
66
67#if USE(PTHREADS) || PLATFORM(WIN)
68template<typename T>
69inline ThreadSpecific<T>::ThreadSpecific()
70{
71 int error = pthread_key_create(&m_key, destroy);
72 if (error)
73 CRASH();
74}
75
76template<typename T>
77inline ThreadSpecific<T>::~ThreadSpecific()
78{
79 pthread_key_delete(m_key); // Does not invoke destructor functions.
80}
81
82template<typename T>
83inline T* ThreadSpecific<T>::get()
84{
85 Data* data = static_cast<Data*>(pthread_getspecific(m_key));
86 return data ? data->value : 0;
87}
88
89template<typename T>
90inline void ThreadSpecific<T>::set(T* ptr)
91{
92 ASSERT(!get());
93 pthread_setspecific(m_key, new Data(ptr, this));
94}
95
96template<typename T>
97inline void ThreadSpecific<T>::destroy(void* ptr)
98{
99 Data* data = static_cast<Data*>(ptr);
100 pthread_setspecific(data->owner->m_key, 0);
101 delete data->value;
102 delete data;
103}
104
105#else
106#error ThreadSpecific is not implemented for this platform.
107#endif
108
109template<typename T>
110inline ThreadSpecific<T>::operator T*()
111{
112 T* ptr = static_cast<T*>(get());
113 if (!ptr) {
114 ptr = new T();
115 set(ptr);
116 }
117 return ptr;
118}
119
120template<typename T>
121inline T* ThreadSpecific<T>::operator->()
122{
123 return operator T*();
124}
125
126template<typename T>
127inline T& ThreadSpecific<T>::operator*()
128{
129 return *operator T*();
130}
131
132}
133
134#endif
Note: See TracBrowser for help on using the repository browser.