From e9fcf8fc9864cac86eeff530128c6b14e1cd2d48 Mon Sep 17 00:00:00 2001 From: "bmeurer@chromium.org" Date: Wed, 31 Jul 2013 07:51:46 +0000 Subject: [PATCH] Revert the latest set of platform changes. Revert "Fix NaCl build." Revert "Revert target arch detection." Revert "Fix typo." Revert "Simplify implementation of Mutex." Revert "Fix for older clang releases that lack __has_extension." Revert "Reland initial bits of "Implement correct OS and CC detection."" TBR=danno@chromium.org,svenpanne@chromium.org Review URL: https://codereview.chromium.org/21095008 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@15976 ce2b1a6d-e550-0410-aec6-3dcde31c8c00 --- src/assembler.cc | 5 +- src/checks.h | 6 +- src/d8-debug.cc | 4 +- src/d8-debug.h | 3 +- src/d8.cc | 5 +- src/d8.h | 2 +- src/debug-agent.cc | 8 +- src/debug-agent.h | 4 +- src/debug.cc | 35 ++- src/debug.h | 9 +- src/globals.h | 396 +++++++++--------------- src/heap.cc | 2 +- src/ia32/macro-assembler-ia32.cc | 2 +- src/isolate.cc | 26 +- src/isolate.h | 16 +- src/log-utils.cc | 2 +- src/mutex.cc | 110 ------- src/mutex.h | 130 -------- src/optimizing-compiler-thread.cc | 8 +- src/optimizing-compiler-thread.h | 10 +- src/platform-cygwin.cc | 2 +- src/platform-freebsd.cc | 2 +- src/platform-linux.cc | 2 +- src/platform-macos.cc | 2 +- src/platform-nullos.cc | 31 ++ src/platform-openbsd.cc | 2 +- src/platform-posix.cc | 42 +++ src/platform-solaris.cc | 2 +- src/platform-win32.cc | 42 ++- src/platform.h | 72 ++++- src/sampler.cc | 2 +- src/spaces.cc | 2 +- src/spaces.h | 9 +- src/v8threads.cc | 8 +- src/v8threads.h | 2 +- src/win32-headers.h | 1 + test/cctest/cctest.gyp | 3 +- test/cctest/test-debug.cc | 2 +- test/cctest/{test-semaphore.cc => test-lock.cc} | 33 +- test/cctest/test-mutex.cc | 70 ----- test/cctest/test-platform-linux.cc | 15 +- test/cctest/test-platform-nullos.cc | 8 +- tools/gyp/v8.gyp | 2 - 43 files changed, 476 insertions(+), 663 deletions(-) delete mode 100644 src/mutex.cc delete mode 100644 src/mutex.h rename test/cctest/{test-semaphore.cc => test-lock.cc} (74%) delete mode 100644 test/cctest/test-mutex.cc diff --git a/src/assembler.cc b/src/assembler.cc index ab957be..ae8a0b5 100644 --- a/src/assembler.cc +++ b/src/assembler.cc @@ -891,7 +891,7 @@ void ExternalReference::SetUp() { double_constants.the_hole_nan = BitCast(kHoleNanInt64); double_constants.negative_infinity = -V8_INFINITY; - math_exp_data_mutex = new Mutex; + math_exp_data_mutex = OS::CreateMutex(); } @@ -899,7 +899,7 @@ void ExternalReference::InitializeMathExpData() { // Early return? if (math_exp_data_initialized) return; - ScopedLock with(math_exp_data_mutex); + math_exp_data_mutex->Lock(); if (!math_exp_data_initialized) { // If this is changed, generated code must be adapted too. const int kTableSizeBits = 11; @@ -935,6 +935,7 @@ void ExternalReference::InitializeMathExpData() { math_exp_data_initialized = true; } + math_exp_data_mutex->Unlock(); } diff --git a/src/checks.h b/src/checks.h index 1feecf3..b309e2c 100644 --- a/src/checks.h +++ b/src/checks.h @@ -30,8 +30,6 @@ #include -#include "globals.h" - #include "../include/v8stdint.h" extern "C" void V8_Fatal(const char* file, int line, const char* format, ...); @@ -234,7 +232,7 @@ inline void CheckNonEqualsHelper(const char* file, // Use C++11 static_assert if possible, which gives error // messages that are easier to understand on first sight. -#if V8_CXX_STATIC_ASSERT +#if __cplusplus >= 201103L #define STATIC_CHECK(test) static_assert(test, #test) #else // This is inspired by the static assertion facility in boost. This @@ -256,7 +254,7 @@ template class StaticAssertionHelper { }; typedef \ StaticAssertionHelper((test))>)> \ SEMI_STATIC_JOIN(__StaticAssertTypedef__, __LINE__) -#endif // V8_CXX_STATIC_ASSERT +#endif extern bool FLAG_enable_slow_asserts; diff --git a/src/d8-debug.cc b/src/d8-debug.cc index 5499d20..9a72518 100644 --- a/src/d8-debug.cc +++ b/src/d8-debug.cc @@ -248,7 +248,7 @@ void RemoteDebugger::ConnectionClosed() { void RemoteDebugger::AddEvent(RemoteDebuggerEvent* event) { - i::ScopedLock lock(&event_access_); + i::ScopedLock lock(event_access_); if (head_ == NULL) { ASSERT(tail_ == NULL); head_ = event; @@ -263,7 +263,7 @@ void RemoteDebugger::AddEvent(RemoteDebuggerEvent* event) { RemoteDebuggerEvent* RemoteDebugger::GetEvent() { - i::ScopedLock lock(&event_access_); + i::ScopedLock lock(event_access_); ASSERT(head_ != NULL); RemoteDebuggerEvent* result = head_; head_ = head_->next(); diff --git a/src/d8-debug.h b/src/d8-debug.h index 276cbd8..2386b6b 100644 --- a/src/d8-debug.h +++ b/src/d8-debug.h @@ -53,6 +53,7 @@ class RemoteDebugger { explicit RemoteDebugger(Isolate* isolate, int port) : isolate_(isolate), port_(port), + event_access_(i::OS::CreateMutex()), event_available_(i::OS::CreateSemaphore(0)), head_(NULL), tail_(NULL) {} void Run(); @@ -83,7 +84,7 @@ class RemoteDebugger { // Linked list of events from debugged V8 and from keyboard input. Access to // the list is guarded by a mutex and a semaphore signals new items in the // list. - i::Mutex event_access_; + i::Mutex* event_access_; i::Semaphore* event_available_; RemoteDebuggerEvent* head_; RemoteDebuggerEvent* tail_; diff --git a/src/d8.cc b/src/d8.cc index 4cdafee..1efe2ae 100644 --- a/src/d8.cc +++ b/src/d8.cc @@ -157,7 +157,7 @@ CounterMap* Shell::counter_map_; i::OS::MemoryMappedFile* Shell::counters_file_ = NULL; CounterCollection Shell::local_counters_; CounterCollection* Shell::counters_ = &local_counters_; -i::Mutex Shell::context_mutex_; +i::Mutex* Shell::context_mutex_(i::OS::CreateMutex()); Persistent Shell::utility_context_; #endif // V8_SHARED @@ -925,7 +925,7 @@ void Shell::InitializeDebugger(Isolate* isolate) { Local Shell::CreateEvaluationContext(Isolate* isolate) { #ifndef V8_SHARED // This needs to be a critical section since this is not thread-safe - i::ScopedLock lock(&context_mutex_); + i::ScopedLock lock(context_mutex_); #endif // V8_SHARED // Initialize the global objects Handle global_template = CreateGlobalTemplate(isolate); @@ -1011,6 +1011,7 @@ void Shell::OnExit() { "-------------+\n"); delete [] counters; } + delete context_mutex_; delete counters_file_; delete counter_map_; #endif // V8_SHARED diff --git a/src/d8.h b/src/d8.h index 7e5e3d5..4f04342 100644 --- a/src/d8.h +++ b/src/d8.h @@ -388,7 +388,7 @@ class Shell : public i::AllStatic { static CounterCollection local_counters_; static CounterCollection* counters_; static i::OS::MemoryMappedFile* counters_file_; - static i::Mutex context_mutex_; + static i::Mutex* context_mutex_; static Counter* GetCounter(const char* name, bool is_histogram); static void InstallUtilityScript(Isolate* isolate); diff --git a/src/debug-agent.cc b/src/debug-agent.cc index fc16bf9..811c00e 100644 --- a/src/debug-agent.cc +++ b/src/debug-agent.cc @@ -106,7 +106,7 @@ static const char* kCreateSessionMessage = "Remote debugging session already active\r\n"; void DebuggerAgent::CreateSession(Socket* client) { - ScopedLock with(&session_access_); + ScopedLock with(session_access_); // If another session is already established terminate this one. if (session_ != NULL) { @@ -123,7 +123,7 @@ void DebuggerAgent::CreateSession(Socket* client) { void DebuggerAgent::CloseSession() { - ScopedLock with(&session_access_); + ScopedLock with(session_access_); // Terminate the session. if (session_ != NULL) { @@ -136,7 +136,7 @@ void DebuggerAgent::CloseSession() { void DebuggerAgent::DebuggerMessage(const v8::Debug::Message& message) { - ScopedLock with(&session_access_); + ScopedLock with(session_access_); // Forward the message handling to the session. if (session_ != NULL) { @@ -154,7 +154,7 @@ void DebuggerAgent::OnSessionClosed(DebuggerAgentSession* session) { } // Terminate the session. - ScopedLock with(&session_access_); + ScopedLock with(session_access_); ASSERT(session == session_); if (session == session_) { session_->Shutdown(); diff --git a/src/debug-agent.h b/src/debug-agent.h index 577239c..6115190 100644 --- a/src/debug-agent.h +++ b/src/debug-agent.h @@ -48,7 +48,7 @@ class DebuggerAgent: public Thread { isolate_(Isolate::Current()), name_(StrDup(name)), port_(port), server_(OS::CreateSocket()), terminate_(false), - session_(NULL), + session_access_(OS::CreateMutex()), session_(NULL), terminate_now_(OS::CreateSemaphore(0)), listening_(OS::CreateSemaphore(0)) { ASSERT(isolate_->debugger_agent_instance() == NULL); @@ -76,7 +76,7 @@ class DebuggerAgent: public Thread { int port_; // Port to use for the agent. Socket* server_; // Server socket for listen/accept. bool terminate_; // Termination flag. - Mutex session_access_; // Mutex guarging access to session_. + Mutex* session_access_; // Mutex guarging access to session_. DebuggerAgentSession* session_; // Current active session if any. Semaphore* terminate_now_; // Semaphore to signal termination. Semaphore* listening_; diff --git a/src/debug.cc b/src/debug.cc index 80885da..a0b9884 100644 --- a/src/debug.cc +++ b/src/debug.cc @@ -2606,6 +2606,7 @@ Debugger::Debugger(Isolate* isolate) message_handler_(NULL), debugger_unload_pending_(false), host_dispatch_handler_(NULL), + dispatch_handler_access_(OS::CreateMutex()), debug_message_dispatch_handler_(NULL), message_dispatch_helper_thread_(NULL), host_dispatch_micros_(100 * 1000), @@ -2618,6 +2619,8 @@ Debugger::Debugger(Isolate* isolate) Debugger::~Debugger() { + delete dispatch_handler_access_; + dispatch_handler_access_ = 0; delete command_received_; command_received_ = 0; } @@ -3300,7 +3303,7 @@ void Debugger::SetHostDispatchHandler(v8::Debug::HostDispatchHandler handler, void Debugger::SetDebugMessageDispatchHandler( v8::Debug::DebugMessageDispatchHandler handler, bool provide_locker) { - ScopedLock with(&dispatch_handler_access_); + ScopedLock with(dispatch_handler_access_); debug_message_dispatch_handler_ = handler; if (provide_locker && message_dispatch_helper_thread_ == NULL) { @@ -3343,7 +3346,7 @@ void Debugger::ProcessCommand(Vector command, MessageDispatchHelperThread* dispatch_thread; { - ScopedLock with(&dispatch_handler_access_); + ScopedLock with(dispatch_handler_access_); dispatch_thread = message_dispatch_helper_thread_; } @@ -3463,7 +3466,7 @@ void Debugger::WaitForAgent() { void Debugger::CallMessageDispatchHandler() { v8::Debug::DebugMessageDispatchHandler handler; { - ScopedLock with(&dispatch_handler_access_); + ScopedLock with(dispatch_handler_access_); handler = Debugger::debug_message_dispatch_handler_; } if (handler != NULL) { @@ -3784,20 +3787,24 @@ void CommandMessageQueue::Expand() { LockingCommandMessageQueue::LockingCommandMessageQueue(Logger* logger, int size) - : logger_(logger), queue_(size) {} + : logger_(logger), queue_(size) { + lock_ = OS::CreateMutex(); +} -LockingCommandMessageQueue::~LockingCommandMessageQueue() {} +LockingCommandMessageQueue::~LockingCommandMessageQueue() { + delete lock_; +} -bool LockingCommandMessageQueue::IsEmpty() { - ScopedLock sl(&lock_); +bool LockingCommandMessageQueue::IsEmpty() const { + ScopedLock sl(lock_); return queue_.IsEmpty(); } CommandMessage LockingCommandMessageQueue::Get() { - ScopedLock sl(&lock_); + ScopedLock sl(lock_); CommandMessage result = queue_.Get(); logger_->DebugEvent("Get", result.text()); return result; @@ -3805,14 +3812,14 @@ CommandMessage LockingCommandMessageQueue::Get() { void LockingCommandMessageQueue::Put(const CommandMessage& message) { - ScopedLock sl(&lock_); + ScopedLock sl(lock_); queue_.Put(message); logger_->DebugEvent("Put", message.text()); } void LockingCommandMessageQueue::Clear() { - ScopedLock sl(&lock_); + ScopedLock sl(lock_); queue_.Clear(); } @@ -3820,17 +3827,19 @@ void LockingCommandMessageQueue::Clear() { MessageDispatchHelperThread::MessageDispatchHelperThread(Isolate* isolate) : Thread("v8:MsgDispHelpr"), isolate_(isolate), sem_(OS::CreateSemaphore(0)), - already_signalled_(false) {} + mutex_(OS::CreateMutex()), already_signalled_(false) { +} MessageDispatchHelperThread::~MessageDispatchHelperThread() { + delete mutex_; delete sem_; } void MessageDispatchHelperThread::Schedule() { { - ScopedLock lock(&mutex_); + ScopedLock lock(mutex_); if (already_signalled_) { return; } @@ -3844,7 +3853,7 @@ void MessageDispatchHelperThread::Run() { while (true) { sem_->Wait(); { - ScopedLock lock(&mutex_); + ScopedLock lock(mutex_); already_signalled_ = false; } { diff --git a/src/debug.h b/src/debug.h index e7b919e..67debc7 100644 --- a/src/debug.h +++ b/src/debug.h @@ -763,15 +763,14 @@ class LockingCommandMessageQueue BASE_EMBEDDED { public: LockingCommandMessageQueue(Logger* logger, int size); ~LockingCommandMessageQueue(); - bool IsEmpty(); + bool IsEmpty() const; CommandMessage Get(); void Put(const CommandMessage& message); void Clear(); - private: Logger* logger_; CommandMessageQueue queue_; - Mutex lock_; + Mutex* lock_; DISALLOW_COPY_AND_ASSIGN(LockingCommandMessageQueue); }; @@ -930,7 +929,7 @@ class Debugger { v8::Debug::MessageHandler2 message_handler_; bool debugger_unload_pending_; // Was message handler cleared? v8::Debug::HostDispatchHandler host_dispatch_handler_; - Mutex dispatch_handler_access_; // Mutex guarding dispatch handler. + Mutex* dispatch_handler_access_; // Mutex guarding dispatch handler. v8::Debug::DebugMessageDispatchHandler debug_message_dispatch_handler_; MessageDispatchHelperThread* message_dispatch_helper_thread_; int host_dispatch_micros_; @@ -1057,7 +1056,7 @@ class MessageDispatchHelperThread: public Thread { Isolate* isolate_; Semaphore* const sem_; - Mutex mutex_; + Mutex* const mutex_; bool already_signalled_; DISALLOW_COPY_AND_ASSIGN(MessageDispatchHelperThread); diff --git a/src/globals.h b/src/globals.h index e13287c..26fd531 100644 --- a/src/globals.h +++ b/src/globals.h @@ -28,176 +28,72 @@ #ifndef V8_GLOBALS_H_ #define V8_GLOBALS_H_ -// ---------------------------------------------------------------------------- -// Operating system detection (V8_OS_x) -// -// ANDROID - Android -// BSD4 - Any BSD 4.4 system -// CYGWIN - Cygwin -// DARWIN - Darwin / Mac OS X -// FREEBSD - FreeBSD -// LINUX - Linux -// NACL - Native Client -// NETBSD - NetBSD -// OPENBSD - OpenBSD -// SOLARIS - Solaris -// UNIX - Any UNIX BSD/SYSV system -// WIN32 - Win32 (Windows 2000/XP/Vista/7 and Windows Server 2003/2008) - -#if defined(ANDROID) || defined(__ANDROID__) -# define V8_OS_ANDROID 1 -# define V8_OS_LINUX 1 -# define V8_OS_UNIX 1 -#elif defined(__APPLE__) && defined(__MACH__) -# define V8_OS_DARWIN 1 -# define V8_OS_BSD4 1 -# define V8_OS_UNIX 1 -#elif defined(__CYGWIN__) -# define V8_OS_CYGWIN 1 -# define V8_OS_UNIX 1 -#elif defined(WIN64) || defined(_WIN64) || defined(__WIN64__) -# define V8_OS_WIN32 1 -# define V8_OS_WIN64 1 -#elif defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || \ - (defined(__MWERKS__) && defined(__INTEL__)) -# define V8_OS_WIN32 1 -#elif defined(__sun) || defined(sun) -# define V8_OS_SOLARIS 1 -# define V8_OS_UNIX 1 -#elif defined(__native_client__) -# define V8_OS_NACL 1 -# define V8_OS_UNIX 1 -#elif defined(__linux__) || defined(__linux) -# define V8_OS_LINUX 1 -# define V8_OS_UNIX 1 -#elif defined(__FreeBSD__) || defined(__DragonFly__) -# define V8_OS_FREEBSD 1 -# define V8_OS_BSD4 1 -# define V8_OS_UNIX 1 -#elif defined(__NetBSD__) -# define V8_OS_NETBSD 1 -# define V8_OS_BSD4 1 -# define V8_OS_UNIX 1 -#elif defined(__OpenBSD__) -# define V8_OS_OPENBSD 1 -# define V8_OS_BSD4 1 -# define V8_OS_UNIX 1 -#else -# error Operating system was not detected as supported by v8 -#endif +// Define V8_INFINITY +#define V8_INFINITY INFINITY +// GCC specific stuff +#ifdef __GNUC__ -// ---------------------------------------------------------------------------- -// Compiler detection (V8_CC_x) -// -// CLANG - C++ front-end for the LLVM compiler -// GNU - GNU C++ or compatible -// INTEL - Intel C++ for Linux or Windows -// MINGW - Minimalistic GNU for Windows Compiler -// MIPS - MIPSpro C++ -// MSVC - Microsoft Visual C/C++ or compatible -// RVCT - ARM Realview Compiler Suite +#define __GNUC_VERSION_FOR_INFTY__ (__GNUC__ * 10000 + __GNUC_MINOR__ * 100) -#if defined(_MSC_VER) -# define V8_CC_MSVC 1 -# if defined(__INTEL_COMPILER) -# define V8_CC_INTEL 1 -# endif -#elif defined(__GNUC__) -# define V8_CC_GNU 1 -# if defined(__MINGW64__) -# define V8_CC_MINGW 1 -# define V8_CC_MINGW64 1 -# elif defined(__MINGW32__) -# define V8_CC_MINGW 1 -# define V8_CC_MINGW32 1 -# elif defined(__ARMCC__) || defined(__CC_ARM) -# define V8_CC_RVCT 1 // ARM Realview Compiler Suite also masquerades as GCC -# elif defined(__INTEL_COMPILER) -# define V8_CC_INTEL 1 // Intel C++ also masquerades as GCC 3.2.0 -# elif defined(__clang__) -# define V8_CC_CLANG 1 // Clang also masquerades as GCC 4.2.1 -# ifndef __has_extension -# define __has_extension __has_feature // Compatibility with older releases -# endif -# endif -#elif defined(__ARMCC__) || defined(__CC_ARM) -# define V8_CC_RVCT 1 -#elif defined(__INTEL_COMPILER) -# define V8_CC_INTEL 1 -#elif defined(__SUNPRO_CC) || defined(__SUNPRO_C) -# define V8_CC_SUN 1 -#else -# error Compiler was not detected as supported by v8 +// Unfortunately, the INFINITY macro cannot be used with the '-pedantic' +// warning flag and certain versions of GCC due to a bug: +// http://gcc.gnu.org/bugzilla/show_bug.cgi?id=11931 +// For now, we use the more involved template-based version from , but +// only when compiling with GCC versions affected by the bug (2.96.x - 4.0.x) +// __GNUC_PREREQ is not defined in GCC for Mac OS X, so we define our own macro +#if __GNUC_VERSION_FOR_INFTY__ >= 29600 && __GNUC_VERSION_FOR_INFTY__ < 40100 +#include +#undef V8_INFINITY +#define V8_INFINITY std::numeric_limits::infinity() #endif +#undef __GNUC_VERSION_FOR_INFTY__ -#if V8_CC_GNU -# define V8_GNUC_PREREQ(major, minor) \ - (__GNUC__ > (major) || (__GNUC__ == (major) && __GNUC_MINOR__ >= (minor))) -#else -# define V8_GNUC_PREREQ(major, minor) 0 -#endif // V8_CC_GNU - - -// ---------------------------------------------------------------------------- -// Compiler features +#endif // __GNUC__ -// C++11 deleted functions -#if __cplusplus >= 201103L -# define V8_CXX_DELETED_FUNCTIONS 1 -#elif V8_CC_CLANG -# define V8_CXX_DELETED_FUNCTIONS __has_feature(cxx_deleted_functions) -#else -# define V8_CXX_DELETED_FUNCTIONS (defined(__GXX_EXPERIMENTAL_CXX0X__) && \ - V8_GNUC_PREREQ(4, 4)) +#ifdef _MSC_VER +#undef V8_INFINITY +#define V8_INFINITY HUGE_VAL #endif -// C++11 static_assert() -#if __cplusplus >= 201103L -# define V8_CXX_STATIC_ASSERT 1 -#elif V8_CC_CLANG -# define V8_CXX_STATIC_ASSERT (__has_extension(cxx_static_assert) || \ - __has_feature(cxx_static_assert)) -#else -# define V8_CXX_STATIC_ASSERT (defined(__GXX_EXPERIMENTAL_CXX0X__) && \ - V8_GNUC_PREREQ(4, 3)) -#endif +#include "../include/v8stdint.h" + +namespace v8 { +namespace internal { -// ---------------------------------------------------------------------------- -// Host architecture detection. For more info on what's defined, see: +// Processor architecture detection. For more info on what's defined, see: // http://msdn.microsoft.com/en-us/library/b0084kay.aspx // http://www.agner.org/optimize/calling_conventions.pdf // or with gcc, run: "echo | gcc -E -dM -" - #if defined(_M_X64) || defined(__x86_64__) -# if V8_OS_NACL +#if defined(__native_client__) // For Native Client builds of V8, use V8_TARGET_ARCH_ARM, so that V8 // generates ARM machine code, together with a portable ARM simulator // compiled for the host architecture in question. // // Since Native Client is ILP-32 on all architectures we use // V8_HOST_ARCH_IA32 on both 32- and 64-bit x86. -# define V8_HOST_ARCH_IA32 1 -# define V8_HOST_ARCH_32_BIT 1 -# define V8_HOST_CAN_READ_UNALIGNED 1 -# else -# define V8_HOST_ARCH_X64 1 -# define V8_HOST_ARCH_64_BIT 1 -# define V8_HOST_CAN_READ_UNALIGNED 1 -# endif // V8_OS_NACL +#define V8_HOST_ARCH_IA32 1 +#define V8_HOST_ARCH_32_BIT 1 +#define V8_HOST_CAN_READ_UNALIGNED 1 +#else +#define V8_HOST_ARCH_X64 1 +#define V8_HOST_ARCH_64_BIT 1 +#define V8_HOST_CAN_READ_UNALIGNED 1 +#endif // __native_client__ #elif defined(_M_IX86) || defined(__i386__) -# define V8_HOST_ARCH_IA32 1 -# define V8_HOST_ARCH_32_BIT 1 -# define V8_HOST_CAN_READ_UNALIGNED 1 +#define V8_HOST_ARCH_IA32 1 +#define V8_HOST_ARCH_32_BIT 1 +#define V8_HOST_CAN_READ_UNALIGNED 1 #elif defined(__ARMEL__) -# define V8_HOST_ARCH_ARM 1 -# define V8_HOST_ARCH_32_BIT 1 +#define V8_HOST_ARCH_ARM 1 +#define V8_HOST_ARCH_32_BIT 1 #elif defined(__MIPSEL__) -# define V8_HOST_ARCH_MIPS 1 -# define V8_HOST_ARCH_32_BIT 1 +#define V8_HOST_ARCH_MIPS 1 +#define V8_HOST_ARCH_32_BIT 1 #else -# error Host architecture was not detected as supported by v8 +#error Host architecture was not detected as supported by v8 #endif #if defined(__ARM_ARCH_7A__) || \ @@ -205,125 +101,68 @@ defined(__ARM_ARCH_7__) # define CAN_USE_ARMV7_INSTRUCTIONS 1 # ifndef CAN_USE_VFP3_INSTRUCTIONS -# define CAN_USE_VFP3_INSTRUCTIONS 1 +# define CAN_USE_VFP3_INSTRUCTIONS # endif #endif -// ---------------------------------------------------------------------------- // Target architecture detection. This may be set externally. If not, detect // in the same way as the host architecture, that is, target the native // environment as presented by the compiler. - #if !V8_TARGET_ARCH_X64 && !V8_TARGET_ARCH_IA32 && \ !V8_TARGET_ARCH_ARM && !V8_TARGET_ARCH_MIPS -# if defined(_M_X64) || defined(__x86_64__) -# define V8_TARGET_ARCH_X64 1 -# elif defined(_M_IX86) || defined(__i386__) -# define V8_TARGET_ARCH_IA32 1 -# elif defined(__ARMEL__) -# define V8_TARGET_ARCH_ARM 1 -# elif defined(__MIPSEL__) -# define V8_TARGET_ARCH_MIPS 1 -# else -# error Target architecture was not detected as supported by v8 -# endif +#if defined(_M_X64) || defined(__x86_64__) +#define V8_TARGET_ARCH_X64 1 +#elif defined(_M_IX86) || defined(__i386__) +#define V8_TARGET_ARCH_IA32 1 +#elif defined(__ARMEL__) +#define V8_TARGET_ARCH_ARM 1 +#elif defined(__MIPSEL__) +#define V8_TARGET_ARCH_MIPS 1 +#else +#error Target architecture was not detected as supported by v8 +#endif #endif // Check for supported combinations of host and target architectures. #if V8_TARGET_ARCH_IA32 && !V8_HOST_ARCH_IA32 -# error Target architecture ia32 is only supported on ia32 host -#elif V8_TARGET_ARCH_X64 && !V8_HOST_ARCH_X64 -# error Target architecture x64 is only supported on x64 host -#elif V8_TARGET_ARCH_ARM && !(V8_HOST_ARCH_IA32 || V8_HOST_ARCH_ARM) -# error Target architecture arm is only supported on arm and ia32 host -#elif V8_TARGET_ARCH_MIPS && !(V8_HOST_ARCH_IA32 || V8_HOST_ARCH_MIPS) -# error Target architecture mips is only supported on mips and ia32 host +#error Target architecture ia32 is only supported on ia32 host +#endif +#if V8_TARGET_ARCH_X64 && !V8_HOST_ARCH_X64 +#error Target architecture x64 is only supported on x64 host +#endif +#if (V8_TARGET_ARCH_ARM && !(V8_HOST_ARCH_IA32 || V8_HOST_ARCH_ARM)) +#error Target architecture arm is only supported on arm and ia32 host +#endif +#if (V8_TARGET_ARCH_MIPS && !(V8_HOST_ARCH_IA32 || V8_HOST_ARCH_MIPS)) +#error Target architecture mips is only supported on mips and ia32 host #endif // Determine whether we are running in a simulated environment. // Setting USE_SIMULATOR explicitly from the build script will force // the use of a simulated environment. #if !defined(USE_SIMULATOR) -# if V8_TARGET_ARCH_ARM && !V8_HOST_ARCH_ARM -# define USE_SIMULATOR 1 -# elif V8_TARGET_ARCH_MIPS && !V8_HOST_ARCH_MIPS -# define USE_SIMULATOR 1 -# endif +#if (V8_TARGET_ARCH_ARM && !V8_HOST_ARCH_ARM) +#define USE_SIMULATOR 1 +#endif +#if (V8_TARGET_ARCH_MIPS && !V8_HOST_ARCH_MIPS) +#define USE_SIMULATOR 1 #endif - -// Determine architecture endiannes (we only support little-endian). -#if V8_TARGET_ARCH_IA32 || V8_TARGET_ARCH_X64 || \ - V8_TARGET_ARCH_ARM || V8_TARGET_ARCH_MIPS -# define V8_TARGET_LITTLE_ENDIAN 1 -#else -# error Unknown target architecture endiannes #endif - -// ---------------------------------------------------------------------------- -// Define our own macros for writing 64-bit constants. This is less fragile -// than defining __STDC_CONSTANT_MACROS before including , and it -// works on compilers that don't have it (like MSVC). -#if V8_HOST_ARCH_64_BIT -# if V8_CC_MSVC -# define V8_UINT64_C(x) (x ## UI64) -# define V8_INT64_C(x) (x ## I64) -# define V8_INTPTR_C(x) (x ## I64) -# define V8_PTR_PREFIX "ll" -# elif V8_CC_MINGW -# define V8_UINT64_C(x) (x ## ULL) -# define V8_INT64_C(x) (x ## LL) -# define V8_INTPTR_C(x) (x ## LL) -# define V8_PTR_PREFIX "I64" -# else -# define V8_UINT64_C(x) (x ## UL) -# define V8_INT64_C(x) (x ## L) -# define V8_INTPTR_C(x) (x ## L) -# define V8_PTR_PREFIX "l" -# endif -#else // V8_HOST_ARCH_64_BIT -# define V8_INTPTR_C(x) (x) -# define V8_PTR_PREFIX "" -#endif // V8_HOST_ARCH_64_BIT - -// The following macro works on both 32 and 64-bit platforms. -// Usage: instead of writing 0x1234567890123456 -// write V8_2PART_UINT64_C(0x12345678,90123456); -#define V8_2PART_UINT64_C(a, b) (((static_cast(a) << 32) + 0x##b##u)) - -#if V8_OS_DARWIN -// Fix for Mac OS X defining uintptr_t as "unsigned long": -# define V8PRIxPTR "lx" -#else -# define V8PRIxPTR V8_PTR_PREFIX "x" -#endif // V8_OS_DARWIN -#define V8PRIdPTR V8_PTR_PREFIX "d" -#define V8PRIuPTR V8_PTR_PREFIX "u" - - -// ---------------------------------------------------------------------------- -// Define V8_INFINITY -#if V8_GNUC_PREREQ(2, 96) && !V8_GNUC_PREREQ(4, 1) -// Unfortunately, the INFINITY macro cannot be used with the '-pedantic' -// warning flag and certain versions of GCC due to a bug: -// http://gcc.gnu.org/bugzilla/show_bug.cgi?id=11931 -// For now, we use the more involved template-based version from , but -// only when compiling with GCC versions affected by the bug (2.96.x - 4.0.x) -# include -# define V8_INFINITY std::numeric_limits::infinity() -#elif V8_CC_MSVC -# define V8_INFINITY HUGE_VAL +// Determine architecture endiannes (we only support little-endian). +#if V8_TARGET_ARCH_IA32 +#define V8_TARGET_LITTLE_ENDIAN 1 +#elif V8_TARGET_ARCH_X64 +#define V8_TARGET_LITTLE_ENDIAN 1 +#elif V8_TARGET_ARCH_ARM +#define V8_TARGET_LITTLE_ENDIAN 1 +#elif V8_TARGET_ARCH_MIPS +#define V8_TARGET_LITTLE_ENDIAN 1 #else -# define V8_INFINITY INFINITY +#error Unknown target architecture endiannes #endif - -#include "../include/v8stdint.h" - -namespace v8 { -namespace internal { - // Support for alternative bool type. This is only enabled if the code is // compiled with USE_MYBOOL defined. This catches some nasty type bugs. // For instance, 'bool b = "false";' results in b == true! This is a hidden @@ -344,6 +183,51 @@ typedef unsigned int __my_bool__; typedef uint8_t byte; typedef byte* Address; +// Define our own macros for writing 64-bit constants. This is less fragile +// than defining __STDC_CONSTANT_MACROS before including , and it +// works on compilers that don't have it (like MSVC). +#if V8_HOST_ARCH_64_BIT +#if defined(_MSC_VER) +#define V8_UINT64_C(x) (x ## UI64) +#define V8_INT64_C(x) (x ## I64) +#define V8_INTPTR_C(x) (x ## I64) +#define V8_PTR_PREFIX "ll" +#elif defined(__MINGW64__) +#define V8_UINT64_C(x) (x ## ULL) +#define V8_INT64_C(x) (x ## LL) +#define V8_INTPTR_C(x) (x ## LL) +#define V8_PTR_PREFIX "I64" +#else +#define V8_UINT64_C(x) (x ## UL) +#define V8_INT64_C(x) (x ## L) +#define V8_INTPTR_C(x) (x ## L) +#define V8_PTR_PREFIX "l" +#endif +#else // V8_HOST_ARCH_64_BIT +#define V8_INTPTR_C(x) (x) +#define V8_PTR_PREFIX "" +#endif // V8_HOST_ARCH_64_BIT + +// The following macro works on both 32 and 64-bit platforms. +// Usage: instead of writing 0x1234567890123456 +// write V8_2PART_UINT64_C(0x12345678,90123456); +#define V8_2PART_UINT64_C(a, b) (((static_cast(a) << 32) + 0x##b##u)) + +#define V8PRIxPTR V8_PTR_PREFIX "x" +#define V8PRIdPTR V8_PTR_PREFIX "d" +#define V8PRIuPTR V8_PTR_PREFIX "u" + +// Fix for Mac OS X defining uintptr_t as "unsigned long": +#if defined(__APPLE__) && defined(__MACH__) +#undef V8PRIxPTR +#define V8PRIxPTR "lx" +#endif + +#if (defined(__APPLE__) && defined(__MACH__)) || \ + defined(__FreeBSD__) || defined(__OpenBSD__) +#define USING_BSD_ABI +#endif + // ----------------------------------------------------------------------------- // Constants @@ -446,10 +330,10 @@ F FUNCTION_CAST(Address addr) { } -#if V8_CXX_DELETED_FUNCTIONS -# define DISALLOW_BY_DELETE = delete +#if __cplusplus >= 201103L +#define DISALLOW_BY_DELETE = delete #else -# define DISALLOW_BY_DELETE +#define DISALLOW_BY_DELETE #endif @@ -474,22 +358,24 @@ F FUNCTION_CAST(Address addr) { // Define used for helping GCC to make better inlining. Don't bother for debug // builds. On GCC 3.4.5 using __attribute__((always_inline)) causes compilation // errors in debug build. -#if V8_GNUC_PREREQ(4, 0) && !defined(DEBUG) -# define INLINE(header) inline header __attribute__((always_inline)) -# define NO_INLINE(header) header __attribute__((noinline)) -#elif V8_CC_GNU && !defined(DEBUG) -# define INLINE(header) inline __attribute__((always_inline)) header -# define NO_INLINE(header) __attribute__((noinline)) header -#elif V8_CC_MSVC && !defined(DEBUG) -# define INLINE(header) __forceinline header -# define NO_INLINE(header) header +#if defined(__GNUC__) && !defined(DEBUG) +#if (__GNUC__ >= 4) +#define INLINE(header) inline header __attribute__((always_inline)) +#define NO_INLINE(header) header __attribute__((noinline)) +#else +#define INLINE(header) inline __attribute__((always_inline)) header +#define NO_INLINE(header) __attribute__((noinline)) header +#endif +#elif defined(_MSC_VER) && !defined(DEBUG) +#define INLINE(header) __forceinline header +#define NO_INLINE(header) header #else -# define INLINE(header) inline header -# define NO_INLINE(header) header +#define INLINE(header) inline header +#define NO_INLINE(header) header #endif -#if V8_GNUC_PREREQ(4, 0) +#if defined(__GNUC__) && __GNUC__ >= 4 #define MUST_USE_RESULT __attribute__ ((warn_unused_result)) #else #define MUST_USE_RESULT diff --git a/src/heap.cc b/src/heap.cc index 84dbdf5..7776615 100644 --- a/src/heap.cc +++ b/src/heap.cc @@ -6877,7 +6877,7 @@ bool Heap::SetUp() { store_buffer()->SetUp(); - if (FLAG_parallel_recompilation) relocation_mutex_ = new Mutex; + if (FLAG_parallel_recompilation) relocation_mutex_ = OS::CreateMutex(); #ifdef DEBUG relocation_mutex_locked_by_optimizer_thread_ = false; #endif // DEBUG diff --git a/src/ia32/macro-assembler-ia32.cc b/src/ia32/macro-assembler-ia32.cc index 074ad54..2ab5a25 100644 --- a/src/ia32/macro-assembler-ia32.cc +++ b/src/ia32/macro-assembler-ia32.cc @@ -1933,7 +1933,7 @@ void MacroAssembler::TailCallRuntime(Runtime::FunctionId fid, // If false, it is returned as a pointer to a preallocated by caller memory // region. Pointer to this region should be passed to a function as an // implicit first argument. -#if V8_OS_BSD4 || V8_CC_MINGW32 || V8_OS_CYGWIN +#if defined(USING_BSD_ABI) || defined(__MINGW32__) || defined(__CYGWIN__) static const bool kReturnHandlesDirectly = true; #else static const bool kReturnHandlesDirectly = false; diff --git a/src/isolate.cc b/src/isolate.cc index f1af6d3..61f1e2d 100644 --- a/src/isolate.cc +++ b/src/isolate.cc @@ -343,7 +343,7 @@ Thread::LocalStorageKey Isolate::per_isolate_thread_data_key_; #ifdef DEBUG Thread::LocalStorageKey PerThreadAssertScopeBase::thread_local_key; #endif // DEBUG -Mutex Isolate::process_wide_mutex_; +Mutex* Isolate::process_wide_mutex_ = OS::CreateMutex(); Isolate::ThreadDataTable* Isolate::thread_data_table_ = NULL; Atomic32 Isolate::isolate_counter_ = 0; @@ -352,7 +352,7 @@ Isolate::PerIsolateThreadData* Isolate::AllocatePerIsolateThreadData( ASSERT(!thread_id.Equals(ThreadId::Invalid())); PerIsolateThreadData* per_thread = new PerIsolateThreadData(this, thread_id); { - ScopedLock lock(&process_wide_mutex_); + ScopedLock lock(process_wide_mutex_); ASSERT(thread_data_table_->Lookup(this, thread_id) == NULL); thread_data_table_->Insert(per_thread); ASSERT(thread_data_table_->Lookup(this, thread_id) == per_thread); @@ -366,11 +366,11 @@ Isolate::PerIsolateThreadData* ThreadId thread_id = ThreadId::Current(); PerIsolateThreadData* per_thread = NULL; { - ScopedLock lock(&process_wide_mutex_); + ScopedLock lock(process_wide_mutex_); per_thread = thread_data_table_->Lookup(this, thread_id); - } - if (per_thread == NULL) { - per_thread = AllocatePerIsolateThreadData(thread_id); + if (per_thread == NULL) { + per_thread = AllocatePerIsolateThreadData(thread_id); + } } return per_thread; } @@ -386,7 +386,7 @@ Isolate::PerIsolateThreadData* Isolate::FindPerThreadDataForThread( ThreadId thread_id) { PerIsolateThreadData* per_thread = NULL; { - ScopedLock lock(&process_wide_mutex_); + ScopedLock lock(process_wide_mutex_); per_thread = thread_data_table_->Lookup(this, thread_id); } return per_thread; @@ -394,7 +394,7 @@ Isolate::PerIsolateThreadData* Isolate::FindPerThreadDataForThread( void Isolate::EnsureDefaultIsolate() { - ScopedLock lock(&process_wide_mutex_); + ScopedLock lock(process_wide_mutex_); if (default_isolate_ == NULL) { isolate_key_ = Thread::CreateThreadLocalKey(); thread_id_key_ = Thread::CreateThreadLocalKey(); @@ -1749,8 +1749,10 @@ Isolate::Isolate() counters_(NULL), code_range_(NULL), // Must be initialized early to allow v8::SetResourceConstraints calls. + break_access_(OS::CreateMutex()), debugger_initialized_(false), // Must be initialized early to allow v8::Debug calls. + debugger_access_(OS::CreateMutex()), logger_(NULL), stats_table_(NULL), stub_cache_(NULL), @@ -1851,7 +1853,7 @@ void Isolate::TearDown() { Deinit(); - { ScopedLock lock(&process_wide_mutex_); + { ScopedLock lock(process_wide_mutex_); thread_data_table_->RemoveAllThreads(this); } @@ -2022,6 +2024,10 @@ Isolate::~Isolate() { delete handle_scope_implementer_; handle_scope_implementer_ = NULL; + delete break_access_; + break_access_ = NULL; + delete debugger_access_; + debugger_access_ = NULL; delete compilation_cache_; compilation_cache_ = NULL; @@ -2121,7 +2127,7 @@ void Isolate::InitializeLoggingAndCounters() { void Isolate::InitializeDebugger() { #ifdef ENABLE_DEBUGGER_SUPPORT - ScopedLock lock(&debugger_access_); + ScopedLock lock(debugger_access_); if (NoBarrier_Load(&debugger_initialized_)) return; InitializeLoggingAndCounters(); debug_ = new Debug(this); diff --git a/src/isolate.h b/src/isolate.h index 009ff78..c008317 100644 --- a/src/isolate.h +++ b/src/isolate.h @@ -544,10 +544,10 @@ class Isolate { static void EnterDefaultIsolate(); // Mutex for serializing access to break control structures. - Mutex* break_access() { return &break_access_; } + Mutex* break_access() { return break_access_; } // Mutex for serializing access to debugger. - Mutex* debugger_access() { return &debugger_access_; } + Mutex* debugger_access() { return debugger_access_; } Address get_address_from_id(AddressId id); @@ -1200,7 +1200,7 @@ class Isolate { // This mutex protects highest_thread_id_, thread_data_table_ and // default_isolate_. - static Mutex process_wide_mutex_; + static Mutex* process_wide_mutex_; static Thread::LocalStorageKey per_isolate_thread_data_key_; static Thread::LocalStorageKey isolate_key_; @@ -1268,9 +1268,9 @@ class Isolate { CompilationCache* compilation_cache_; Counters* counters_; CodeRange* code_range_; - Mutex break_access_; + Mutex* break_access_; Atomic32 debugger_initialized_; - Mutex debugger_access_; + Mutex* debugger_access_; Logger* logger_; StackGuard stack_guard_; StatsTable* stats_table_; @@ -1462,11 +1462,11 @@ class ExecutionAccess BASE_EMBEDDED { } ~ExecutionAccess() { Unlock(isolate_); } - static void Lock(Isolate* isolate) { isolate->break_access()->Lock(); } - static void Unlock(Isolate* isolate) { isolate->break_access()->Unlock(); } + static void Lock(Isolate* isolate) { isolate->break_access_->Lock(); } + static void Unlock(Isolate* isolate) { isolate->break_access_->Unlock(); } static bool TryLock(Isolate* isolate) { - return isolate->break_access()->TryLock(); + return isolate->break_access_->TryLock(); } private: diff --git a/src/log-utils.cc b/src/log-utils.cc index 0a94ca9..6bba882 100644 --- a/src/log-utils.cc +++ b/src/log-utils.cc @@ -48,7 +48,7 @@ Log::Log(Logger* logger) void Log::Initialize(const char* log_file_name) { - mutex_ = new Mutex; + mutex_ = OS::CreateMutex(); message_buffer_ = NewArray(kMessageBufferSize); // --log-all enables all the log flags. diff --git a/src/mutex.cc b/src/mutex.cc deleted file mode 100644 index e02ace5..0000000 --- a/src/mutex.cc +++ /dev/null @@ -1,110 +0,0 @@ -// Copyright 2013 the V8 project authors. All rights reserved. -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following -// disclaimer in the documentation and/or other materials provided -// with the distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived -// from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -#include "mutex.h" - -#include - -#include "checks.h" - -namespace v8 { -namespace internal { - -#if V8_OS_UNIX - -Mutex::Mutex() { - pthread_mutexattr_t attr; - int result = pthread_mutexattr_init(&attr); - ASSERT_EQ(0, result); - result = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); - ASSERT_EQ(0, result); - result = pthread_mutex_init(&mutex_, &attr); - ASSERT_EQ(0, result); - result = pthread_mutexattr_destroy(&attr); - ASSERT_EQ(0, result); - USE(result); -} - - -Mutex::~Mutex() { - pthread_mutex_destroy(&mutex_); -} - - -void Mutex::Lock() { - int result = pthread_mutex_lock(&mutex_); - ASSERT_EQ(0, result); - USE(result); -} - - -void Mutex::Unlock() { - int result = pthread_mutex_unlock(&mutex_); - ASSERT_EQ(0, result); - USE(result); -} - - -bool Mutex::TryLock() { - int result = pthread_mutex_trylock(&mutex_); - // Return false if the lock is busy and locking failed. - if (result == EBUSY) { - return false; - } - ASSERT_EQ(0, result); - return true; -} - -#elif V8_OS_WIN32 - -Mutex::Mutex() { - InitializeCriticalSection(&cs_); -} - - -Mutex::~Mutex() { - DeleteCriticalSection(&cs_); -} - - -void Mutex::Lock() { - EnterCriticalSection(&cs_); -} - - -void Mutex::Unlock() { - LeaveCriticalSection(&cs_); -} - - -bool Mutex::TryLock() { - return TryEnterCriticalSection(&cs_); -} - -#endif // V8_OS_WIN32 - -} } // namespace v8::internal diff --git a/src/mutex.h b/src/mutex.h deleted file mode 100644 index 94a202e..0000000 --- a/src/mutex.h +++ /dev/null @@ -1,130 +0,0 @@ -// Copyright 2013 the V8 project authors. All rights reserved. -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following -// disclaimer in the documentation and/or other materials provided -// with the distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived -// from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. - -#ifndef V8_MUTEX_H_ -#define V8_MUTEX_H_ - -#include "globals.h" - -#if V8_OS_UNIX -#include // NOLINT -#elif V8_OS_WIN32 -#include "win32-headers.h" -#endif - -#include "checks.h" -#include "lazy-instance.h" - -namespace v8 { -namespace internal { - -// ---------------------------------------------------------------------------- -// Mutex -// -// Mutexes are used for serializing access to non-reentrant sections of code. -// The implementations of mutex should allow for nested/recursive locking. -// -class Mutex { - public: - Mutex(); - ~Mutex(); - - // Locks the given mutex. If the mutex is currently unlocked, it becomes - // locked and owned by the calling thread. If the mutex is already locked - // by another thread, suspends the calling thread until the mutex is - // unlocked. - void Lock(); - - // Unlocks the given mutex. The mutex is assumed to be locked and owned - // by the calling thread on entrance. - void Unlock(); - - // Tries to lock the given mutex. Returns true if the mutex was locked - // successfully. - bool TryLock(); - - private: -#if V8_OS_UNIX - pthread_mutex_t mutex_; -#elif V8_OS_WIN32 - CRITICAL_SECTION cs_; -#endif - - DISALLOW_COPY_AND_ASSIGN(Mutex); -}; - - -// ---------------------------------------------------------------------------- -// LazyMutex -// -// POD Mutex initialized lazily (i.e. the first time Pointer() is called). -// Usage: -// static LazyMutex my_mutex = LAZY_MUTEX_INITIALIZER; -// -// void my_function() { -// ScopedLock my_lock(&my_mutex); -// // Do something. -// } -// -typedef LazyDynamicInstance, - ThreadSafeInitOnceTrait>::type LazyMutex; - -#define LAZY_MUTEX_INITIALIZER LAZY_DYNAMIC_INSTANCE_INITIALIZER - - -// ---------------------------------------------------------------------------- -// ScopedLock -// -// Stack-allocated ScopedLocks provide block-scoped locking and -// unlocking of a mutex. -// -class ScopedLock { - public: - explicit ScopedLock(Mutex* mutex): mutex_(mutex) { - ASSERT(mutex_ != NULL); - mutex_->Lock(); - } - - explicit ScopedLock(LazyMutex* lazy_mutex) : mutex_(lazy_mutex->Pointer()) { - ASSERT(mutex_ != NULL); - mutex_->Lock(); - } - - ~ScopedLock() { - mutex_->Unlock(); - } - - private: - Mutex* mutex_; - - DISALLOW_COPY_AND_ASSIGN(ScopedLock); -}; - -} } // namespace v8::internal - -#endif // V8_MUTEX_H_ diff --git a/src/optimizing-compiler-thread.cc b/src/optimizing-compiler-thread.cc index 39fc191..21ef237 100644 --- a/src/optimizing-compiler-thread.cc +++ b/src/optimizing-compiler-thread.cc @@ -39,7 +39,7 @@ namespace internal { void OptimizingCompilerThread::Run() { #ifdef DEBUG - { ScopedLock lock(&thread_id_mutex_); + { ScopedLock lock(thread_id_mutex_); thread_id_ = ThreadId::Current().ToInteger(); } #endif @@ -93,7 +93,7 @@ void OptimizingCompilerThread::CompileNext() { // The function may have already been optimized by OSR. Simply continue. // Use a mutex to make sure that functions marked for install // are always also queued. - ScopedLock mark_and_queue(&install_mutex_); + ScopedLock mark_and_queue(install_mutex_); { Heap::RelocationLock relocation_lock(isolate_->heap()); AllowHandleDereference ahd; optimizing_compiler->info()->closure()->MarkForInstallingRecompiledCode(); @@ -141,7 +141,7 @@ void OptimizingCompilerThread::InstallOptimizedFunctions() { OptimizingCompiler* compiler; while (true) { { // Memory barrier to ensure marked functions are queued. - ScopedLock marked_and_queued(&install_mutex_); + ScopedLock marked_and_queued(install_mutex_); if (!output_queue_.Dequeue(&compiler)) return; } Compiler::InstallOptimizedCode(compiler); @@ -163,7 +163,7 @@ void OptimizingCompilerThread::QueueForOptimization( #ifdef DEBUG bool OptimizingCompilerThread::IsOptimizerThread() { if (!FLAG_parallel_recompilation) return false; - ScopedLock lock(&thread_id_mutex_); + ScopedLock lock(thread_id_mutex_); return ThreadId::Current().ToInteger() == thread_id_; } #endif diff --git a/src/optimizing-compiler-thread.h b/src/optimizing-compiler-thread.h index 336522f..275ceb4 100644 --- a/src/optimizing-compiler-thread.h +++ b/src/optimizing-compiler-thread.h @@ -46,10 +46,12 @@ class OptimizingCompilerThread : public Thread { Thread("OptimizingCompilerThread"), #ifdef DEBUG thread_id_(0), + thread_id_mutex_(OS::CreateMutex()), #endif isolate_(isolate), stop_semaphore_(OS::CreateSemaphore(0)), input_queue_semaphore_(OS::CreateSemaphore(0)), + install_mutex_(OS::CreateMutex()), time_spent_compiling_(0), time_spent_total_(0) { NoBarrier_Store(&stop_thread_, static_cast(false)); @@ -81,14 +83,18 @@ class OptimizingCompilerThread : public Thread { #endif ~OptimizingCompilerThread() { + delete install_mutex_; delete input_queue_semaphore_; delete stop_semaphore_; +#ifdef DEBUG + delete thread_id_mutex_; +#endif } private: #ifdef DEBUG int thread_id_; - Mutex thread_id_mutex_; + Mutex* thread_id_mutex_; #endif Isolate* isolate_; @@ -96,7 +102,7 @@ class OptimizingCompilerThread : public Thread { Semaphore* input_queue_semaphore_; UnboundQueue input_queue_; UnboundQueue output_queue_; - Mutex install_mutex_; + Mutex* install_mutex_; volatile AtomicWord stop_thread_; volatile Atomic32 queue_length_; int64_t time_spent_compiling_; diff --git a/src/platform-cygwin.cc b/src/platform-cygwin.cc index f6412ae..4c7b017 100644 --- a/src/platform-cygwin.cc +++ b/src/platform-cygwin.cc @@ -471,7 +471,7 @@ void OS::SetUp() { // call this setup code within the same millisecond. uint64_t seed = static_cast(TimeCurrentMillis()); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-freebsd.cc b/src/platform-freebsd.cc index 5da6eca..e0917fa 100644 --- a/src/platform-freebsd.cc +++ b/src/platform-freebsd.cc @@ -436,7 +436,7 @@ void OS::SetUp() { // call this setup code within the same millisecond. uint64_t seed = static_cast(TimeCurrentMillis()); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-linux.cc b/src/platform-linux.cc index 800c20a..5c252bb 100644 --- a/src/platform-linux.cc +++ b/src/platform-linux.cc @@ -757,7 +757,7 @@ void OS::SetUp() { // Seed the random number generator. We preserve microsecond resolution. uint64_t seed = Ticks() ^ (getpid() << 16); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-macos.cc b/src/platform-macos.cc index b2d92d5..6135cd1 100644 --- a/src/platform-macos.cc +++ b/src/platform-macos.cc @@ -443,7 +443,7 @@ void OS::SetUp() { // Seed the random number generator. We preserve microsecond resolution. uint64_t seed = Ticks() ^ (getpid() << 16); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-nullos.cc b/src/platform-nullos.cc index eadb300..dd5a3dd 100644 --- a/src/platform-nullos.cc +++ b/src/platform-nullos.cc @@ -477,6 +477,37 @@ void Thread::YieldCPU() { } +class NullMutex : public Mutex { + public: + NullMutex() : data_(NULL) { + UNIMPLEMENTED(); + } + + virtual ~NullMutex() { + UNIMPLEMENTED(); + } + + virtual int Lock() { + UNIMPLEMENTED(); + return 0; + } + + virtual int Unlock() { + UNIMPLEMENTED(); + return 0; + } + + private: + void* data_; +}; + + +Mutex* OS::CreateMutex() { + UNIMPLEMENTED(); + return new NullMutex(); +} + + class NullSemaphore : public Semaphore { public: explicit NullSemaphore(int count) : data_(NULL) { diff --git a/src/platform-openbsd.cc b/src/platform-openbsd.cc index 4771671..e591601 100644 --- a/src/platform-openbsd.cc +++ b/src/platform-openbsd.cc @@ -502,7 +502,7 @@ void OS::SetUp() { // Seed the random number generator. We preserve microsecond resolution. uint64_t seed = Ticks() ^ (getpid() << 16); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-posix.cc b/src/platform-posix.cc index 31fc7a6..13b819b 100644 --- a/src/platform-posix.cc +++ b/src/platform-posix.cc @@ -756,6 +756,48 @@ void Thread::SetThreadLocal(LocalStorageKey key, void* value) { } +class POSIXMutex : public Mutex { + public: + POSIXMutex() { + pthread_mutexattr_t attr; + memset(&attr, 0, sizeof(attr)); + int result = pthread_mutexattr_init(&attr); + ASSERT(result == 0); + result = pthread_mutexattr_settype(&attr, PTHREAD_MUTEX_RECURSIVE); + ASSERT(result == 0); + result = pthread_mutex_init(&mutex_, &attr); + ASSERT(result == 0); + result = pthread_mutexattr_destroy(&attr); + ASSERT(result == 0); + USE(result); + } + + virtual ~POSIXMutex() { pthread_mutex_destroy(&mutex_); } + + virtual int Lock() { return pthread_mutex_lock(&mutex_); } + + virtual int Unlock() { return pthread_mutex_unlock(&mutex_); } + + virtual bool TryLock() { + int result = pthread_mutex_trylock(&mutex_); + // Return false if the lock is busy and locking failed. + if (result == EBUSY) { + return false; + } + ASSERT(result == 0); // Verify no other errors. + return true; + } + + private: + pthread_mutex_t mutex_; // Pthread mutex for POSIX platforms. +}; + + +Mutex* OS::CreateMutex() { + return new POSIXMutex(); +} + + // ---------------------------------------------------------------------------- // POSIX socket support. // diff --git a/src/platform-solaris.cc b/src/platform-solaris.cc index 654d98b..b1d88af 100644 --- a/src/platform-solaris.cc +++ b/src/platform-solaris.cc @@ -479,7 +479,7 @@ void OS::SetUp() { // call this setup code within the same millisecond. uint64_t seed = static_cast(TimeCurrentMillis()); srandom(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform-win32.cc b/src/platform-win32.cc index c0f049c..292c24a 100644 --- a/src/platform-win32.cc +++ b/src/platform-win32.cc @@ -1705,6 +1705,46 @@ void Thread::YieldCPU() { // ---------------------------------------------------------------------------- +// Win32 mutex support. +// +// On Win32 mutexes are implemented using CRITICAL_SECTION objects. These are +// faster than Win32 Mutex objects because they are implemented using user mode +// atomic instructions. Therefore we only do ring transitions if there is lock +// contention. + +class Win32Mutex : public Mutex { + public: + Win32Mutex() { InitializeCriticalSection(&cs_); } + + virtual ~Win32Mutex() { DeleteCriticalSection(&cs_); } + + virtual int Lock() { + EnterCriticalSection(&cs_); + return 0; + } + + virtual int Unlock() { + LeaveCriticalSection(&cs_); + return 0; + } + + + virtual bool TryLock() { + // Returns non-zero if critical section is entered successfully entered. + return TryEnterCriticalSection(&cs_); + } + + private: + CRITICAL_SECTION cs_; // Critical section used for mutex +}; + + +Mutex* OS::CreateMutex() { + return new Win32Mutex(); +} + + +// ---------------------------------------------------------------------------- // Win32 semaphore support. // // On Win32 semaphores are implemented using Win32 Semaphore objects. The @@ -1947,7 +1987,7 @@ void OS::SetUp() { // call this setup code within the same millisecond. uint64_t seed = static_cast(TimeCurrentMillis()); srand(static_cast(seed)); - limit_mutex = new Mutex; + limit_mutex = CreateMutex(); } diff --git a/src/platform.h b/src/platform.h index 51d5698..8b27c19 100644 --- a/src/platform.h +++ b/src/platform.h @@ -100,7 +100,7 @@ int random(); #endif // WIN32 -#include "mutex.h" +#include "lazy-instance.h" #include "utils.h" #include "v8globals.h" @@ -309,6 +309,10 @@ class OS { static int StackWalk(Vector frames); + // Factory method for creating platform dependent Mutex. + // Please use delete to reclaim the storage for the returned Mutex. + static Mutex* CreateMutex(); + // Factory method for creating platform dependent Semaphore. // Please use delete to reclaim the storage for the returned Semaphore. static Semaphore* CreateSemaphore(int count); @@ -712,6 +716,72 @@ class Thread { // ---------------------------------------------------------------------------- +// Mutex +// +// Mutexes are used for serializing access to non-reentrant sections of code. +// The implementations of mutex should allow for nested/recursive locking. + +class Mutex { + public: + virtual ~Mutex() {} + + // Locks the given mutex. If the mutex is currently unlocked, it becomes + // locked and owned by the calling thread, and immediately. If the mutex + // is already locked by another thread, suspends the calling thread until + // the mutex is unlocked. + virtual int Lock() = 0; + + // Unlocks the given mutex. The mutex is assumed to be locked and owned by + // the calling thread on entrance. + virtual int Unlock() = 0; + + // Tries to lock the given mutex. Returns whether the mutex was + // successfully locked. + virtual bool TryLock() = 0; +}; + +struct CreateMutexTrait { + static Mutex* Create() { + return OS::CreateMutex(); + } +}; + +// POD Mutex initialized lazily (i.e. the first time Pointer() is called). +// Usage: +// static LazyMutex my_mutex = LAZY_MUTEX_INITIALIZER; +// +// void my_function() { +// ScopedLock my_lock(my_mutex.Pointer()); +// // Do something. +// } +// +typedef LazyDynamicInstance< + Mutex, CreateMutexTrait, ThreadSafeInitOnceTrait>::type LazyMutex; + +#define LAZY_MUTEX_INITIALIZER LAZY_DYNAMIC_INSTANCE_INITIALIZER + +// ---------------------------------------------------------------------------- +// ScopedLock +// +// Stack-allocated ScopedLocks provide block-scoped locking and +// unlocking of a mutex. +class ScopedLock { + public: + explicit ScopedLock(Mutex* mutex): mutex_(mutex) { + ASSERT(mutex_ != NULL); + mutex_->Lock(); + } + ~ScopedLock() { + mutex_->Unlock(); + } + + private: + Mutex* mutex_; + DISALLOW_COPY_AND_ASSIGN(ScopedLock); +}; + + +// ---------------------------------------------------------------------------- // Socket // diff --git a/src/sampler.cc b/src/sampler.cc index db7a54e..d72ed1a 100644 --- a/src/sampler.cc +++ b/src/sampler.cc @@ -415,7 +415,7 @@ class SamplerThread : public Thread { : Thread(Thread::Options("SamplerThread", kSamplerThreadStackSize)), interval_(interval) {} - static void SetUp() { if (!mutex_) mutex_ = new Mutex; } + static void SetUp() { if (!mutex_) mutex_ = OS::CreateMutex(); } static void TearDown() { delete mutex_; } static void AddActiveSampler(Sampler* sampler) { diff --git a/src/spaces.cc b/src/spaces.cc index 539b77e..5935c4a 100644 --- a/src/spaces.cc +++ b/src/spaces.cc @@ -2043,7 +2043,7 @@ intptr_t FreeListCategory::Concatenate(FreeListCategory* category) { // This is safe (not going to deadlock) since Concatenate operations // are never performed on the same free lists at the same time in // reverse order. - ScopedLock lock_target(mutex()); + ScopedLock lock_target(mutex_); ScopedLock lock_source(category->mutex()); free_bytes = category->available(); if (end_ == NULL) { diff --git a/src/spaces.h b/src/spaces.h index 165a226..b47452e 100644 --- a/src/spaces.h +++ b/src/spaces.h @@ -1444,9 +1444,12 @@ class FreeListCategory { FreeListCategory() : top_(NULL), end_(NULL), + mutex_(OS::CreateMutex()), available_(0) {} - ~FreeListCategory() {} + ~FreeListCategory() { + delete mutex_; + } intptr_t Concatenate(FreeListCategory* category); @@ -1473,7 +1476,7 @@ class FreeListCategory { int available() const { return available_; } void set_available(int available) { available_ = available; } - Mutex* mutex() { return &mutex_; } + Mutex* mutex() { return mutex_; } #ifdef DEBUG intptr_t SumFreeList(); @@ -1483,7 +1486,7 @@ class FreeListCategory { private: FreeListNode* top_; FreeListNode* end_; - Mutex mutex_; + Mutex* mutex_; // Total available bytes in all blocks of this free list category. int available_; diff --git a/src/v8threads.cc b/src/v8threads.cc index c1f20b1..2df187a 100644 --- a/src/v8threads.cc +++ b/src/v8threads.cc @@ -214,7 +214,7 @@ bool ThreadManager::RestoreThread() { void ThreadManager::Lock() { - mutex_.Lock(); + mutex_->Lock(); mutex_owner_ = ThreadId::Current(); ASSERT(IsLockedByCurrentThread()); } @@ -222,7 +222,7 @@ void ThreadManager::Lock() { void ThreadManager::Unlock() { mutex_owner_ = ThreadId::Invalid(); - mutex_.Unlock(); + mutex_->Unlock(); } @@ -303,7 +303,8 @@ ThreadState* ThreadState::Next() { // be distinguished from not having a thread id at all (since NULL is // defined as 0.) ThreadManager::ThreadManager() - : mutex_owner_(ThreadId::Invalid()), + : mutex_(OS::CreateMutex()), + mutex_owner_(ThreadId::Invalid()), lazily_archived_thread_(ThreadId::Invalid()), lazily_archived_thread_state_(NULL), free_anchor_(NULL), @@ -314,6 +315,7 @@ ThreadManager::ThreadManager() ThreadManager::~ThreadManager() { + delete mutex_; DeleteThreadStateList(free_anchor_); DeleteThreadStateList(in_use_anchor_); } diff --git a/src/v8threads.h b/src/v8threads.h index b8ed817..8dce860 100644 --- a/src/v8threads.h +++ b/src/v8threads.h @@ -119,7 +119,7 @@ class ThreadManager { void EagerlyArchiveThread(); - Mutex mutex_; + Mutex* mutex_; ThreadId mutex_owner_; ThreadId lazily_archived_thread_; ThreadState* lazily_archived_thread_state_; diff --git a/src/win32-headers.h b/src/win32-headers.h index bf568b3..2b5d7d7 100644 --- a/src/win32-headers.h +++ b/src/win32-headers.h @@ -94,4 +94,5 @@ #undef ANY #undef IGNORE #undef GetObject +#undef CreateMutex #undef CreateSemaphore diff --git a/test/cctest/cctest.gyp b/test/cctest/cctest.gyp index 1cdf9f4..9df5c7b 100644 --- a/test/cctest/cctest.gyp +++ b/test/cctest/cctest.gyp @@ -79,10 +79,10 @@ 'test-heap-profiler.cc', 'test-list.cc', 'test-liveedit.cc', + 'test-lock.cc', 'test-lockers.cc', 'test-log.cc', 'test-mark-compact.cc', - 'test-mutex.cc', 'test-object-observe.cc', 'test-parsing.cc', 'test-platform.cc', @@ -91,7 +91,6 @@ 'test-random.cc', 'test-regexp.cc', 'test-reloc-info.cc', - 'test-semaphore.cc', 'test-serialize.cc', 'test-sockets.cc', 'test-spaces.cc', diff --git a/test/cctest/test-debug.cc b/test/cctest/test-debug.cc index 90453f7..484eb8e 100644 --- a/test/cctest/test-debug.cc +++ b/test/cctest/test-debug.cc @@ -4714,7 +4714,7 @@ class ThreadBarrier { ThreadBarrier::ThreadBarrier(int num_threads) : num_threads_(num_threads), num_blocked_(0) { - lock_ = new v8::internal::Mutex; + lock_ = OS::CreateMutex(); sem_ = OS::CreateSemaphore(0); invalid_ = false; // A barrier may only be used once. Then it is invalid. } diff --git a/test/cctest/test-semaphore.cc b/test/cctest/test-lock.cc similarity index 74% rename from test/cctest/test-semaphore.cc rename to test/cctest/test-lock.cc index e06d52d..d4387d0 100644 --- a/test/cctest/test-semaphore.cc +++ b/test/cctest/test-lock.cc @@ -1,4 +1,4 @@ -// Copyright 2006-2013 the V8 project authors. All rights reserved. +// Copyright 2006-2008 the V8 project authors. All rights reserved. // Redistribution and use in source and binary forms, with or without // modification, are permitted provided that the following conditions are // met: @@ -25,7 +25,9 @@ // (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE // OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. // -// Tests of the Semaphore class from platform.h +// Tests of the TokenLock class from lock.h + +#include #include "v8.h" @@ -36,6 +38,33 @@ using namespace ::v8::internal; +// Simple test of locking logic +TEST(Simple) { + Mutex* mutex = OS::CreateMutex(); + CHECK_EQ(0, mutex->Lock()); // acquire the lock with the right token + CHECK_EQ(0, mutex->Unlock()); // can unlock with the right token + delete mutex; +} + + +TEST(MultiLock) { + Mutex* mutex = OS::CreateMutex(); + CHECK_EQ(0, mutex->Lock()); + CHECK_EQ(0, mutex->Unlock()); + delete mutex; +} + + +TEST(ShallowLock) { + Mutex* mutex = OS::CreateMutex(); + CHECK_EQ(0, mutex->Lock()); + CHECK_EQ(0, mutex->Unlock()); + CHECK_EQ(0, mutex->Lock()); + CHECK_EQ(0, mutex->Unlock()); + delete mutex; +} + + TEST(SemaphoreTimeout) { bool ok; Semaphore* sem = OS::CreateSemaphore(0); diff --git a/test/cctest/test-mutex.cc b/test/cctest/test-mutex.cc deleted file mode 100644 index 935bacc..0000000 --- a/test/cctest/test-mutex.cc +++ /dev/null @@ -1,70 +0,0 @@ -// Copyright 2006-2013 the V8 project authors. All rights reserved. -// Redistribution and use in source and binary forms, with or without -// modification, are permitted provided that the following conditions are -// met: -// -// * Redistributions of source code must retain the above copyright -// notice, this list of conditions and the following disclaimer. -// * Redistributions in binary form must reproduce the above -// copyright notice, this list of conditions and the following -// disclaimer in the documentation and/or other materials provided -// with the distribution. -// * Neither the name of Google Inc. nor the names of its -// contributors may be used to endorse or promote products derived -// from this software without specific prior written permission. -// -// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -// -// Tests of the Mutex class from mutex.h - -#include "v8.h" - -#include "mutex.h" -#include "cctest.h" - - -using namespace ::v8::internal; - - -TEST(Simple) { - Mutex mutex; - mutex.Lock(); - mutex.Unlock(); -} - - -TEST(Recursive) { - Mutex mutex; - mutex.Lock(); - mutex.Lock(); - mutex.Unlock(); - mutex.Unlock(); -} - - -TEST(SimpleScopedLock) { - Mutex mutex; - { - ScopedLock fst(&mutex); - } - { - ScopedLock snd(&mutex); - } -} - - -TEST(RecursiveScopedLock) { - Mutex mutex; - ScopedLock fst(&mutex); - ScopedLock snd(&mutex); -} diff --git a/test/cctest/test-platform-linux.cc b/test/cctest/test-platform-linux.cc index 5945241..6bb2902 100644 --- a/test/cctest/test-platform-linux.cc +++ b/test/cctest/test-platform-linux.cc @@ -52,18 +52,18 @@ static void LoopIncrement(Mutex* mutex, int rem) { int count = 0; int last_count = -1; do { - mutex->Lock(); + CHECK_EQ(0, mutex->Lock()); count = busy_lock_counter; - mutex->Unlock(); + CHECK_EQ(0, mutex->Unlock()); yield(); } while (count % 2 == rem && count < kLockCounterLimit); if (count >= kLockCounterLimit) break; - mutex->Lock(); + CHECK_EQ(0, mutex->Lock()); CHECK_EQ(count, busy_lock_counter); CHECK(last_count == -1 || count == last_count + 1); busy_lock_counter++; last_count = count; - mutex->Unlock(); + CHECK_EQ(0, mutex->Unlock()); yield(); } } @@ -79,14 +79,15 @@ static void* RunTestBusyLock(void* arg) { // increment a variable. TEST(BusyLock) { pthread_t other; - Mutex mutex; + Mutex* mutex = OS::CreateMutex(); int thread_created = pthread_create(&other, NULL, &RunTestBusyLock, - &mutex); + mutex); CHECK_EQ(0, thread_created); - LoopIncrement(&mutex, 1); + LoopIncrement(mutex, 1); pthread_join(other, NULL); + delete mutex; } diff --git a/test/cctest/test-platform-nullos.cc b/test/cctest/test-platform-nullos.cc index 0ad67be..3afbd90 100644 --- a/test/cctest/test-platform-nullos.cc +++ b/test/cctest/test-platform-nullos.cc @@ -52,18 +52,18 @@ static void LoopIncrement(Mutex* mutex, int rem) { int count = 0; int last_count = -1; do { - mutex->Lock(); + CHECK_EQ(0, mutex->Lock()); count = busy_lock_counter; - mutex->Unlock(); + CHECK_EQ(0, mutex->Unlock()); yield(); } while (count % 2 == rem && count < kLockCounterLimit); if (count >= kLockCounterLimit) break; - mutex->Lock(); + CHECK_EQ(0, mutex->Lock()); CHECK_EQ(count, busy_lock_counter); CHECK(last_count == -1 || count == last_count + 1); busy_lock_counter++; last_count = count; - mutex->Unlock(); + CHECK_EQ(0, mutex->Unlock()); yield(); } } diff --git a/tools/gyp/v8.gyp b/tools/gyp/v8.gyp index 8a7e06d..bdbc716 100644 --- a/tools/gyp/v8.gyp +++ b/tools/gyp/v8.gyp @@ -419,8 +419,6 @@ '../../src/marking-thread.cc', '../../src/messages.cc', '../../src/messages.h', - '../../src/mutex.cc', - '../../src/mutex.h', '../../src/natives.h', '../../src/objects-debug.cc', '../../src/objects-inl.h', -- 2.7.4