Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(576)

Unified Diff: src/lazy-instance.h

Issue 10020040: Merged r11194, r11198, r11201, r11214, r11225, r11233, r11240 into 3.9 branch. (Closed) Base URL: https://v8.googlecode.com/svn/branches/3.9
Patch Set: Created 8 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « src/isolate.cc ('k') | src/mips/lithium-mips.cc » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: src/lazy-instance.h
diff --git a/src/lazy-instance.h b/src/lazy-instance.h
index 09dfe2154dc2992305a0b04787d8c3cca3391193..d0893e560470ee345adbd1af45cd295b998fc610 100644
--- a/src/lazy-instance.h
+++ b/src/lazy-instance.h
@@ -65,6 +65,9 @@
// static LazyInstance<MyClass, MyCreateTrait>::type my_instance =
// LAZY_INSTANCE_INITIALIZER;
//
+// WARNING: This implementation of LazyInstance is NOT thread-safe by default.
+// See ThreadSafeInitOnceTrait declared below for that.
+//
// Notes for advanced users:
// LazyInstance can actually be used in two different ways:
//
@@ -104,9 +107,17 @@ struct LeakyInstanceTrait {
// Traits that define how an instance is allocated and accessed.
+// TODO(kalmard): __alignof__ is only defined for GCC > 4.2. Fix alignment issue
+// on MIPS with other compilers.
+#if defined(__GNUC__) && (__GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ > 2))
+#define LAZY_ALIGN(x) __attribute__((aligned(__alignof__(x))))
+#else
+#define LAZY_ALIGN(x)
+#endif
+
template <typename T>
struct StaticallyAllocatedInstanceTrait {
- typedef char StorageType[sizeof(T)];
+ typedef char StorageType[sizeof(T)] LAZY_ALIGN(T);
static T* MutableInstance(StorageType* storage) {
return reinterpret_cast<T*>(storage);
@@ -118,6 +129,8 @@ struct StaticallyAllocatedInstanceTrait {
}
};
+#undef LAZY_ALIGN
+
template <typename T>
struct DynamicallyAllocatedInstanceTrait {
@@ -151,9 +164,29 @@ struct DefaultCreateTrait {
};
+struct ThreadSafeInitOnceTrait {
+ template <typename Function, typename Storage>
+ static void Init(OnceType* once, Function function, Storage storage) {
+ CallOnce(once, function, storage);
+ }
+};
+
+
+// Initialization trait for users who don't care about thread-safety.
+struct SingleThreadInitOnceTrait {
+ template <typename Function, typename Storage>
+ static void Init(OnceType* once, Function function, Storage storage) {
+ if (*once == ONCE_STATE_UNINITIALIZED) {
+ function(storage);
+ *once = ONCE_STATE_DONE;
+ }
+ }
+};
+
+
// TODO(pliard): Handle instances destruction (using global destructors).
template <typename T, typename AllocationTrait, typename CreateTrait,
- typename DestroyTrait /* not used yet. */ >
+ typename InitOnceTrait, typename DestroyTrait /* not used yet. */>
struct LazyInstanceImpl {
public:
typedef typename AllocationTrait::StorageType StorageType;
@@ -164,7 +197,12 @@ struct LazyInstanceImpl {
}
void Init() const {
- CallOnce(&once_, &InitInstance, &storage_);
+ InitOnceTrait::Init(
+ &once_,
+ // Casts to void* are needed here to avoid breaking strict aliasing
+ // rules.
+ reinterpret_cast<void(*)(void*)>(&InitInstance), // NOLINT
+ reinterpret_cast<void*>(&storage_));
}
public:
@@ -180,35 +218,40 @@ struct LazyInstanceImpl {
mutable OnceType once_;
// Note that the previous field, OnceType, is an AtomicWord which guarantees
- // the correct alignment of the storage field below.
+ // 4-byte alignment of the storage field below. If compiling with GCC (>4.2),
+ // the LAZY_ALIGN macro above will guarantee correctness for any alignment.
mutable StorageType storage_;
};
template <typename T,
typename CreateTrait = DefaultConstructTrait<T>,
+ typename InitOnceTrait = SingleThreadInitOnceTrait,
typename DestroyTrait = LeakyInstanceTrait<T> >
struct LazyStaticInstance {
- typedef LazyInstanceImpl<T, StaticallyAllocatedInstanceTrait<T>, CreateTrait,
- DestroyTrait> type;
+ typedef LazyInstanceImpl<T, StaticallyAllocatedInstanceTrait<T>,
+ CreateTrait, InitOnceTrait, DestroyTrait> type;
};
template <typename T,
typename CreateTrait = DefaultConstructTrait<T>,
+ typename InitOnceTrait = SingleThreadInitOnceTrait,
typename DestroyTrait = LeakyInstanceTrait<T> >
struct LazyInstance {
// A LazyInstance is a LazyStaticInstance.
- typedef typename LazyStaticInstance<T, CreateTrait, DestroyTrait>::type type;
+ typedef typename LazyStaticInstance<T, CreateTrait, InitOnceTrait,
+ DestroyTrait>::type type;
};
template <typename T,
typename CreateTrait = DefaultConstructTrait<T>,
+ typename InitOnceTrait = SingleThreadInitOnceTrait,
typename DestroyTrait = LeakyInstanceTrait<T> >
struct LazyDynamicInstance {
- typedef LazyInstanceImpl<T, DynamicallyAllocatedInstanceTrait<T>, CreateTrait,
- DestroyTrait> type;
+ typedef LazyInstanceImpl<T, DynamicallyAllocatedInstanceTrait<T>,
+ CreateTrait, InitOnceTrait, DestroyTrait> type;
};
} } // namespace v8::internal
« no previous file with comments | « src/isolate.cc ('k') | src/mips/lithium-mips.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698