WaitForClient moved to server, now working.
This commit is contained in:
parent
8a7bd7b69a
commit
d98d5c855a
|
@ -30,8 +30,10 @@ DebugServer::DebugServer(Emulator* emulator) :
|
|||
emulator_(emulator), lock_(0) {
|
||||
lock_ = xe_mutex_alloc(10000);
|
||||
|
||||
//protocols_.push_back(
|
||||
// new protocols::gdb::GDBProtocol(this));
|
||||
client_event_ = CreateEvent(NULL, FALSE, FALSE, NULL);
|
||||
|
||||
protocols_.push_back(
|
||||
new protocols::gdb::GDBProtocol(this));
|
||||
protocols_.push_back(
|
||||
new protocols::ws::WSProtocol(this));
|
||||
}
|
||||
|
@ -39,10 +41,19 @@ DebugServer::DebugServer(Emulator* emulator) :
|
|||
DebugServer::~DebugServer() {
|
||||
Shutdown();
|
||||
|
||||
CloseHandle(client_event_);
|
||||
|
||||
xe_free(lock_);
|
||||
lock_ = 0;
|
||||
}
|
||||
|
||||
bool DebugServer::has_clients() {
|
||||
xe_mutex_lock(lock_);
|
||||
bool has_clients = clients_.size() > 0;
|
||||
xe_mutex_unlock(lock_);
|
||||
return has_clients;
|
||||
}
|
||||
|
||||
int DebugServer::Startup() {
|
||||
return 0;
|
||||
}
|
||||
|
@ -66,7 +77,7 @@ int DebugServer::BeforeEntry() {
|
|||
// If desired, wait until the first client connects.
|
||||
//if (FLAGS_wait_for_debugger) {
|
||||
XELOGI("Waiting for debugger...");
|
||||
if (protocols_[0]->WaitForClient()) {
|
||||
if (WaitForClient()) {
|
||||
return 1;
|
||||
}
|
||||
XELOGI("Debugger attached, continuing...");
|
||||
|
@ -95,6 +106,13 @@ void DebugServer::Shutdown() {
|
|||
xe_mutex_unlock(lock_);
|
||||
}
|
||||
|
||||
int DebugServer::WaitForClient() {
|
||||
while (!has_clients()) {
|
||||
WaitForSingleObject(client_event_, INFINITE);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
|
||||
void DebugServer::AddClient(DebugClient* debug_client) {
|
||||
xe_mutex_lock(lock_);
|
||||
|
||||
|
@ -108,6 +126,8 @@ void DebugServer::AddClient(DebugClient* debug_client) {
|
|||
clients_.push_back(debug_client);
|
||||
|
||||
xe_mutex_unlock(lock_);
|
||||
|
||||
SetEvent(client_event_);
|
||||
}
|
||||
|
||||
void DebugServer::RemoveClient(DebugClient* debug_client) {
|
||||
|
|
|
@ -32,10 +32,14 @@ public:
|
|||
|
||||
Emulator* emulator() const { return emulator_; }
|
||||
|
||||
bool has_clients();
|
||||
|
||||
int Startup();
|
||||
int BeforeEntry();
|
||||
void Shutdown();
|
||||
|
||||
int WaitForClient();
|
||||
|
||||
private:
|
||||
void AddClient(DebugClient* debug_client);
|
||||
void RemoveClient(DebugClient* debug_client);
|
||||
|
@ -48,6 +52,7 @@ private:
|
|||
|
||||
xe_mutex_t* lock_;
|
||||
std::vector<DebugClient*> clients_;
|
||||
HANDLE client_event_;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -27,7 +27,6 @@ public:
|
|||
virtual ~Protocol();
|
||||
|
||||
virtual int Setup() = 0;
|
||||
virtual int WaitForClient() = 0;
|
||||
|
||||
protected:
|
||||
DebugServer* debug_server_;
|
||||
|
|
|
@ -24,11 +24,18 @@ using namespace xe::debug::protocols::gdb;
|
|||
|
||||
|
||||
GDBProtocol::GDBProtocol(DebugServer* debug_server) :
|
||||
port_(0), socket_id_(0), thread_(0), running_(false),
|
||||
Protocol(debug_server) {
|
||||
port_ = FLAGS_gdb_debug_port;
|
||||
}
|
||||
|
||||
GDBProtocol::~GDBProtocol() {
|
||||
if (thread_) {
|
||||
// Join thread.
|
||||
running_ = false;
|
||||
xe_thread_release(thread_);
|
||||
thread_ = 0;
|
||||
}
|
||||
if (socket_id_) {
|
||||
xe_socket_close(socket_id_);
|
||||
}
|
||||
|
@ -60,29 +67,39 @@ int GDBProtocol::Setup() {
|
|||
return 1;
|
||||
}
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
int GDBProtocol::WaitForClient() {
|
||||
if (!socket_id_) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
// Accept the first connection we get.
|
||||
xe_socket_connection_t client_info;
|
||||
if (xe_socket_accept(socket_id_, &client_info)) {
|
||||
return 1;
|
||||
}
|
||||
|
||||
XELOGI("GDB debugger connected from %s", client_info.addr);
|
||||
|
||||
// Create the client object.
|
||||
// Note that the client will delete itself when done.
|
||||
GDBClient* client = new GDBClient(debug_server_, client_info.socket);
|
||||
if (client->Setup()) {
|
||||
// Client failed to setup - abort.
|
||||
return 1;
|
||||
}
|
||||
thread_ = xe_thread_create("GDB Debugger Listener", StartCallback, this);
|
||||
running_ = true;
|
||||
return xe_thread_start(thread_);
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
void GDBProtocol::StartCallback(void* param) {
|
||||
GDBProtocol* protocol = reinterpret_cast<GDBProtocol*>(param);
|
||||
protocol->AcceptThread();
|
||||
}
|
||||
|
||||
void GDBProtocol::AcceptThread() {
|
||||
while (running_) {
|
||||
if (!socket_id_) {
|
||||
break;
|
||||
}
|
||||
|
||||
// Accept the first connection we get.
|
||||
xe_socket_connection_t client_info;
|
||||
if (xe_socket_accept(socket_id_, &client_info)) {
|
||||
XELOGE("WS debugger failed to accept connection");
|
||||
break;
|
||||
}
|
||||
|
||||
XELOGI("WS debugger connected from %s", client_info.addr);
|
||||
|
||||
// Create the client object.
|
||||
// Note that the client will delete itself when done.
|
||||
GDBClient* client = new GDBClient(debug_server_, client_info.socket);
|
||||
if (client->Setup()) {
|
||||
// Client failed to setup - abort.
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -31,12 +31,18 @@ public:
|
|||
virtual ~GDBProtocol();
|
||||
|
||||
virtual int Setup();
|
||||
virtual int WaitForClient();
|
||||
|
||||
private:
|
||||
static void StartCallback(void* param);
|
||||
void AcceptThread();
|
||||
|
||||
protected:
|
||||
uint32_t port_;
|
||||
|
||||
socket_t socket_id_;
|
||||
|
||||
xe_thread_ref thread_;
|
||||
bool running_;
|
||||
};
|
||||
|
||||
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
|
||||
#include <xenia/debug/protocols/ws/ws_protocol.h>
|
||||
|
||||
#include <xenia/debug/debug_server.h>
|
||||
#include <xenia/debug/protocols/ws/ws_client.h>
|
||||
|
||||
#include <gflags/gflags.h>
|
||||
|
@ -25,7 +26,6 @@ DEFINE_int32(ws_debug_port, 6200,
|
|||
|
||||
WSProtocol::WSProtocol(DebugServer* debug_server) :
|
||||
port_(0), socket_id_(0), thread_(0), running_(false),
|
||||
accepted_event_(INVALID_HANDLE_VALUE),
|
||||
Protocol(debug_server) {
|
||||
port_ = FLAGS_ws_debug_port;
|
||||
}
|
||||
|
@ -37,9 +37,6 @@ WSProtocol::~WSProtocol() {
|
|||
xe_thread_release(thread_);
|
||||
thread_ = 0;
|
||||
}
|
||||
if (accepted_event_ != INVALID_HANDLE_VALUE) {
|
||||
CloseHandle(accepted_event_);
|
||||
}
|
||||
if (socket_id_) {
|
||||
xe_socket_close(socket_id_);
|
||||
}
|
||||
|
@ -71,8 +68,6 @@ int WSProtocol::Setup() {
|
|||
return 1;
|
||||
}
|
||||
|
||||
accepted_event_ = CreateEvent(NULL, FALSE, FALSE, NULL);
|
||||
|
||||
thread_ = xe_thread_create("WS Debugger Listener", StartCallback, this);
|
||||
running_ = true;
|
||||
return xe_thread_start(thread_);
|
||||
|
@ -105,12 +100,5 @@ void WSProtocol::AcceptThread() {
|
|||
// Client failed to setup - abort.
|
||||
continue;
|
||||
}
|
||||
|
||||
SetEvent(accepted_event_);
|
||||
}
|
||||
}
|
||||
|
||||
int WSProtocol::WaitForClient() {
|
||||
WaitForSingleObject(accepted_event_, INFINITE);
|
||||
return 0;
|
||||
}
|
||||
|
|
|
@ -31,7 +31,6 @@ public:
|
|||
virtual ~WSProtocol();
|
||||
|
||||
virtual int Setup();
|
||||
virtual int WaitForClient();
|
||||
|
||||
private:
|
||||
static void StartCallback(void* param);
|
||||
|
@ -44,7 +43,6 @@ protected:
|
|||
|
||||
xe_thread_ref thread_;
|
||||
bool running_;
|
||||
HANDLE accepted_event_;
|
||||
};
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue