Index: src/debug.cc |
=================================================================== |
--- src/debug.cc (revision 1787) |
+++ src/debug.cc (working copy) |
@@ -1420,16 +1420,13 @@ |
bool Debugger::compiling_natives_ = false; |
bool Debugger::is_loading_debugger_ = false; |
bool Debugger::never_unload_debugger_ = false; |
-DebugMessageThread* Debugger::message_thread_ = NULL; |
v8::Debug::MessageHandler Debugger::message_handler_ = NULL; |
bool Debugger::message_handler_cleared_ = false; |
v8::Debug::HostDispatchHandler Debugger::host_dispatch_handler_ = NULL; |
int Debugger::host_dispatch_micros_ = 100 * 1000; |
DebuggerAgent* Debugger::agent_ = NULL; |
-LockingMessageQueue Debugger::command_queue_(kQueueInitialSize); |
-LockingMessageQueue Debugger::message_queue_(kQueueInitialSize); |
+LockingCommandMessageQueue Debugger::command_queue_(kQueueInitialSize); |
Semaphore* Debugger::command_received_ = OS::CreateSemaphore(0); |
-Semaphore* Debugger::message_received_ = OS::CreateSemaphore(0); |
Handle<Object> Debugger::MakeJSObject(Vector<const char> constructor_name, |
@@ -1818,7 +1815,7 @@ |
// Notify the debugger that a debug event has occurred unless auto continue is |
// active in which case no event is send. |
if (!auto_continue) { |
- bool success = SendEventMessage(event_data); |
+ bool success = InvokeMessageHandlerWithEvent(event_data); |
if (!success) { |
// If failed to notify debugger just continue running. |
return; |
@@ -1845,7 +1842,7 @@ |
StackGuard::Continue(DEBUGCOMMAND); |
// Get the command from the queue. |
- Message command = command_queue_.Get(); |
+ CommandMessage command = command_queue_.Get(); |
Logger::DebugTag("Got request from command queue, in interactive loop."); |
if (!Debugger::IsDebuggerActive()) { |
// Delete command text and user data. |
@@ -1900,7 +1897,7 @@ |
} |
// Return the result. |
- SendMessage(Message::NewOutput(response, command.client_data())); |
+ InvokeMessageHandler(response, command.client_data()); |
// Return from debug event processing if either the VM is put into the |
// runnning state (through a continue command) or auto continue is active |
@@ -1946,17 +1943,11 @@ |
} |
-void Debugger::SetMessageHandler(v8::Debug::MessageHandler handler, |
- bool message_handler_thread) { |
+void Debugger::SetMessageHandler(v8::Debug::MessageHandler handler) { |
ScopedLock with(debugger_access_); |
message_handler_ = handler; |
- if (handler != NULL) { |
- if (!message_thread_ && message_handler_thread) { |
- message_thread_ = new DebugMessageThread(); |
- message_thread_->Start(); |
- } |
- } else { |
+ if (handler == NULL) { |
// Indicate that the message handler was recently cleared. |
message_handler_cleared_ = true; |
@@ -1980,34 +1971,25 @@ |
// public API. Messages are kept internally as Vector<uint16_t> strings, which |
// are allocated in various places and deallocated by the calling function |
// sometime after this call. |
-void Debugger::InvokeMessageHandler(Message message) { |
+void Debugger::InvokeMessageHandler(v8::Handle<v8::String> output, |
+ v8::Debug::ClientData* data) { |
ScopedLock with(debugger_access_); |
if (message_handler_ != NULL) { |
- message_handler_(message.text().start(), |
- message.text().length(), |
- message.client_data()); |
- } |
- message.Dispose(); |
-} |
+ Vector<uint16_t> text = Vector<uint16_t>::New(output->Length()); |
+ output->Write(text.start(), 0, output->Length()); |
+ message_handler_(text.start(), |
+ text.length(), |
+ data); |
-void Debugger::SendMessage(Message message) { |
- if (message_thread_ == NULL) { |
- // If there is no message thread just invoke the message handler from the |
- // V8 thread. |
- InvokeMessageHandler(message); |
- } else { |
- // Put the message coming from V8 on the queue. The text and user data will |
- // be destroyed by the message thread. |
- Logger::DebugTag("Put message on event message_queue."); |
- message_queue_.Put(message); |
- message_received_->Signal(); |
+ text.Dispose(); |
} |
+ delete data; |
} |
-bool Debugger::SendEventMessage(Handle<Object> event_data) { |
+bool Debugger::InvokeMessageHandlerWithEvent(Handle<Object> event_data) { |
v8::HandleScope scope; |
// Call toJSONProtocol on the debug event object. |
v8::Local<v8::Object> api_event_data = |
@@ -2024,11 +2006,10 @@ |
if (FLAG_trace_debug_json) { |
PrintLn(json_event_string); |
} |
- SendMessage(Message::NewOutput( |
- json_event_string, |
- NULL /* no user data since there was no request */)); |
+ InvokeMessageHandler(json_event_string, |
+ NULL /* no user data since there was no request */); |
} else { |
- SendMessage(Message::NewEmptyMessage()); |
+ InvokeMessageHandler(v8::String::Empty(), NULL); |
} |
} else { |
PrintLn(try_catch.Exception()); |
@@ -2041,13 +2022,11 @@ |
// Puts a command coming from the public API on the queue. Creates |
// a copy of the command string managed by the debugger. Up to this |
// point, the command data was managed by the API client. Called |
-// by the API client thread. This is where the API client hands off |
-// processing of the command to the DebugMessageThread thread. |
-// The new copy of the command is destroyed in HandleCommand(). |
+// by the API client thread. |
void Debugger::ProcessCommand(Vector<const uint16_t> command, |
v8::Debug::ClientData* client_data) { |
// Need to cast away const. |
- Message message = Message::NewCommand( |
+ CommandMessage message = CommandMessage::New( |
Vector<uint16_t>(const_cast<uint16_t*>(command.start()), |
command.length()), |
client_data); |
@@ -2122,99 +2101,51 @@ |
} |
-void Debugger::TearDown() { |
- if (message_thread_ != NULL) { |
- message_thread_->Stop(); |
- delete message_thread_; |
- message_thread_ = NULL; |
- } |
+CommandMessage::CommandMessage() : text_(Vector<uint16_t>::empty()), |
+ client_data_(NULL) { |
} |
-void DebugMessageThread::Run() { |
- // Sends debug events to an installed debugger message callback. |
- while (keep_running_) { |
- // Wait and Get are paired so that semaphore count equals queue length. |
- Debugger::message_received_->Wait(); |
- Logger::DebugTag("Get message from event message_queue."); |
- Message message = Debugger::message_queue_.Get(); |
- if (message.text().length() > 0) { |
- Debugger::InvokeMessageHandler(message); |
- } else { |
- message.Dispose(); |
- } |
- } |
-} |
- |
- |
-void DebugMessageThread::Stop() { |
- keep_running_ = false; |
- Debugger::SendMessage(Message::NewEmptyMessage()); |
- Join(); |
-} |
- |
- |
-Message::Message() : text_(Vector<uint16_t>::empty()), |
- client_data_(NULL) { |
-} |
- |
- |
-Message::Message(const Vector<uint16_t>& text, |
- v8::Debug::ClientData* data) |
+CommandMessage::CommandMessage(const Vector<uint16_t>& text, |
+ v8::Debug::ClientData* data) |
: text_(text), |
client_data_(data) { |
} |
-Message::~Message() { |
+CommandMessage::~CommandMessage() { |
} |
-void Message::Dispose() { |
+void CommandMessage::Dispose() { |
text_.Dispose(); |
delete client_data_; |
client_data_ = NULL; |
} |
-Message Message::NewCommand(const Vector<uint16_t>& command, |
- v8::Debug::ClientData* data) { |
- return Message(command.Clone(), data); |
+CommandMessage CommandMessage::New(const Vector<uint16_t>& command, |
+ v8::Debug::ClientData* data) { |
+ return CommandMessage(command.Clone(), data); |
} |
-Message Message::NewOutput(v8::Handle<v8::String> output, |
- v8::Debug::ClientData* data) { |
- Vector<uint16_t> text; |
- if (!output.IsEmpty()) { |
- // Do not include trailing '\0'. |
- text = Vector<uint16_t>::New(output->Length()); |
- output->Write(text.start(), 0, output->Length()); |
- } |
- return Message(text, data); |
+CommandMessageQueue::CommandMessageQueue(int size) : start_(0), end_(0), |
+ size_(size) { |
+ messages_ = NewArray<CommandMessage>(size); |
} |
-Message Message::NewEmptyMessage() { |
- return Message(); |
-} |
- |
- |
-MessageQueue::MessageQueue(int size) : start_(0), end_(0), size_(size) { |
- messages_ = NewArray<Message>(size); |
-} |
- |
- |
-MessageQueue::~MessageQueue() { |
+CommandMessageQueue::~CommandMessageQueue() { |
while (!IsEmpty()) { |
- Message m = Get(); |
+ CommandMessage m = Get(); |
m.Dispose(); |
} |
DeleteArray(messages_); |
} |
-Message MessageQueue::Get() { |
+CommandMessage CommandMessageQueue::Get() { |
ASSERT(!IsEmpty()); |
int result = start_; |
start_ = (start_ + 1) % size_; |
@@ -2222,7 +2153,7 @@ |
} |
-void MessageQueue::Put(const Message& message) { |
+void CommandMessageQueue::Put(const CommandMessage& message) { |
if ((end_ + 1) % size_ == start_) { |
Expand(); |
} |
@@ -2231,12 +2162,12 @@ |
} |
-void MessageQueue::Expand() { |
- MessageQueue new_queue(size_ * 2); |
+void CommandMessageQueue::Expand() { |
+ CommandMessageQueue new_queue(size_ * 2); |
while (!IsEmpty()) { |
new_queue.Put(Get()); |
} |
- Message* array_to_free = messages_; |
+ CommandMessage* array_to_free = messages_; |
*this = new_queue; |
new_queue.messages_ = array_to_free; |
// Make the new_queue empty so that it doesn't call Dispose on any messages. |
@@ -2245,38 +2176,39 @@ |
} |
-LockingMessageQueue::LockingMessageQueue(int size) : queue_(size) { |
+LockingCommandMessageQueue::LockingCommandMessageQueue(int size) |
+ : queue_(size) { |
lock_ = OS::CreateMutex(); |
} |
-LockingMessageQueue::~LockingMessageQueue() { |
+LockingCommandMessageQueue::~LockingCommandMessageQueue() { |
delete lock_; |
} |
-bool LockingMessageQueue::IsEmpty() const { |
+bool LockingCommandMessageQueue::IsEmpty() const { |
ScopedLock sl(lock_); |
return queue_.IsEmpty(); |
} |
-Message LockingMessageQueue::Get() { |
+CommandMessage LockingCommandMessageQueue::Get() { |
ScopedLock sl(lock_); |
- Message result = queue_.Get(); |
+ CommandMessage result = queue_.Get(); |
Logger::DebugEvent("Get", result.text()); |
return result; |
} |
-void LockingMessageQueue::Put(const Message& message) { |
+void LockingCommandMessageQueue::Put(const CommandMessage& message) { |
ScopedLock sl(lock_); |
queue_.Put(message); |
Logger::DebugEvent("Put", message.text()); |
} |
-void LockingMessageQueue::Clear() { |
+void LockingCommandMessageQueue::Clear() { |
ScopedLock sl(lock_); |
queue_.Clear(); |
} |