From aed5c39d973e77f8ce069ba4b13a38ac9ff5f5b9 Mon Sep 17 00:00:00 2001 From: Rene Gollent Date: Wed, 20 Apr 2016 20:43:15 -0400 Subject: [PATCH] Debugger: Implement host interface roster listener. TargetHostInterfaceRoster: - Add Listener interface. For now, this simply notifies the listener of changes to the active debugger count. - Adjust show new team window command to automatically fall back to the local interface window if one isn't specified. Fixes the Start New Team menu item in the TeamWindow. The latter will later be expanded to show the available interfaces to start a new team on in a submenu. Debugger: - Implement roster listener interface in order to know when to attempt application quit. With this commit, all necessary work to isolate the application from the target host is complete, and work on the actual remote interface and protocol can begin. --- src/apps/debugger/Debugger.cpp | 37 ++++++++++++++----- .../TargetHostInterfaceRoster.cpp | 26 +++++++++++-- .../TargetHostInterfaceRoster.h | 14 ++++++- 3 files changed, 62 insertions(+), 15 deletions(-) diff --git a/src/apps/debugger/Debugger.cpp b/src/apps/debugger/Debugger.cpp index a23de964a6..e09c479c58 100644 --- a/src/apps/debugger/Debugger.cpp +++ b/src/apps/debugger/Debugger.cpp @@ -208,7 +208,7 @@ parse_arguments(int argc, const char* const* argv, bool noOutput, } static status_t -global_init() +global_init(TargetHostInterfaceRoster::Listener* listener) { status_t error = TypeHandlerRoster::CreateDefault(); if (error != B_OK) @@ -222,7 +222,7 @@ global_init() if (error != B_OK) return error; - error = TargetHostInterfaceRoster::CreateDefault(); + error = TargetHostInterfaceRoster::CreateDefault(listener); if (error != B_OK) return error; @@ -242,7 +242,8 @@ global_init() // #pragma mark - Debugger application class -class Debugger : public BApplication { +class Debugger : public BApplication, + private TargetHostInterfaceRoster::Listener { public: Debugger(); ~Debugger(); @@ -256,6 +257,9 @@ private: virtual bool QuitRequested(); virtual void Quit(); + // TargetHostInterfaceRoster::Listener + virtual void TeamDebuggerCountChanged(int32 count); + private: status_t _StartNewTeam(TargetHostInterface* interface, const char* teamPath, const char* args); @@ -270,7 +274,7 @@ private: // #pragma mark - CliDebugger -class CliDebugger { +class CliDebugger : private TargetHostInterfaceRoster::Listener { public: CliDebugger(); ~CliDebugger(); @@ -279,7 +283,7 @@ public: }; -class ReportDebugger { +class ReportDebugger : private TargetHostInterfaceRoster::Listener { public: ReportDebugger(); ~ReportDebugger(); @@ -293,6 +297,7 @@ public: Debugger::Debugger() : BApplication(kDebuggerSignature), + TargetHostInterfaceRoster::Listener(), fTeamsWindow(NULL), fStartTeamWindow(NULL) { @@ -311,7 +316,7 @@ Debugger::~Debugger() status_t Debugger::Init() { - status_t error = global_init(); + status_t error = global_init(this); if (error != B_OK) return error; @@ -351,8 +356,12 @@ Debugger::MessageReceived(BMessage* message) TargetHostInterface* hostInterface; if (message->FindPointer("interface", reinterpret_cast(&hostInterface)) != B_OK) { - break; + // if an interface isn't explicitly supplied, fall back to + // the default local interface. + hostInterface = TargetHostInterfaceRoster::Default() + ->ActiveInterfaceAt(0); } + BMessenger messenger(fStartTeamWindow); if (!messenger.IsValid()) { fStartTeamWindow = StartTeamWindow::Create(hostInterface); @@ -473,6 +482,16 @@ Debugger::Quit() } +void +Debugger::TeamDebuggerCountChanged(int32 count) +{ + if (count == 0) { + AutoLocker lock(this); + Quit(); + } +} + + status_t Debugger::_StartNewTeam(TargetHostInterface* interface, const char* path, const char* args) @@ -529,7 +548,7 @@ CliDebugger::Run(const Options& options) SignalSet(SIGINT).BlockInCurrentThread(); // initialize global objects and settings manager - status_t error = global_init(); + status_t error = global_init(this); if (error != B_OK) { fprintf(stderr, "Error: Global initialization failed: %s\n", strerror(error)); @@ -596,7 +615,7 @@ bool ReportDebugger::Run(const Options& options) { // initialize global objects and settings manager - status_t error = global_init(); + status_t error = global_init(this); if (error != B_OK) { fprintf(stderr, "Error: Global initialization failed: %s\n", strerror(error)); diff --git a/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.cpp b/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.cpp index bc520ae8e9..460e3b448d 100644 --- a/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.cpp +++ b/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.cpp @@ -23,7 +23,8 @@ TargetHostInterfaceRoster::TargetHostInterfaceRoster() fLock(), fRunningTeamDebuggers(0), fInterfaceInfos(20, false), - fActiveInterfaces(20, false) + fActiveInterfaces(20, false), + fListener(NULL) { } @@ -41,7 +42,7 @@ TargetHostInterfaceRoster::Default() /*static*/ status_t -TargetHostInterfaceRoster::CreateDefault() +TargetHostInterfaceRoster::CreateDefault(Listener* listener) { if (sDefaultInstance != NULL) return B_OK; @@ -52,7 +53,7 @@ TargetHostInterfaceRoster::CreateDefault() return B_NO_MEMORY; ObjectDeleter rosterDeleter(roster); - status_t error = roster->Init(); + status_t error = roster->Init(listener); if (error != B_OK) return error; @@ -75,8 +76,9 @@ TargetHostInterfaceRoster::DeleteDefault() status_t -TargetHostInterfaceRoster::Init() +TargetHostInterfaceRoster::Init(Listener* listener) { + fListener = listener; return fLock.InitCheck(); } @@ -161,6 +163,7 @@ void TargetHostInterfaceRoster::TeamDebuggerStarted(TeamDebugger* debugger) { fRunningTeamDebuggers++; + fListener->TeamDebuggerCountChanged(fRunningTeamDebuggers); } @@ -168,6 +171,7 @@ void TargetHostInterfaceRoster::TeamDebuggerQuit(TeamDebugger* debugger) { fRunningTeamDebuggers--; + fListener->TeamDebuggerCountChanged(fRunningTeamDebuggers); } @@ -178,3 +182,17 @@ TargetHostInterfaceRoster::TargetHostInterfaceQuit( AutoLocker locker(this); fActiveInterfaces.RemoveItem(interface); } + + +// #pragma mark - TargetHostInterfaceRoster::Listener + + +TargetHostInterfaceRoster::Listener::~Listener() +{ +} + + +void +TargetHostInterfaceRoster::Listener::TeamDebuggerCountChanged(int32 count) +{ +} diff --git a/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.h b/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.h index 9016aa457c..9a416156cc 100644 --- a/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.h +++ b/src/apps/debugger/target_host_interface/TargetHostInterfaceRoster.h @@ -19,17 +19,18 @@ class TargetHostInterfaceInfo; class TargetHostInterfaceRoster : private TargetHostInterface::Listener { public: + class Listener; TargetHostInterfaceRoster(); virtual ~TargetHostInterfaceRoster(); static TargetHostInterfaceRoster* Default(); - static status_t CreateDefault(); + static status_t CreateDefault(Listener* listener); static void DeleteDefault(); bool Lock() { return fLock.Lock(); } void Unlock() { fLock.Unlock(); } - status_t Init(); + status_t Init(Listener* listener); status_t RegisterInterfaceInfos(); int32 CountInterfaceInfos() const; @@ -63,6 +64,15 @@ private: int32 fRunningTeamDebuggers; InfoList fInterfaceInfos; InterfaceList fActiveInterfaces; + Listener* fListener; +}; + + +class TargetHostInterfaceRoster::Listener { +public: + virtual ~Listener(); + + virtual void TeamDebuggerCountChanged(int32 newCount); };