all repos — mgba @ 74bb02065d232108192b41eb80e2889e000457bf

mGBA Game Boy Advance Emulator

src/platform/qt/DebuggerConsoleController.cpp (view raw)

  1/* Copyright (c) 2013-2016 Jeffrey Pfau
  2 *
  3 * This Source Code Form is subject to the terms of the Mozilla Public
  4 * License, v. 2.0. If a copy of the MPL was not distributed with this
  5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
  6#include "DebuggerConsoleController.h"
  7
  8#include "GameController.h"
  9
 10#include <QMutexLocker>
 11
 12extern "C" {
 13#include "debugger/cli-debugger.h"
 14}
 15
 16using namespace QGBA;
 17
 18DebuggerConsoleController::DebuggerConsoleController(GameController* controller, QObject* parent)
 19	: DebuggerController(controller, &m_cliDebugger.d, parent)
 20{
 21	m_backend.d.printf = printf;
 22	m_backend.d.init = init;
 23	m_backend.d.deinit = deinit;
 24	m_backend.d.readline = readLine;
 25	m_backend.d.lineAppend = lineAppend;
 26	m_backend.d.historyLast = historyLast;
 27	m_backend.d.historyAppend = historyAppend;
 28	m_backend.self = this;
 29
 30	CLIDebuggerCreate(&m_cliDebugger);
 31	CLIDebuggerAttachBackend(&m_cliDebugger, &m_backend.d);
 32}
 33
 34void DebuggerConsoleController::enterLine(const QString& line) {
 35	QMutexLocker lock(&m_mutex);
 36	m_lines.append(line);
 37	if (m_cliDebugger.d.state == DEBUGGER_RUNNING) {
 38		mDebuggerEnter(&m_cliDebugger.d, DEBUGGER_ENTER_MANUAL, nullptr);
 39	}
 40	m_cond.wakeOne();
 41}
 42
 43void DebuggerConsoleController::attachInternal() {
 44	mCore* core = m_gameController->thread()->core;
 45	CLIDebuggerAttachSystem(&m_cliDebugger, core->cliDebuggerSystem(core));
 46}
 47
 48void DebuggerConsoleController::printf(struct CLIDebuggerBackend* be, const char* fmt, ...) {
 49	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 50	DebuggerConsoleController* self = consoleBe->self;
 51	va_list args;
 52	va_start(args, fmt);
 53	self->log(QString().vsprintf(fmt, args));
 54	va_end(args);
 55}
 56
 57void DebuggerConsoleController::init(struct CLIDebuggerBackend* be) {
 58	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 59	DebuggerConsoleController* self = consoleBe->self;
 60}
 61
 62void DebuggerConsoleController::deinit(struct CLIDebuggerBackend* be) {
 63	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 64	DebuggerConsoleController* self = consoleBe->self;
 65}
 66
 67const char* DebuggerConsoleController::readLine(struct CLIDebuggerBackend* be, size_t* len) {
 68	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 69	DebuggerConsoleController* self = consoleBe->self;
 70	GameController::Interrupter interrupter(self->m_gameController, true);
 71	QMutexLocker lock(&self->m_mutex);
 72	while (self->m_lines.isEmpty()) {
 73		self->m_cond.wait(&self->m_mutex);
 74	}
 75	self->m_last = self->m_lines.takeFirst().toUtf8();
 76	*len = self->m_last.size();
 77	return self->m_last.constData();
 78
 79}
 80
 81void DebuggerConsoleController::lineAppend(struct CLIDebuggerBackend* be, const char* line) {
 82	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 83	DebuggerConsoleController* self = consoleBe->self;
 84	self->lineAppend(QString::fromUtf8(line));
 85}
 86
 87const char* DebuggerConsoleController::historyLast(struct CLIDebuggerBackend* be, size_t* len) {
 88	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 89	DebuggerConsoleController* self = consoleBe->self;
 90	GameController::Interrupter interrupter(self->m_gameController, true);
 91	QMutexLocker lock(&self->m_mutex);
 92	self->m_last = self->m_history.last().toUtf8();
 93	return self->m_last.constData();
 94}
 95
 96void DebuggerConsoleController::historyAppend(struct CLIDebuggerBackend* be, const char* line) {
 97	Backend* consoleBe = reinterpret_cast<Backend*>(be);
 98	DebuggerConsoleController* self = consoleBe->self;
 99	GameController::Interrupter interrupter(self->m_gameController, true);
100	QMutexLocker lock(&self->m_mutex);
101	self->m_history.append(QString::fromUtf8(line));
102}