Skip to content
This repository has been archived by the owner on Apr 22, 2023. It is now read-only.

Commit

Permalink
v8: fix semaphore on MacOS
Browse files Browse the repository at this point in the history
  • Loading branch information
indutny authored and piscisaureus committed Sep 6, 2012
1 parent c5e554d commit 052e63f
Show file tree
Hide file tree
Showing 2 changed files with 86 additions and 6 deletions.
22 changes: 16 additions & 6 deletions deps/v8/src/platform-macos.cc
Expand Up @@ -682,17 +682,27 @@ Mutex* OS::CreateMutex() {
class MacOSSemaphore : public Semaphore {
public:
explicit MacOSSemaphore(int count) {
semaphore_create(mach_task_self(), &semaphore_, SYNC_POLICY_FIFO, count);
int r;
r = semaphore_create(mach_task_self(),
&semaphore_,
SYNC_POLICY_FIFO,
count);
ASSERT(r == KERN_SUCCESS);
}

~MacOSSemaphore() {
semaphore_destroy(mach_task_self(), semaphore_);
int r;
r = semaphore_destroy(mach_task_self(), semaphore_);
ASSERT(r == KERN_SUCCESS);
}

// The MacOS mach semaphore documentation claims it does not have spurious
// wakeups, the way pthreads semaphores do. So the code from the linux
// platform is not needed here.
void Wait() { semaphore_wait(semaphore_); }
void Wait() {
int r;
do {
r = semaphore_wait(semaphore_);
ASSERT(r == KERN_SUCCESS || r == KERN_ABORTED);
} while (r == KERN_ABORTED);
}

bool Wait(int timeout);

Expand Down
70 changes: 70 additions & 0 deletions deps/v8/test/cctest/test-api.cc
Expand Up @@ -27,6 +27,11 @@

#include <limits.h>

#ifndef WIN32
#include <signal.h> // kill
#include <unistd.h> // getpid
#endif // WIN32

#include "v8.h"

#include "api.h"
Expand Down Expand Up @@ -17017,3 +17022,68 @@ THREADED_TEST(Regress142088) {
CHECK(context->Global()->Get(v8_str("y_from_obj"))->IsUndefined());
CHECK(context->Global()->Get(v8_str("y_from_subobj"))->IsUndefined());
}


#ifndef WIN32
class ThreadInterruptTest {
public:
ThreadInterruptTest() : sem_(NULL), sem_value_(0) { }
~ThreadInterruptTest() { delete sem_; }

void RunTest() {
sem_ = i::OS::CreateSemaphore(0);

InterruptThread i_thread(this);
i_thread.Start();

sem_->Wait();
CHECK_EQ(kExpectedValue, sem_value_);
}

private:
static const int kExpectedValue = 1;

class InterruptThread : public i::Thread {
public:
explicit InterruptThread(ThreadInterruptTest* test)
: Thread("InterruptThread"), test_(test) {}

virtual void Run() {
struct sigaction action;

// Ensure that we'll enter waiting condition
i::OS::Sleep(100);

// Setup signal handler
memset(&action, 0, sizeof(action));
action.sa_handler = SignalHandler;
sigaction(SIGCHLD, &action, NULL);

// Send signal
kill(getpid(), SIGCHLD);

// Ensure that if wait has returned because of error
i::OS::Sleep(100);

// Set value and signal semaphore
test_->sem_value_ = 1;
test_->sem_->Signal();
}

static void SignalHandler(int signal) {
}

private:
ThreadInterruptTest* test_;
struct sigaction sa_;
};

i::Semaphore* sem_;
volatile int sem_value_;
};


THREADED_TEST(SemaphoreInterruption) {
ThreadInterruptTest().RunTest();
}
#endif // WIN32

0 comments on commit 052e63f

Please sign in to comment.