Moving debugger.

This commit is contained in:
Ben Vanik 2015-05-04 20:57:46 -07:00
parent b07d5b8ed3
commit 499bed21c0
18 changed files with 200 additions and 67 deletions

View File

@ -30,9 +30,11 @@ void X64Function::Setup(void* machine_code, size_t code_size) {
code_size_ = code_size; code_size_ = code_size;
} }
int X64Function::AddBreakpointImpl(Breakpoint* breakpoint) { return 0; } int X64Function::AddBreakpointImpl(debug::Breakpoint* breakpoint) { return 0; }
int X64Function::RemoveBreakpointImpl(Breakpoint* breakpoint) { return 0; } int X64Function::RemoveBreakpointImpl(debug::Breakpoint* breakpoint) {
return 0;
}
int X64Function::CallImpl(ThreadState* thread_state, uint32_t return_address) { int X64Function::CallImpl(ThreadState* thread_state, uint32_t return_address) {
auto backend = auto backend =

View File

@ -30,8 +30,8 @@ class X64Function : public Function {
void Setup(void* machine_code, size_t code_size); void Setup(void* machine_code, size_t code_size);
protected: protected:
virtual int AddBreakpointImpl(Breakpoint* breakpoint); virtual int AddBreakpointImpl(debug::Breakpoint* breakpoint);
virtual int RemoveBreakpointImpl(Breakpoint* breakpoint); virtual int RemoveBreakpointImpl(debug::Breakpoint* breakpoint);
virtual int CallImpl(ThreadState* thread_state, uint32_t return_address); virtual int CallImpl(ThreadState* thread_state, uint32_t return_address);
private: private:

View File

@ -19,8 +19,6 @@ namespace xe {
namespace cpu { namespace cpu {
namespace frontend { namespace frontend {
using xe::cpu::Runtime;
void InitializeIfNeeded(); void InitializeIfNeeded();
void CleanupOnShutdown(); void CleanupOnShutdown();

View File

@ -10,13 +10,14 @@
#include "xenia/cpu/function.h" #include "xenia/cpu/function.h"
#include "xenia/base/logging.h" #include "xenia/base/logging.h"
#include "xenia/cpu/debugger.h"
#include "xenia/cpu/symbol_info.h" #include "xenia/cpu/symbol_info.h"
#include "xenia/cpu/thread_state.h" #include "xenia/cpu/thread_state.h"
namespace xe { namespace xe {
namespace cpu { namespace cpu {
using xe::debug::Breakpoint;
Function::Function(FunctionInfo* symbol_info) Function::Function(FunctionInfo* symbol_info)
: address_(symbol_info->address()), symbol_info_(symbol_info) {} : address_(symbol_info->address()), symbol_info_(symbol_info) {}

View File

@ -16,11 +16,11 @@
#include "xenia/cpu/debug_info.h" #include "xenia/cpu/debug_info.h"
#include "xenia/cpu/thread_state.h" #include "xenia/cpu/thread_state.h"
#include "xenia/debug/breakpoint.h"
namespace xe { namespace xe {
namespace cpu { namespace cpu {
class Breakpoint;
class FunctionInfo; class FunctionInfo;
class Function { class Function {
@ -36,15 +36,15 @@ class Function {
debug_info_ = std::move(debug_info); debug_info_ = std::move(debug_info);
} }
int AddBreakpoint(Breakpoint* breakpoint); int AddBreakpoint(debug::Breakpoint* breakpoint);
int RemoveBreakpoint(Breakpoint* breakpoint); int RemoveBreakpoint(debug::Breakpoint* breakpoint);
int Call(ThreadState* thread_state, uint32_t return_address); int Call(ThreadState* thread_state, uint32_t return_address);
protected: protected:
Breakpoint* FindBreakpoint(uint32_t address); debug::Breakpoint* FindBreakpoint(uint32_t address);
virtual int AddBreakpointImpl(Breakpoint* breakpoint) { return 0; } virtual int AddBreakpointImpl(debug::Breakpoint* breakpoint) { return 0; }
virtual int RemoveBreakpointImpl(Breakpoint* breakpoint) { return 0; } virtual int RemoveBreakpointImpl(debug::Breakpoint* breakpoint) { return 0; }
virtual int CallImpl(ThreadState* thread_state, uint32_t return_address) = 0; virtual int CallImpl(ThreadState* thread_state, uint32_t return_address) = 0;
protected: protected:
@ -54,7 +54,7 @@ class Function {
// TODO(benvanik): move elsewhere? DebugData? // TODO(benvanik): move elsewhere? DebugData?
std::mutex lock_; std::mutex lock_;
std::vector<Breakpoint*> breakpoints_; std::vector<debug::Breakpoint*> breakpoints_;
}; };
} // namespace cpu } // namespace cpu

View File

@ -22,6 +22,7 @@
#include "xenia/cpu/module.h" #include "xenia/cpu/module.h"
#include "xenia/cpu/thread_state.h" #include "xenia/cpu/thread_state.h"
#include "xenia/cpu/xex_module.h" #include "xenia/cpu/xex_module.h"
#include "xenia/debug/debugger.h"
#include "xenia/profiling.h" #include "xenia/profiling.h"
// TODO(benvanik): based on compiler support // TODO(benvanik): based on compiler support
@ -108,7 +109,7 @@ int Processor::Setup() {
assert_not_null(memory_); assert_not_null(memory_);
// Create debugger first. Other types hook up to it. // Create debugger first. Other types hook up to it.
debugger_.reset(new Debugger(this)); debugger_.reset(new xe::debug::Debugger(this));
std::unique_ptr<Module> builtin_module(new BuiltinModule(this)); std::unique_ptr<Module> builtin_module(new BuiltinModule(this));
builtin_module_ = builtin_module.get(); builtin_module_ = builtin_module.get();

View File

@ -14,7 +14,6 @@
#include <vector> #include <vector>
#include "xenia/cpu/backend/backend.h" #include "xenia/cpu/backend/backend.h"
#include "xenia/cpu/debugger.h"
#include "xenia/cpu/entry_table.h" #include "xenia/cpu/entry_table.h"
#include "xenia/cpu/export_resolver.h" #include "xenia/cpu/export_resolver.h"
#include "xenia/cpu/frontend/ppc_frontend.h" #include "xenia/cpu/frontend/ppc_frontend.h"
@ -23,10 +22,15 @@
#include "xenia/cpu/thread_state.h" #include "xenia/cpu/thread_state.h"
#include "xenia/memory.h" #include "xenia/memory.h"
namespace xe {
namespace debug {
class Debugger;
} // namespace debug
} // namespace xe
namespace xe { namespace xe {
namespace cpu { namespace cpu {
class Runtime;
class ThreadState; class ThreadState;
class XexModule; class XexModule;
@ -43,7 +47,7 @@ class Processor {
~Processor(); ~Processor();
Memory* memory() const { return memory_; } Memory* memory() const { return memory_; }
Debugger* debugger() const { return debugger_.get(); } debug::Debugger* debugger() const { return debugger_.get(); }
frontend::PPCFrontend* frontend() const { return frontend_.get(); } frontend::PPCFrontend* frontend() const { return frontend_.get(); }
backend::Backend* backend() const { return backend_.get(); } backend::Backend* backend() const { return backend_.get(); }
ExportResolver* export_resolver() const { return export_resolver_; } ExportResolver* export_resolver() const { return export_resolver_; }
@ -85,7 +89,7 @@ class Processor {
uint32_t debug_info_flags_; uint32_t debug_info_flags_;
uint32_t trace_flags_; uint32_t trace_flags_;
std::unique_ptr<Debugger> debugger_; std::unique_ptr<debug::Debugger> debugger_;
std::unique_ptr<frontend::PPCFrontend> frontend_; std::unique_ptr<frontend::PPCFrontend> frontend_;
std::unique_ptr<backend::Backend> backend_; std::unique_ptr<backend::Backend> backend_;

View File

@ -6,8 +6,6 @@
'cpu.h', 'cpu.h',
'debug_info.cc', 'debug_info.cc',
'debug_info.h', 'debug_info.h',
'debugger.cc',
'debugger.h',
'entry_table.cc', 'entry_table.cc',
'entry_table.h', 'entry_table.h',
'export_resolver.cc', 'export_resolver.cc',

View File

@ -12,6 +12,7 @@
#include "xenia/base/assert.h" #include "xenia/base/assert.h"
#include "xenia/base/threading.h" #include "xenia/base/threading.h"
#include "xenia/cpu/processor.h" #include "xenia/cpu/processor.h"
#include "xenia/debug/debugger.h"
namespace xe { namespace xe {
namespace cpu { namespace cpu {

View File

@ -0,0 +1,45 @@
/**
******************************************************************************
* Xenia : Xbox 360 Emulator Research Project *
******************************************************************************
* Copyright 2013 Ben Vanik. All rights reserved. *
* Released under the BSD license - see LICENSE in the root for more details. *
******************************************************************************
*/
#ifndef XENIA_DEBUG_BREAKPOINT_H_
#define XENIA_DEBUG_BREAKPOINT_H_
#include <string>
namespace xe {
namespace debug {
class Breakpoint {
public:
enum Type {
TEMP_TYPE,
CODE_TYPE,
};
public:
Breakpoint(Type type, uint32_t address);
~Breakpoint();
Type type() const { return type_; }
uint32_t address() const { return address_; }
const char* id() const { return id_.c_str(); }
void set_id(const char* id) { id_ = std::string(id); }
private:
Type type_;
uint32_t address_;
std::string id_;
};
} // namespace debug
} // namespace xe
#endif // XENIA_DEBUG_BREAKPOINT_H_

View File

@ -0,0 +1,18 @@
/**
******************************************************************************
* Xenia : Xbox 360 Emulator Research Project *
******************************************************************************
* Copyright 2015 Ben Vanik. All rights reserved. *
* Released under the BSD license - see LICENSE in the root for more details. *
******************************************************************************
*/
#include "xenia/debug/debug_server.h"
namespace xe {
namespace debug {
//
} // namespace debug
} // namespace xe

View File

@ -0,0 +1,21 @@
/**
******************************************************************************
* Xenia : Xbox 360 Emulator Research Project *
******************************************************************************
* Copyright 2015 Ben Vanik. All rights reserved. *
* Released under the BSD license - see LICENSE in the root for more details. *
******************************************************************************
*/
#ifndef XENIA_DEBUG_DEBUG_SERVER_H_
#define XENIA_DEBUG_DEBUG_SERVER_H_
namespace xe {
namespace debug {
//
} // namespace debug
} // namespace xe
#endif // XENIA_DEBUG_DEBUG_SERVER_H_

View File

@ -7,7 +7,7 @@
****************************************************************************** ******************************************************************************
*/ */
#include "xenia/cpu/debugger.h" #include "xenia/debug/debugger.h"
#include <mutex> #include <mutex>
@ -15,14 +15,16 @@
#include "xenia/cpu/processor.h" #include "xenia/cpu/processor.h"
namespace xe { namespace xe {
namespace cpu { namespace debug {
using xe::cpu::ThreadState;
Breakpoint::Breakpoint(Type type, uint32_t address) Breakpoint::Breakpoint(Type type, uint32_t address)
: type_(type), address_(address) {} : type_(type), address_(address) {}
Breakpoint::~Breakpoint() = default; Breakpoint::~Breakpoint() = default;
Debugger::Debugger(Processor* processor) : processor_(processor) {} Debugger::Debugger(cpu::Processor* processor) : processor_(processor) {}
Debugger::~Debugger() = default; Debugger::~Debugger() = default;
@ -156,8 +158,8 @@ void Debugger::OnThreadDestroyed(ThreadState* thread_state) {
} }
} }
void Debugger::OnFunctionDefined(FunctionInfo* symbol_info, void Debugger::OnFunctionDefined(cpu::FunctionInfo* symbol_info,
Function* function) { cpu::Function* function) {
// Man, I'd love not to take this lock. // Man, I'd love not to take this lock.
std::vector<Breakpoint*> breakpoints; std::vector<Breakpoint*> breakpoints;
{ {
@ -195,5 +197,5 @@ void Debugger::OnBreakpointHit(ThreadState* thread_state,
// Note that we stay suspended. // Note that we stay suspended.
} }
} // namespace cpu } // namespace debug
} // namespace xe } // namespace xe

View File

@ -7,8 +7,8 @@
****************************************************************************** ******************************************************************************
*/ */
#ifndef XENIA_CPU_DEBUGGER_H_ #ifndef XENIA_DEBUG_DEBUGGER_H_
#define XENIA_CPU_DEBUGGER_H_ #define XENIA_DEBUG_DEBUGGER_H_
#include <map> #include <map>
#include <mutex> #include <mutex>
@ -17,38 +17,20 @@
#include "xenia/base/delegate.h" #include "xenia/base/delegate.h"
#include "xenia/cpu/thread_state.h" #include "xenia/cpu/thread_state.h"
#include "xenia/debug/breakpoint.h"
namespace xe { namespace xe {
namespace cpu { namespace cpu {
class Debugger;
class Function; class Function;
class FunctionInfo; class FunctionInfo;
class Processor; class Processor;
} // namespace cpu
} // namespace xe
class Breakpoint { namespace xe {
public: namespace debug {
enum Type {
TEMP_TYPE,
CODE_TYPE,
};
public: class Debugger;
Breakpoint(Type type, uint32_t address);
~Breakpoint();
Type type() const { return type_; }
uint32_t address() const { return address_; }
const char* id() const { return id_.c_str(); }
void set_id(const char* id) { id_ = std::string(id); }
private:
Type type_;
uint32_t address_;
std::string id_;
};
class DebugEvent { class DebugEvent {
public: public:
@ -62,32 +44,32 @@ class DebugEvent {
class BreakpointHitEvent : public DebugEvent { class BreakpointHitEvent : public DebugEvent {
public: public:
BreakpointHitEvent(Debugger* debugger, ThreadState* thread_state, BreakpointHitEvent(Debugger* debugger, cpu::ThreadState* thread_state,
Breakpoint* breakpoint) Breakpoint* breakpoint)
: DebugEvent(debugger), : DebugEvent(debugger),
thread_state_(thread_state), thread_state_(thread_state),
breakpoint_(breakpoint) {} breakpoint_(breakpoint) {}
~BreakpointHitEvent() override = default; ~BreakpointHitEvent() override = default;
ThreadState* thread_state() const { return thread_state_; } cpu::ThreadState* thread_state() const { return thread_state_; }
Breakpoint* breakpoint() const { return breakpoint_; } Breakpoint* breakpoint() const { return breakpoint_; }
protected: protected:
ThreadState* thread_state_; cpu::ThreadState* thread_state_;
Breakpoint* breakpoint_; Breakpoint* breakpoint_;
}; };
class Debugger { class Debugger {
public: public:
Debugger(Processor* processor); Debugger(cpu::Processor* processor);
~Debugger(); ~Debugger();
Processor* processor() const { return processor_; } cpu::Processor* processor() const { return processor_; }
int SuspendAllThreads(uint32_t timeout_ms = UINT_MAX); int SuspendAllThreads(uint32_t timeout_ms = UINT_MAX);
int ResumeThread(uint32_t thread_id); int ResumeThread(uint32_t thread_id);
int ResumeAllThreads(bool force = false); int ResumeAllThreads(bool force = false);
void ForEachThread(std::function<void(ThreadState*)> callback); void ForEachThread(std::function<void(cpu::ThreadState*)> callback);
int AddBreakpoint(Breakpoint* breakpoint); int AddBreakpoint(Breakpoint* breakpoint);
int RemoveBreakpoint(Breakpoint* breakpoint); int RemoveBreakpoint(Breakpoint* breakpoint);
@ -97,26 +79,27 @@ class Debugger {
// TODO(benvanik): utility functions for modification (make function ignored, // TODO(benvanik): utility functions for modification (make function ignored,
// etc). // etc).
void OnThreadCreated(ThreadState* thread_state); void OnThreadCreated(cpu::ThreadState* thread_state);
void OnThreadDestroyed(ThreadState* thread_state); void OnThreadDestroyed(cpu::ThreadState* thread_state);
void OnFunctionDefined(FunctionInfo* symbol_info, Function* function); void OnFunctionDefined(cpu::FunctionInfo* symbol_info,
cpu::Function* function);
void OnBreakpointHit(ThreadState* thread_state, Breakpoint* breakpoint); void OnBreakpointHit(cpu::ThreadState* thread_state, Breakpoint* breakpoint);
public: public:
Delegate<BreakpointHitEvent> breakpoint_hit; Delegate<BreakpointHitEvent> breakpoint_hit;
private: private:
Processor* processor_; cpu::Processor* processor_;
std::mutex threads_lock_; std::mutex threads_lock_;
std::unordered_map<uint32_t, ThreadState*> threads_; std::unordered_map<uint32_t, cpu::ThreadState*> threads_;
std::mutex breakpoints_lock_; std::mutex breakpoints_lock_;
std::multimap<uint32_t, Breakpoint*> breakpoints_; std::multimap<uint32_t, Breakpoint*> breakpoints_;
}; };
} // namespace cpu } // namespace debug
} // namespace xe } // namespace xe
#endif // XENIA_CPU_DEBUGGER_H_ #endif // XENIA_DEBUG_DEBUGGER_H_

View File

@ -0,0 +1,11 @@
# Copyright 2015 Ben Vanik. All Rights Reserved.
{
'sources': [
'debug_server.cc',
'debug_server.h',
'debugger.cc',
'debugger.h',
'trace_writer.cc',
'trace_writer.h',
],
}

View File

@ -0,0 +1,18 @@
/**
******************************************************************************
* Xenia : Xbox 360 Emulator Research Project *
******************************************************************************
* Copyright 2015 Ben Vanik. All rights reserved. *
* Released under the BSD license - see LICENSE in the root for more details. *
******************************************************************************
*/
#include "xenia/debug/trace_writer.h"
namespace xe {
namespace debug {
//
} // namespace debug
} // namespace xe

View File

@ -0,0 +1,29 @@
/**
******************************************************************************
* Xenia : Xbox 360 Emulator Research Project *
******************************************************************************
* Copyright 2015 Ben Vanik. All rights reserved. *
* Released under the BSD license - see LICENSE in the root for more details. *
******************************************************************************
*/
#ifndef XENIA_DEBUG_TRACE_WRITER_H_
#define XENIA_DEBUG_TRACE_WRITER_H_
namespace xe {
namespace debug {
enum TraceFlags {
kTraceFunctionInfo = 1 << 0,
kTraceInstructionReferences = 1 << 1,
kTraceInstructionResults = 1 << 2,
};
class TraceWriter {
public:
};
} // namespace debug
} // namespace xe
#endif // XENIA_DEBUG_TRACE_WRITER_H_

View File

@ -15,6 +15,7 @@
'apu/sources.gypi', 'apu/sources.gypi',
'base/sources.gypi', 'base/sources.gypi',
'cpu/sources.gypi', 'cpu/sources.gypi',
'debug/sources.gypi',
'gpu/sources.gypi', 'gpu/sources.gypi',
'hid/sources.gypi', 'hid/sources.gypi',
'kernel/sources.gypi', 'kernel/sources.gypi',