Merge branch 'master' of git@scm.dev.nokia.troll.no:creator/mainline

This commit is contained in:
dt
2009-01-15 15:57:24 +01:00
29 changed files with 771 additions and 462 deletions

View File

@@ -26,11 +26,11 @@ HEADERS += attachexternaldialog.h \
disassemblerwindow.h \
gdbengine.h \
gdbmi.h \
gdboptionpage.h \
idebuggerengine.h \
imports.h \
moduleshandler.h \
moduleswindow.h \
outputcollector.h \
procinterrupt.h \
registerhandler.h \
registerwindow.h \
@@ -41,7 +41,7 @@ HEADERS += attachexternaldialog.h \
threadswindow.h \
watchhandler.h \
watchwindow.h
SOURCES += attachexternaldialog.cpp \
attachremotedialog.cpp \
breakhandler.cpp \
@@ -55,10 +55,9 @@ SOURCES += attachexternaldialog.cpp \
disassemblerwindow.cpp \
gdbengine.cpp \
gdbmi.cpp \
gdboptionpage.cpp \
gdbengine.h \
moduleshandler.cpp \
moduleswindow.cpp \
outputcollector.cpp \
procinterrupt.cpp \
registerhandler.cpp \
registerwindow.cpp \

View File

@@ -86,6 +86,18 @@ using namespace Debugger::Constants;
static const QString tooltipIName = "tooltip";
DebuggerSettings::DebuggerSettings()
{
m_autoRun = false;
m_autoQuit = false;
m_skipKnownFrames = false;
m_debugDumpers = false;
m_useToolTips = false;
m_useToolTips = false;
m_useCustomDumpers = true;
}
///////////////////////////////////////////////////////////////////////
//
// BreakByFunctionDialog
@@ -322,56 +334,6 @@ void DebuggerManager::init()
m_breakAtMainAction = new QAction(this);
m_breakAtMainAction->setText(tr("Set Breakpoint at Function 'main'"));
m_debugDumpersAction = new QAction(this);
m_debugDumpersAction->setText(tr("Debug Custom Dumpers"));
m_debugDumpersAction->setToolTip(tr("This is an internal tool to "
"make debugging the Custom Data Dumper code easier. "
"Using this action is in general not needed unless you "
"want do debug Qt Creator itself."));
m_debugDumpersAction->setCheckable(true);
m_skipKnownFramesAction = new QAction(this);
m_skipKnownFramesAction->setText(tr("Skip Known Frames When Stepping"));
m_skipKnownFramesAction->setToolTip(tr("After checking this option"
"'Step Into' combines in certain situations several steps, "
"leading to 'less noisy' debugging. So will, e.g., the atomic "
"reference counting code be skipped, and a single 'Step Into' "
"for a signal emission will end up directly in the slot connected "
"to it"));
m_skipKnownFramesAction->setCheckable(true);
m_useCustomDumpersAction = new QAction(this);
m_useCustomDumpersAction->setText(tr("Use Custom Display for Qt Objects"));
m_useCustomDumpersAction->setToolTip(tr("Checking this will make the debugger "
"try to use code to format certain data (QObject, QString, ...) nicely. "));
m_useCustomDumpersAction->setCheckable(true);
m_useCustomDumpersAction->setChecked(true);
m_useFastStartAction = new QAction(this);
m_useFastStartAction->setText(tr("Fast Debugger Start"));
m_useFastStartAction->setToolTip(tr("Checking this will make the debugger "
"start fast by loading only very few debug symbols on start up. This "
"might lead to situations where breakpoints can not be set properly. "
"So uncheck this option if you experience breakpoint related problems."));
m_useFastStartAction->setCheckable(true);
m_useFastStartAction->setChecked(true);
m_useToolTipsAction = new QAction(this);
m_useToolTipsAction->setText(tr("Use Tooltips While Debugging"));
m_useToolTipsAction->setToolTip(tr("Checking this will make enable "
"tooltips for variable values during debugging. Since this can slow "
"down debugging and does not provide reliable information as it does "
"not use scope information, it is switched off by default."));
m_useToolTipsAction->setCheckable(true);
m_useToolTipsAction->setChecked(false);
// FIXME
m_useFastStartAction->setChecked(false);
m_useFastStartAction->setEnabled(false);
m_dumpLogAction = new QAction(this);
m_dumpLogAction->setText(tr("Dump Log File for Debugging Purposes"));
m_watchAction = new QAction(this);
m_watchAction->setText(tr("Add to Watch Window"));
@@ -416,14 +378,6 @@ void DebuggerManager::init()
connect(m_breakAtMainAction, SIGNAL(triggered()),
this, SLOT(breakAtMain()));
connect(m_useFastStartAction, SIGNAL(triggered()),
this, SLOT(saveSessionData()));
connect(m_useCustomDumpersAction, SIGNAL(triggered()),
this, SLOT(saveSessionData()));
connect(m_skipKnownFramesAction, SIGNAL(triggered()),
this, SLOT(saveSessionData()));
connect(m_dumpLogAction, SIGNAL(triggered()),
this, SLOT(dumpLog()));
connect(m_statusTimer, SIGNAL(timeout()),
this, SLOT(clearStatusMessage()));
@@ -636,9 +590,9 @@ void DebuggerManager::notifyInferiorPidChanged(int pid)
emit inferiorPidChanged(pid);
}
void DebuggerManager::showApplicationOutput(const QString &prefix, const QString &str)
void DebuggerManager::showApplicationOutput(const QString &str)
{
emit applicationOutputAvailable(prefix, str);
emit applicationOutputAvailable(str);
}
void DebuggerManager::shutdown()
@@ -947,16 +901,6 @@ void DebuggerManager::loadSessionData()
{
m_breakHandler->loadSessionData();
m_watchHandler->loadSessionData();
QVariant value;
querySessionValue(QLatin1String("UseFastStart"), &value);
m_useFastStartAction->setChecked(value.toBool());
querySessionValue(QLatin1String("UseToolTips"), &value);
m_useToolTipsAction->setChecked(value.toBool());
querySessionValue(QLatin1String("UseCustomDumpers"), &value);
m_useCustomDumpersAction->setChecked(!value.isValid() || value.toBool());
querySessionValue(QLatin1String("SkipKnownFrames"), &value);
m_skipKnownFramesAction->setChecked(value.toBool());
engine()->loadSessionData();
}
@@ -964,15 +908,6 @@ void DebuggerManager::saveSessionData()
{
m_breakHandler->saveSessionData();
m_watchHandler->saveSessionData();
setSessionValue(QLatin1String("UseFastStart"),
m_useFastStartAction->isChecked());
setSessionValue(QLatin1String("UseToolTips"),
m_useToolTipsAction->isChecked());
setSessionValue(QLatin1String("UseCustomDumpers"),
m_useCustomDumpersAction->isChecked());
setSessionValue(QLatin1String("SkipKnownFrames"),
m_skipKnownFramesAction->isChecked());
engine()->saveSessionData();
}
@@ -1139,22 +1074,22 @@ void DebuggerManager::setBusyCursor(bool busy)
bool DebuggerManager::skipKnownFrames() const
{
return m_skipKnownFramesAction->isChecked();
return m_settings.m_skipKnownFrames;
}
bool DebuggerManager::debugDumpers() const
{
return m_debugDumpersAction->isChecked();
return m_settings.m_debugDumpers;
}
bool DebuggerManager::useCustomDumpers() const
{
return m_useCustomDumpersAction->isChecked();
return m_settings.m_useCustomDumpers;
}
bool DebuggerManager::useFastStart() const
{
return 0; // && m_useFastStartAction->isChecked();
return 0; // && m_settings.m_useFastStart;
}
void DebuggerManager::queryCurrentTextEditor(QString *fileName, int *lineNumber,

View File

@@ -166,9 +166,9 @@ private:
virtual ThreadsHandler *threadsHandler() = 0;
virtual WatchHandler *watchHandler() = 0;
virtual void showApplicationOutput(const QString &prefix, const QString &data) = 0;
virtual QAction *useCustomDumpersAction() const = 0;
virtual QAction *debugDumpersAction() const = 0;
virtual void showApplicationOutput(const QString &data) = 0;
//virtual QAction *useCustomDumpersAction() const = 0;
//virtual QAction *debugDumpersAction() const = 0;
virtual bool skipKnownFrames() const = 0;
virtual bool debugDumpers() const = 0;
virtual bool useCustomDumpers() const = 0;
@@ -180,6 +180,30 @@ private:
};
//
// DebuggerSettings
//
class DebuggerSettings
{
public:
DebuggerSettings();
public:
QString m_gdbCmd;
QString m_gdbEnv;
bool m_autoRun;
bool m_autoQuit;
bool m_useCustomDumpers;
bool m_skipKnownFrames;
bool m_debugDumpers;
bool m_useFastStart;
bool m_useToolTips;
QString m_scriptFile;
};
//
// DebuggerManager
//
@@ -196,6 +220,7 @@ public:
IDebuggerManagerAccessForEngines *engineInterface();
QMainWindow *mainWindow() const { return m_mainWindow; }
QLabel *statusLabel() const { return m_statusLabel; }
DebuggerSettings *settings() { return &m_settings; }
enum StartMode { startInternal, startExternal, attachExternal };
enum DebuggerType { GdbDebugger, ScriptDebugger, WinDebugger };
@@ -260,7 +285,7 @@ public slots:
private slots:
void showDebuggerOutput(const QString &prefix, const QString &msg);
void showDebuggerInput(const QString &prefix, const QString &msg);
void showApplicationOutput(const QString &prefix, const QString &msg);
void showApplicationOutput(const QString &data);
void reloadDisassembler();
void disassemblerDockToggled(bool on);
@@ -286,9 +311,9 @@ private:
StackHandler *stackHandler() { return m_stackHandler; }
ThreadsHandler *threadsHandler() { return m_threadsHandler; }
WatchHandler *watchHandler() { return m_watchHandler; }
QAction *useCustomDumpersAction() const { return m_useCustomDumpersAction; }
QAction *useToolTipsAction() const { return m_useToolTipsAction; }
QAction *debugDumpersAction() const { return m_debugDumpersAction; }
//QAction *useCustomDumpersAction() const { return m_useCustomDumpersAction; }
//QAction *useToolTipsAction() const { return m_useToolTipsAction; }
//QAction *debugDumpersAction() const { return m_debugDumpersAction; }
bool skipKnownFrames() const;
bool debugDumpers() const;
bool useCustomDumpers() const;
@@ -340,8 +365,7 @@ signals:
void setSessionValueRequested(const QString &name, const QVariant &value);
void configValueRequested(const QString &name, QVariant *value);
void setConfigValueRequested(const QString &name, const QVariant &value);
void applicationOutputAvailable(const QString &prefix, const QString &msg);
void applicationOutputAvailable(const QString &output);
public:
// FIXME: make private
@@ -406,13 +430,6 @@ private:
QAction *m_sepAction;
QAction *m_stepIAction;
QAction *m_nextIAction;
QAction *m_skipKnownFramesAction;
QAction *m_debugDumpersAction;
QAction *m_useCustomDumpersAction;
QAction *m_useFastStartAction;
QAction *m_useToolTipsAction;
QAction *m_dumpLogAction;
QWidget *m_breakWindow;
QWidget *m_disassemblerWindow;
@@ -432,9 +449,9 @@ private:
IDebuggerEngine *engine();
IDebuggerEngine *m_engine;
DebuggerSettings m_settings;
};
} // namespace Internal
} // namespace Debugger

View File

@@ -36,12 +36,14 @@
#include "debuggerconstants.h"
#include "debuggermanager.h"
#include "debuggerrunner.h"
#include "gdboptionpage.h"
#include "gdbengine.h"
#include "ui_gdboptionpage.h"
#include <coreplugin/actionmanager/actionmanager.h>
#include <coreplugin/basemode.h>
#include <coreplugin/coreconstants.h>
#include <coreplugin/dialogs/ioptionspage.h>
#include <coreplugin/editormanager/editormanager.h>
#include <coreplugin/findplaceholder.h>
#include <coreplugin/icore.h>
@@ -53,6 +55,8 @@
#include <coreplugin/rightpane.h>
#include <coreplugin/uniqueidmanager.h>
#include <extensionsystem/pluginmanager.h>
#include <cplusplus/ExpressionUnderCursor.h>
#include <cppeditor/cppeditorconstants.h>
@@ -73,6 +77,7 @@
#include <QtCore/QSettings>
#include <QtCore/QtPlugin>
#include <QtGui/QLineEdit>
#include <QtGui/QDockWidget>
#include <QtGui/QMainWindow>
#include <QtGui/QPlainTextEdit>
@@ -80,6 +85,8 @@
#include <QtGui/QTextCursor>
namespace ExtensionSystem { class PluginManager; }
using namespace Core;
using namespace Debugger::Constants;
using namespace Debugger::Internal;
@@ -99,13 +106,7 @@ const char * const JUMP_TO_LINE = "Debugger.JumpToLine";
const char * const TOGGLE_BREAK = "Debugger.ToggleBreak";
const char * const BREAK_BY_FUNCTION = "Debugger.BreakByFunction";
const char * const BREAK_AT_MAIN = "Debugger.BreakAtMain";
const char * const DEBUG_DUMPERS = "Debugger.DebugDumpers";
const char * const ADD_TO_WATCH = "Debugger.AddToWatch";
const char * const USE_CUSTOM_DUMPERS = "Debugger.UseCustomDumpers";
const char * const USE_FAST_START = "Debugger.UseFastStart";
const char * const USE_TOOL_TIPS = "Debugger.UseToolTips";
const char * const SKIP_KNOWN_FRAMES = "Debugger.SkipKnownFrames";
const char * const DUMP_LOG = "Debugger.DumpLog";
#ifdef Q_OS_MAC
const char * const INTERRUPT_KEY = "Shift+F5";
@@ -143,6 +144,12 @@ const char * const ADD_TO_WATCH_KEY = "Ctrl+Alt+Q";
} // namespace Debugger
///////////////////////////////////////////////////////////////////////
//
// DebugMode
//
///////////////////////////////////////////////////////////////////////
namespace Debugger {
namespace Internal {
@@ -159,9 +166,6 @@ public:
void shutdown() {}
};
} // namespace Internal
} // namespace Debugger
DebugMode::DebugMode(QObject *parent)
: BaseMode(parent)
{
@@ -177,6 +181,9 @@ DebugMode::~DebugMode()
EditorManager::instance()->setParent(0);
}
} // namespace Internal
} // namespace Debugger
///////////////////////////////////////////////////////////////////////
//
@@ -184,8 +191,10 @@ DebugMode::~DebugMode()
//
///////////////////////////////////////////////////////////////////////
class Debugger::Internal::LocationMark
: public TextEditor::BaseTextMark
namespace Debugger {
namespace Internal {
class LocationMark : public TextEditor::BaseTextMark
{
Q_OBJECT
@@ -212,6 +221,108 @@ QIcon LocationMark::icon() const
return icon;
}
} // namespace Internal
} // namespace Debugger
///////////////////////////////////////////////////////////////////////
//
// GdbOptionPage
//
///////////////////////////////////////////////////////////////////////
namespace Debugger {
namespace Internal {
class GdbOptionPage : public Core::IOptionsPage
{
Q_OBJECT
public:
GdbOptionPage(DebuggerPlugin *plugin) : m_plugin(plugin) {}
// IOptionsPage
QString name() const { return tr("Gdb"); }
QString category() const { return "Debugger"; }
QString trCategory() const { return tr("Debugger"); }
QWidget *createPage(QWidget *parent);
void apply();
void finish() {} // automatically calls "apply"
private:
Ui::GdbOptionPage m_ui;
DebuggerSettings m_settings;
DebuggerPlugin *m_plugin;
};
QWidget *GdbOptionPage::createPage(QWidget *parent)
{
QWidget *w = new QWidget(parent);
m_settings = *m_plugin->m_manager->settings();
m_ui.setupUi(w);
m_ui.gdbLocationChooser->setExpectedKind(Core::Utils::PathChooser::Command);
m_ui.gdbLocationChooser->setPromptDialogTitle(tr("Choose Gdb Location"));
m_ui.gdbLocationChooser->setPath(m_settings.m_gdbCmd);
m_ui.scriptFileChooser->setExpectedKind(Core::Utils::PathChooser::File);
m_ui.scriptFileChooser->setPromptDialogTitle(tr("Choose Location of Startup Script File"));
m_ui.scriptFileChooser->setPath(m_settings.m_scriptFile);
m_ui.environmentEdit->setText(m_settings.m_gdbEnv);
m_ui.autoStartBox->setChecked(m_settings.m_autoRun);
m_ui.autoQuitBox->setChecked(m_settings.m_autoQuit);
m_ui.checkBoxSkipKnownFrames->setChecked(m_settings.m_skipKnownFrames);
m_ui.checkBoxDebugDumpers->setChecked(m_settings.m_debugDumpers);
m_ui.checkBoxUseCustomDumpers->setChecked(m_settings.m_useCustomDumpers);
m_ui.checkBoxFastStart->setChecked(m_settings.m_useFastStart);
m_ui.checkBoxUseToolTips->setChecked(m_settings.m_useToolTips);
#ifndef QT_DEBUG
#if 0
cmd = am->registerAction(m_manager->m_dumpLogAction,
Constants::DUMP_LOG, globalcontext);
//cmd->setDefaultKeySequence(QKeySequence(tr("Ctrl+D,Ctrl+L")));
cmd->setDefaultKeySequence(QKeySequence(tr("Ctrl+Shift+F11")));
mdebug->addAction(cmd);
#endif
#endif
// FIXME
m_ui.autoStartBox->hide();
m_ui.autoQuitBox->hide();
m_ui.environmentEdit->hide();
m_ui.labelEnvironment->hide();
m_ui.checkBoxFastStart->setChecked(false);
m_ui.checkBoxFastStart->hide();
//m_dumpLogAction = new QAction(this);
//m_dumpLogAction->setText(tr("Dump Log File for Debugging Purposes"));
return w;
}
void GdbOptionPage::apply()
{
m_settings.m_gdbCmd = m_ui.gdbLocationChooser->path();
m_settings.m_gdbEnv = m_ui.environmentEdit->text();
m_settings.m_autoRun = m_ui.autoStartBox->isChecked();
m_settings.m_autoQuit = m_ui.autoQuitBox->isChecked();
m_settings.m_scriptFile = m_ui.scriptFileChooser->path();
m_settings.m_skipKnownFrames = m_ui.checkBoxSkipKnownFrames->isChecked();
m_settings.m_debugDumpers = m_ui.checkBoxDebugDumpers->isChecked();
m_settings.m_useCustomDumpers = m_ui.checkBoxUseCustomDumpers->isChecked();
m_settings.m_useFastStart = m_ui.checkBoxFastStart->isChecked();
m_settings.m_useToolTips = m_ui.checkBoxUseToolTips->isChecked();
*m_plugin->m_manager->settings() = m_settings;
m_plugin->writeSettings();
}
} // namespace Internal
} // namespace Debugger
///////////////////////////////////////////////////////////////////////
//
@@ -409,34 +520,6 @@ bool DebuggerPlugin::initialize(const QStringList &arguments, QString *error_mes
cmd = am->registerAction(sep, QLatin1String("Debugger.Sep2"), globalcontext);
mdebug->addAction(cmd);
cmd = am->registerAction(m_manager->m_skipKnownFramesAction,
Constants::SKIP_KNOWN_FRAMES, globalcontext);
mdebug->addAction(cmd);
cmd = am->registerAction(m_manager->m_useCustomDumpersAction,
Constants::USE_CUSTOM_DUMPERS, globalcontext);
mdebug->addAction(cmd);
cmd = am->registerAction(m_manager->m_useFastStartAction,
Constants::USE_FAST_START, globalcontext);
mdebug->addAction(cmd);
cmd = am->registerAction(m_manager->m_useToolTipsAction,
Constants::USE_TOOL_TIPS, globalcontext);
mdebug->addAction(cmd);
#ifdef QT_DEBUG
cmd = am->registerAction(m_manager->m_dumpLogAction,
Constants::DUMP_LOG, globalcontext);
//cmd->setDefaultKeySequence(QKeySequence(tr("Ctrl+D,Ctrl+L")));
cmd->setDefaultKeySequence(QKeySequence(tr("Ctrl+Shift+F11")));
mdebug->addAction(cmd);
cmd = am->registerAction(m_manager->m_debugDumpersAction,
Constants::DEBUG_DUMPERS, debuggercontext);
mdebug->addAction(cmd);
#endif
sep = new QAction(this);
sep->setSeparator(true);
cmd = am->registerAction(sep, QLatin1String("Debugger.Sep4"), globalcontext);
@@ -479,7 +562,7 @@ bool DebuggerPlugin::initialize(const QStringList &arguments, QString *error_mes
m_generalOptionPage = 0;
// FIXME:
m_generalOptionPage = new GdbOptionPage(&theGdbSettings());
m_generalOptionPage = new GdbOptionPage(this);
addObject(m_generalOptionPage);
m_locationMark = 0;
@@ -711,7 +794,7 @@ void DebuggerPlugin::requestMark(TextEditor::ITextEditor *editor, int lineNumber
void DebuggerPlugin::showToolTip(TextEditor::ITextEditor *editor,
const QPoint &point, int pos)
{
if (!m_manager->useToolTipsAction()->isChecked())
if (!m_manager->settings()->m_useToolTips)
return;
QPlainTextEdit *plaintext = qobject_cast<QPlainTextEdit*>(editor->widget());
@@ -799,22 +882,57 @@ void DebuggerPlugin::changeStatus(int status)
void DebuggerPlugin::writeSettings() const
{
QSettings *s = settings();
QTC_ASSERT(m_manager, return);
QTC_ASSERT(m_manager->mainWindow(), return);
QSettings *s = settings();
DebuggerSettings *m = m_manager->settings();
s->beginGroup(QLatin1String("DebugMode"));
s->setValue(QLatin1String("State"), m_manager->mainWindow()->saveState());
s->setValue(QLatin1String("Locked"), m_toggleLockedAction->isChecked());
s->setValue("State", m_manager->mainWindow()->saveState());
s->setValue("Locked", m_toggleLockedAction->isChecked());
s->setValue("Location", m->m_gdbCmd);
s->setValue("Environment", m->m_gdbEnv);
s->setValue("AutoRun", m->m_autoRun);
s->setValue("AutoQuit", m->m_autoQuit);
s->setValue("UseFastStart", m->m_useFastStart);
s->setValue("UseToolTips", m->m_useToolTips);
s->setValue("UseCustomDumpers", m->m_useCustomDumpers);
s->setValue("SkipKnowFrames", m->m_skipKnownFrames);
s->setValue("DebugDumpers", m->m_debugDumpers);
s->endGroup();
}
void DebuggerPlugin::readSettings()
{
QSettings *s = settings();
DebuggerSettings *m = &m_manager->m_settings;
QString defaultCommand("gdb");
#if defined(Q_OS_WIN32)
defaultCommand.append(".exe");
#endif
Core::ICore *coreIFace = m_pm->getObject<Core::ICore>();
QString defaultScript = coreIFace->resourcePath() +
QLatin1String("/gdb/qt4macros");
s->beginGroup(QLatin1String("DebugMode"));
m_manager->mainWindow()->restoreState(s->value(QLatin1String("State"), QByteArray()).toByteArray());
m_toggleLockedAction->setChecked(s->value(QLatin1String("Locked"), true).toBool());
QByteArray ba = s->value("State", QByteArray()).toByteArray();
m_toggleLockedAction->setChecked(s->value("Locked", true).toBool());
m->m_gdbCmd = s->value("Location", defaultCommand).toString();
m->m_scriptFile= s->value("ScriptFile", defaultScript).toString();
m->m_gdbEnv = s->value("Environment", "").toString();
m->m_autoRun = s->value("AutoRun", true).toBool();
m->m_autoQuit = s->value("AutoQuit", true).toBool();
m->m_skipKnownFrames = s->value("SkipKnownFrames", false).toBool();
m->m_debugDumpers = s->value("DebugDumpers", false).toBool();
m->m_useCustomDumpers = s->value("UseCustomDupers", false).toBool();
m->m_useFastStart = s->value("UseFastStart", false).toBool();
m->m_useToolTips = s->value("UseToolTips", false).toBool();
s->endGroup();
m_manager->mainWindow()->restoreState(ba);
}
void DebuggerPlugin::focusCurrentEditor(IMode *mode)

View File

@@ -78,7 +78,6 @@ private slots:
void changeStatus(int status);
void requestMark(TextEditor::ITextEditor *editor, int lineNumber);
void showToolTip(TextEditor::ITextEditor *editor, const QPoint &pnt, int pos);
void querySessionValue(const QString &name, QVariant *value);
void setSessionValue(const QString &name, const QVariant &value);
void queryConfigValue(const QString &name, QVariant *value);
@@ -97,6 +96,7 @@ private:
void writeSettings() const;
friend class DebuggerManager;
friend class GdbOptionPage;
friend class DebugMode; // FIXME: Just a hack now so that it can access the views
ProjectExplorer::ProjectExplorerPlugin *projectExplorer() const;

View File

@@ -108,8 +108,8 @@ DebuggerRunControl::DebuggerRunControl(DebuggerManager *manager,
{
connect(m_manager, SIGNAL(debuggingFinished()),
this, SLOT(debuggingFinished()));
connect(m_manager, SIGNAL(applicationOutputAvailable(QString, QString)),
this, SLOT(slotAddToOutputWindow(QString, QString)));
connect(m_manager, SIGNAL(applicationOutputAvailable(QString)),
this, SLOT(slotAddToOutputWindowInline(QString)));
connect(m_manager, SIGNAL(inferiorPidChanged(qint64)),
this, SLOT(bringApplicationToForeground(qint64)));
}
@@ -138,12 +138,9 @@ void DebuggerRunControl::start()
debuggingFinished();
}
void DebuggerRunControl::slotAddToOutputWindow(const QString &prefix, const QString &line)
void DebuggerRunControl::slotAddToOutputWindowInline(const QString &data)
{
Q_UNUSED(prefix);
foreach (const QString &l, line.split('\n'))
emit addToOutputWindow(this, prefix + Qt::escape(l));
//emit addToOutputWindow(this, prefix + Qt::escape(line));
emit addToOutputWindowInline(this, data);
}
void DebuggerRunControl::stop()

View File

@@ -84,7 +84,7 @@ public:
private slots:
void debuggingFinished();
void slotAddToOutputWindow(const QString &prefix, const QString &line);
void slotAddToOutputWindowInline(const QString &output);
private:
DebuggerManager *m_manager;

View File

@@ -84,19 +84,6 @@ Q_DECLARE_METATYPE(Debugger::Internal::GdbMi);
static const QString tooltipIName = "tooltip";
///////////////////////////////////////////////////////////////////////
//
// GdbSettings
//
///////////////////////////////////////////////////////////////////////
GdbSettings &Debugger::Internal::theGdbSettings()
{
static GdbSettings settings;
return settings;
}
///////////////////////////////////////////////////////////////////////
//
// GdbCommandType
@@ -265,7 +252,7 @@ void GdbEngine::init()
m_pendingRequests = 0;
m_gdbVersion = 100;
m_shared = 0;
qq->debugDumpersAction()->setChecked(false);
m_outputCodec = QTextCodec::codecForLocale();
m_oldestAcceptableToken = -1;
@@ -279,12 +266,9 @@ void GdbEngine::init()
connect(&m_gdbProc, SIGNAL(finished(int, QProcess::ExitStatus)), q,
SLOT(exitDebugger()));
connect(qq->debugDumpersAction(), SIGNAL(toggled(bool)),
this, SLOT(setDebugDumpers(bool)));
connect(qq->useCustomDumpersAction(), SIGNAL(toggled(bool)),
this, SLOT(setCustomDumpersWanted(bool)));
// Output
connect(&m_outputCollector, SIGNAL(byteDelivery(QByteArray)),
SLOT(readDebugeeOutput(QByteArray)));
connect(this, SIGNAL(gdbResponseAvailable()),
this, SLOT(handleResponse()), Qt::QueuedConnection);
@@ -294,8 +278,8 @@ void GdbEngine::init()
connect(this, SIGNAL(gdbInputAvailable(QString,QString)),
q, SLOT(showDebuggerInput(QString,QString)),
Qt::QueuedConnection);
connect(this, SIGNAL(applicationOutputAvailable(QString,QString)),
q, SLOT(showApplicationOutput(QString,QString)),
connect(this, SIGNAL(applicationOutputAvailable(QString)),
q, SLOT(showApplicationOutput(QString)),
Qt::QueuedConnection);
}
@@ -306,7 +290,7 @@ void GdbEngine::gdbProcError(QProcess::ProcessError error)
case QProcess::FailedToStart:
msg = QString(tr("The Gdb process failed to start. Either the "
"invoked program '%1' is missing, or you may have insufficient "
"permissions to invoke the program.")).arg(theGdbSettings().m_gdbCmd);
"permissions to invoke the program.")).arg(q->settings()->m_gdbCmd);
break;
case QProcess::Crashed:
msg = tr("The Gdb process crashed some time after starting "
@@ -374,6 +358,12 @@ static void skipTerminator(const char *&from, const char *to)
skipSpaces(from, to);
}
void GdbEngine::readDebugeeOutput(const QByteArray &data)
{
emit applicationOutputAvailable(m_outputCodec->toUnicode(
data.constData(), data.length(), &m_outputCodecState));
}
// called asyncronously as response to Gdb stdout output in
// gdbResponseAvailable()
void GdbEngine::handleResponse()
@@ -426,22 +416,6 @@ void GdbEngine::handleResponse()
break;
}
if (token == -1 && *from != '&' && *from != '~' && *from != '*') {
// FIXME: On Linux the application's std::out is merged in here.
// High risk of falsely interpreting this as MI output.
// We assume that we _always_ use tokens, so not finding a token
// is a positive indication for the presence of application output.
QString s;
while (from != to && *from != '\n')
s += *from++;
//qDebug() << "UNREQUESTED DATA " << s << " TAKEN AS APPLICATION OUTPUT";
//s += '\n';
m_inbuffer = QByteArray(from, to - from);
emit applicationOutputAvailable("app-stdout: ", s);
continue;
}
// next char decides kind of record
const char c = *from++;
//qDebug() << "CODE:" << c;
@@ -609,8 +583,7 @@ static void fixMac(QByteArray &out)
void GdbEngine::readGdbStandardError()
{
QByteArray err = m_gdbProc.readAllStandardError();
emit applicationOutputAvailable("app-stderr:", err);
qWarning() << "Unexpected gdb stderr:" << m_gdbProc.readAllStandardError();
}
void GdbEngine::readGdbStandardOutput()
@@ -1097,7 +1070,7 @@ void GdbEngine::handleStreamOutput(const QString &data, char code)
// On Windows, the contents seem to depend on the debugger
// version and/or OS version used.
if (data.startsWith("warning:"))
qq->showApplicationOutput(QString(), data);
qq->showApplicationOutput(data);
break;
}
@@ -1503,7 +1476,8 @@ void GdbEngine::exitDebugger()
m_varToType.clear();
m_dataDumperState = DataDumperUninitialized;
m_shared = 0;
qq->debugDumpersAction()->setChecked(false);
m_outputCollector.shutdown();
//q->settings()->m_debugDumpers = false;
}
@@ -1525,6 +1499,15 @@ bool GdbEngine::startDebugger()
return false;
}
if (!m_outputCollector.listen()) {
QMessageBox::critical(q->mainWindow(), tr("Debugger Startup Failure"),
tr("Cannot set up communication with child process: %1")
.arg(m_outputCollector.errorString()));
return false;
}
gdbArgs.prepend(QLatin1String("--tty=") + m_outputCollector.serverName());
//gdbArgs.prepend(QLatin1String("--quiet"));
gdbArgs.prepend(QLatin1String("mi"));
gdbArgs.prepend(QLatin1String("-i"));
@@ -1535,7 +1518,7 @@ bool GdbEngine::startDebugger()
m_gdbProc.setEnvironment(q->m_environment);
#if 0
qDebug() << "Command: " << theGdbSettings().m_gdbCmd;
qDebug() << "Command: " << q->settings()->m_gdbCmd;
qDebug() << "WorkingDirectory: " << m_gdbProc.workingDirectory();
qDebug() << "Environment: " << m_gdbProc.environment();
qDebug() << "Arguments: " << gdbArgs;
@@ -1544,13 +1527,17 @@ bool GdbEngine::startDebugger()
#endif
q->showStatusMessage(tr("Starting Debugger"));
emit gdbInputAvailable(QString(), theGdbSettings().m_gdbCmd + ' ' + gdbArgs.join(" "));
emit gdbInputAvailable(QString(), q->settings()->m_gdbCmd + ' ' + gdbArgs.join(" "));
m_gdbProc.start(theGdbSettings().m_gdbCmd, gdbArgs);
m_gdbProc.start(q->settings()->m_gdbCmd, gdbArgs);
m_gdbProc.waitForStarted();
if (m_gdbProc.state() != QProcess::Running)
if (m_gdbProc.state() != QProcess::Running) {
QMessageBox::critical(q->mainWindow(), tr("Debugger Startup Failure"),
tr("Cannot start debugger: %1").arg(m_gdbProc.errorString()));
m_outputCollector.shutdown();
return false;
}
q->showStatusMessage(tr("Gdb Running"));
@@ -2589,7 +2576,7 @@ void GdbEngine::setToolTipExpression(const QPoint &pos, const QString &exp0)
return;
}
if (qq->debugDumpersAction()->isChecked()) {
if (q->settings()->m_debugDumpers) {
// minimize interference
return;
}
@@ -2909,10 +2896,10 @@ void GdbEngine::setCustomDumpersWanted(bool on)
bool GdbEngine::isCustomValueDumperAvailable(const QString &type) const
{
if (!qq->useCustomDumpers())
DebuggerSettings *s = q->settings();
if (!s->m_useCustomDumpers)
return false;
if (qq->debugDumpersAction()->isChecked()
&& qq->stackHandler()->isDebuggingDumpers())
if (s->m_debugDumpers && qq->stackHandler()->isDebuggingDumpers())
return false;
if (m_dataDumperState != DataDumperAvailable)
return false;
@@ -3470,7 +3457,7 @@ void GdbEngine::handleDumpCustomValue1(const GdbResultRecord &record,
//qDebug() << "CUSTOM DUMPER ERROR MESSAGE: " << msg;
#ifdef QT_DEBUG
// Make debugging of dumers easier
if (qq->debugDumpersAction()->isChecked()
if (q->settings()->m_debugDumpers
&& msg.startsWith("The program being debugged stopped while")
&& msg.contains("qDumpObjectData440")) {
// Fake full stop

View File

@@ -36,6 +36,7 @@
#include "idebuggerengine.h"
#include "gdbmi.h"
#include "outputcollector.h"
#include <QtCore/QByteArray>
#include <QtCore/QHash>
@@ -43,6 +44,7 @@
#include <QtCore/QObject>
#include <QtCore/QProcess>
#include <QtCore/QPoint>
#include <QtCore/QTextCodec>
#include <QtCore/QVariant>
QT_BEGIN_NAMESPACE
@@ -81,23 +83,6 @@ enum DataDumperState
};
class GdbSettings
{
public:
GdbSettings() { m_autoRun = m_autoQuit = false; }
public:
QString m_gdbCmd;
QString m_gdbEnv;
bool m_autoRun;
bool m_autoQuit;
QString m_scriptFile;
QMap<QString, QVariant> m_typeMacros;
};
GdbSettings &theGdbSettings();
class GdbEngine : public IDebuggerEngine
{
Q_OBJECT
@@ -110,7 +95,7 @@ signals:
void gdbResponseAvailable();
void gdbInputAvailable(const QString &prefix, const QString &msg);
void gdbOutputAvailable(const QString &prefix, const QString &msg);
void applicationOutputAvailable(const QString &prefix, const QString &msg);
void applicationOutputAvailable(const QString &output);
private:
//
@@ -190,6 +175,7 @@ private slots:
void gdbProcError(QProcess::ProcessError error);
void readGdbStandardOutput();
void readGdbStandardError();
void readDebugeeOutput(const QByteArray &data);
private:
int terminationIndex(const QByteArray &buffer, int &length);
@@ -207,6 +193,10 @@ private:
void handleQueryPwd(const GdbResultRecord &response);
void handleQuerySources(const GdbResultRecord &response);
OutputCollector m_outputCollector;
QTextCodec *m_outputCodec;
QTextCodec::ConverterState m_outputCodecState;
QByteArray m_inbuffer;
QProcess m_gdbProc;

View File

@@ -1,145 +0,0 @@
/***************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Qt Software Information (qt-info@nokia.com)
**
**
** Non-Open Source Usage
**
** Licensees may use this file in accordance with the Qt Beta Version
** License Agreement, Agreement version 2.2 provided with the Software or,
** alternatively, in accordance with the terms contained in a written
** agreement between you and Nokia.
**
** GNU General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU General
** Public License versions 2.0 or 3.0 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the packaging
** of this file. Please review the following information to ensure GNU
** General Public Licensing requirements will be met:
**
** http://www.fsf.org/licensing/licenses/info/GPLv2.html and
** http://www.gnu.org/copyleft/gpl.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt GPL Exception
** version 1.3, included in the file GPL_EXCEPTION.txt in this package.
**
***************************************************************************/
#include "gdboptionpage.h"
#include "gdbengine.h"
#include <extensionsystem/pluginmanager.h>
#include <coreplugin/icore.h>
#include <QtCore/QSettings>
#include <QtGui/QLineEdit>
#include <QtGui/QFileDialog>
using namespace Debugger::Internal;
GdbOptionPage::GdbOptionPage(GdbSettings *settings)
{
m_pm = ExtensionSystem::PluginManager::instance();
m_settings = settings;
Core::ICore *coreIFace = m_pm->getObject<Core::ICore>();
if (!coreIFace || !coreIFace->settings())
return;
QSettings *s = coreIFace->settings();
s->beginGroup("GdbOptions");
QString defaultCommand("gdb");
#if defined(Q_OS_WIN32)
defaultCommand.append(".exe");
#endif
QString defaultScript = coreIFace->resourcePath() +
QLatin1String("/gdb/qt4macros");
m_settings->m_gdbCmd = s->value("Location", defaultCommand).toString();
m_settings->m_scriptFile= s->value("ScriptFile", defaultScript).toString();
m_settings->m_gdbEnv = s->value("Environment", "").toString();
m_settings->m_autoRun = s->value("AutoRun", true).toBool();
m_settings->m_autoQuit = s->value("AutoQuit", true).toBool();
s->endGroup();
}
QString GdbOptionPage::name() const
{
return tr("Gdb");
}
QString GdbOptionPage::category() const
{
return "Debugger";
}
QString GdbOptionPage::trCategory() const
{
return tr("Debugger");
}
QWidget *GdbOptionPage::createPage(QWidget *parent)
{
QWidget *w = new QWidget(parent);
m_ui.setupUi(w);
m_ui.gdbLocationChooser->setExpectedKind(Core::Utils::PathChooser::Command);
m_ui.gdbLocationChooser->setPromptDialogTitle(tr("Choose Gdb Location"));
m_ui.gdbLocationChooser->setPath(m_settings->m_gdbCmd);
m_ui.scriptFileChooser->setExpectedKind(Core::Utils::PathChooser::File);
m_ui.scriptFileChooser->setPromptDialogTitle(tr("Choose Location of Startup Script File"));
m_ui.scriptFileChooser->setPath(m_settings->m_scriptFile);
m_ui.environmentEdit->setText(m_settings->m_gdbEnv);
m_ui.autoStartBox->setChecked(m_settings->m_autoRun);
m_ui.autoQuitBox->setChecked(m_settings->m_autoQuit);
// FIXME
m_ui.autoStartBox->hide();
m_ui.autoQuitBox->hide();
m_ui.environmentEdit->hide();
m_ui.labelEnvironment->hide();
connect(m_ui.gdbLocationChooser, SIGNAL(changed()),
this, SLOT(onGdbLocationChanged()));
connect(m_ui.scriptFileChooser, SIGNAL(changed()),
this, SLOT(onScriptFileChanged()));
return w;
}
void GdbOptionPage::onGdbLocationChanged()
{
m_settings->m_gdbCmd = m_ui.gdbLocationChooser->path();
}
void GdbOptionPage::onScriptFileChanged()
{
m_settings->m_scriptFile = m_ui.scriptFileChooser->path();
}
void GdbOptionPage::apply()
{
m_settings->m_gdbCmd = m_ui.gdbLocationChooser->path();
m_settings->m_gdbEnv = m_ui.environmentEdit->text();
m_settings->m_autoRun = m_ui.autoStartBox->isChecked();
m_settings->m_autoQuit = m_ui.autoQuitBox->isChecked();
m_settings->m_scriptFile = m_ui.scriptFileChooser->path();
Core::ICore *coreIFace = m_pm->getObject<Core::ICore>();
if (!coreIFace || !coreIFace->settings())
return;
QSettings *s = coreIFace->settings();
s->beginGroup("GdbOptions");
s->setValue("Location", m_settings->m_gdbCmd);
s->setValue("Environment", m_settings->m_gdbEnv);
s->setValue("AutoRun", m_settings->m_autoRun);
s->setValue("AutoQuit", m_settings->m_autoQuit);
s->endGroup();
}

View File

@@ -6,8 +6,8 @@
<rect>
<x>0</x>
<y>0</y>
<width>433</width>
<height>233</height>
<width>465</width>
<height>372</height>
</rect>
</property>
<property name="windowTitle">
@@ -36,7 +36,7 @@
<widget class="QLineEdit" name="environmentEdit"/>
</item>
<item row="0" column="0">
<widget class="QLabel" name="labelGdbLocaltion">
<widget class="QLabel" name="labelGdbLocation">
<property name="toolTip">
<string>This is either a full abolute path leading to the gdb binary you intend to use or the name of a gdb binary that wiull be searched in your PATH.</string>
</property>
@@ -74,6 +74,58 @@
</layout>
</widget>
</item>
<item>
<widget class="QCheckBox" name="checkBoxUseCustomDumpers">
<property name="toolTip">
<string>Checking this will make the debugger try to use code to format certain data (QObject, QString, std::string etc.) nicely.</string>
</property>
<property name="text">
<string>Use custom display for Qt and Standard Library objects</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="checkBoxFastStart">
<property name="toolTip">
<string>Checking this will make the debugger start fast by loading only very few debug symbols on start up. This might lead to situations where breakpoints can not be set properly. So uncheck this option if you experience breakpoint related problems.</string>
</property>
<property name="text">
<string>Fast debugger start</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="checkBoxSkipKnownFrames">
<property name="toolTip">
<string>fter checking this option 'Step Into' combines in certain situations several steps, leading to 'less noisy' debugging. So will, e.g., the atomic
reference counting code be skipped, and a single 'Step Into' for a signal emission will end up directly in the slot connected to it.
</string>
</property>
<property name="text">
<string>Skip known frames when stepping</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="checkBoxUseToolTips">
<property name="toolTip">
<string>Checking this will make enable tooltips for variable values during debugging. Since this can slow down debugging and does not provide reliable information as it does not use scope information, it is switched off by default.</string>
</property>
<property name="text">
<string>Use tooltips while debugging</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="checkBoxDebugDumpers">
<property name="toolTip">
<string notr="true">This is an internal tool to make debugging the Custom Data Dumper code easier. Using this action is in general not needed unless you want do debug Qt Creator itself.</string>
</property>
<property name="text">
<string>Debug Custom Dumpers</string>
</property>
</widget>
</item>
<item>
<widget class="QCheckBox" name="autoStartBox">
<property name="text">

View File

@@ -0,0 +1,180 @@
/***************************************************************************
**
** This file is part of Qt Creator
**
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Qt Software Information (qt-info@nokia.com)
**
**
** Non-Open Source Usage
**
** Licensees may use this file in accordance with the Qt Beta Version
** License Agreement, Agreement version 2.2 provided with the Software or,
** alternatively, in accordance with the terms contained in a written
** agreement between you and Nokia.
**
** GNU General Public License Usage
**
** Alternatively, this file may be used under the terms of the GNU General
** Public License versions 2.0 or 3.0 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the packaging
** of this file. Please review the following information to ensure GNU
** General Public Licensing requirements will be met:
**
** http://www.fsf.org/licensing/licenses/info/GPLv2.html and
** http://www.gnu.org/copyleft/gpl.html.
**
** In addition, as a special exception, Nokia gives you certain additional
** rights. These rights are described in the Nokia Qt GPL Exception
** version 1.3, included in the file GPL_EXCEPTION.txt in this package.
**
***************************************************************************/
#include "outputcollector.h"
#ifdef Q_OS_WIN
#include <QtNetwork/QLocalServer>
#include <QtNetwork/QLocalSocket>
#include <QtCore/QCoreApplication>
#else
#include <QtCore/QFile>
#include <QtCore/QSocketNotifier>
#include <QtCore/QTemporaryFile>
#include <QtCore/QVarLengthArray>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <errno.h>
#include <fcntl.h>
#include <string.h>
#include <unistd.h>
#endif
namespace Debugger {
namespace Internal {
OutputCollector::OutputCollector(QObject *parent)
: QObject(parent)
{
#ifdef Q_OS_WIN
m_server = 0;
m_socket = 0;
#endif
}
OutputCollector::~OutputCollector()
{
shutdown();
}
bool OutputCollector::listen()
{
#ifdef Q_OS_WIN
if (m_server)
return m_server->isListening();
m_server = new QLocalServer(this);
connect(m_server, SIGNAL(newConnection()), SLOT(newConnectionAvailable()));
return m_server->listen(QLatin1String("creator-") + QCoreApplication::applicationPid()); // XXX how to make that secure?
#else
if (!m_serverPath.isEmpty())
return true;
QByteArray codedServerPath;
forever {
{
QTemporaryFile tf;
if (!tf.open()) {
m_errorString = tr("Cannot create temporary file: %2").arg(tf.errorString());
m_serverPath.clear();
return false;
}
m_serverPath = tf.fileName();
}
// By now the temp file was deleted again
codedServerPath = QFile::encodeName(m_serverPath);
if (!::mkfifo(codedServerPath.constData(), 0600))
break;
if (errno != EEXIST) {
m_errorString = tr("Cannot create FiFo %1: %2").arg(m_serverPath, strerror(errno));
m_serverPath.clear();
return false;
}
}
if ((m_serverFd = ::open(codedServerPath.constData(), O_RDONLY|O_NONBLOCK)) < 0) {
m_errorString = tr("Cannot open FiFo %1: %2").arg(m_serverPath, strerror(errno));
m_serverPath.clear();
return false;
}
m_serverNotifier = new QSocketNotifier(m_serverFd, QSocketNotifier::Read, this);
connect(m_serverNotifier, SIGNAL(activated(int)), SLOT(bytesAvailable()));
return true;
#endif
}
void OutputCollector::shutdown()
{
#ifdef Q_OS_WIN
delete m_server; // Deletes socket as well (QObject parent)
m_server = 0;
m_socket = 0;
#else
if (!m_serverPath.isEmpty()) {
::close(m_serverFd);
::unlink(QFile::encodeName(m_serverPath).constData());
delete m_serverNotifier;
m_serverPath.clear();
}
#endif
}
QString OutputCollector::errorString() const
{
#ifdef Q_OS_WIN
return m_socket ? m_socket->errorString() : m_server->errorString();
#else
return m_errorString;
#endif
}
QString OutputCollector::serverName() const
{
#ifdef Q_OS_WIN
return m_server->fullServerName();
#else
return m_serverPath;
#endif
}
#ifdef Q_OS_WIN
void OutputCollector::newConnectionAvailable()
{
if (m_socket)
return;
m_socket = m_server->nextPendingConnection();
connect(m_socket, SIGNAL(bytesAvailable()), SLOT(bytesAvailable()));
}
#endif
void OutputCollector::bytesAvailable()
{
#ifdef Q_OS_WIN
emit byteDelivery(m_socket->readAll());
#else
size_t nbytes = 0;
if (::ioctl(m_serverFd, FIONREAD, (char *) &nbytes) < 0)
return;
QVarLengthArray<char, 8192> buff(nbytes);
if (::read(m_serverFd, buff.data(), nbytes) != (int)nbytes)
return;
if (nbytes) // Skip EOF notifications
emit byteDelivery(QByteArray::fromRawData(buff.data(), nbytes));
#endif
}
} // namespace Internal
} // namespace Debugger

View File

@@ -2,7 +2,7 @@
**
** This file is part of Qt Creator
**
** Copyright (c) 2008-2009 Nokia Corporation and/or its subsidiary(-ies).
** Copyright (c) 2009 Nokia Corporation and/or its subsidiary(-ies).
**
** Contact: Qt Software Information (qt-info@nokia.com)
**
@@ -31,79 +31,61 @@
**
***************************************************************************/
#ifndef GDBOPTIONPAGE_H
#define GDBOPTIONPAGE_H
#ifndef OUTPUT_COLLECTOR_H
#define OUTPUT_COLLECTOR_H
#include "ui_gdboptionpage.h"
#include <QtCore/QByteArray>
#include <QtCore/QObject>
#include <coreplugin/dialogs/ioptionspage.h>
#include <QtGui/QWidget>
namespace ExtensionSystem { class PluginManager; }
QT_BEGIN_NAMESPACE
class QLocalServer;
class QLocalSocket;
class QSocketNotifier;
QT_END_NAMESPACE
namespace Debugger {
namespace Internal {
class GdbSettings;
///////////////////////////////////////////////////////////////////////
//
// OutputCollector
//
///////////////////////////////////////////////////////////////////////
class GdbOptionPage : public Core::IOptionsPage
class OutputCollector : public QObject
{
Q_OBJECT
public:
GdbOptionPage(GdbSettings *settings);
OutputCollector(QObject *parent = 0);
~OutputCollector();
bool listen();
void shutdown();
QString serverName() const;
QString errorString() const;
QString name() const;
QString category() const;
QString trCategory() const;
QWidget *createPage(QWidget *parent);
void apply();
void finish() { }
public slots:
void onGdbLocationChanged();
void onScriptFileChanged();
private:
ExtensionSystem::PluginManager *m_pm;
Ui::GdbOptionPage m_ui;
GdbSettings *m_settings;
};
#if 0
class TypeMacroPage : public Core::IOptionsPage
{
Q_OBJECT
public:
TypeMacroPage(GdbSettings *settings);
QString name() const;
QString category() const;
QString trCategory() const;
QWidget *createPage(QWidget *parent);
void finished(bool accepted);
signals:
void byteDelivery(const QByteArray &data);
private slots:
void onAddButton();
void onDelButton();
void currentItemChanged(QTreeWidgetItem *item);
void updateButtonState();
void bytesAvailable();
#ifdef Q_OS_WIN
void newConnectionAvailable();
#endif
private:
ExtensionSystem::PluginManager *m_pm;
Ui::TypeMacroPage m_ui;
GdbSettings *m_settings;
QWidget *m_widget;
};
#ifdef Q_OS_WIN
QLocalServer *m_server;
QLocalSocket *m_socket;
#else
QString m_serverPath;
int m_serverFd;
QSocketNotifier *m_serverNotifier;
QString m_errorString;
#endif
};
} // namespace Internal
} // namespace Debugger
#endif // GDBOPTIONPAGE_H
#endif // OUTPUT_COLLECTOR_H

View File

@@ -35,6 +35,13 @@
#include "fakevimconstants.h"
// Please do not add any direct dependencies to other Qt Creator code here.
// Instead emit signals and let the FakeVimPlugin channel the information to
// Qt Creator. The idea is to keep this file here in a "clean" state that
// allows easy reuse with any QTextEdit or QPlainTextEdit derived class.
//#include <indenter.h>
#include <QtCore/QDebug>
#include <QtCore/QFile>
#include <QtCore/QObject>
@@ -53,11 +60,6 @@
#include <QtGui/QTextDocumentFragment>
#include <QtGui/QTextEdit>
//#include <texteditor/basetexteditor.h>
//#include <texteditor/textblockiterator.h>
//#include <cppeditor/cppeditor.h>
//#include <indenter.h>
using namespace FakeVim::Internal;
using namespace FakeVim::Constants;
@@ -724,7 +726,7 @@ bool FakeVimHandler::Private::handleCommandMode(int key, const QString &text)
} else if (key == 'G') {
int n = m_mvcount.isEmpty() ? linesInDocument() : count();
m_tc.setPosition(positionForLine(n), KeepAnchor);
if (m_config.contains(ConfigStartOfLine))
if (m_config[ConfigStartOfLine] == ConfigOn)
moveToFirstNonBlankOnLine();
finishMovement();
} else if (key == 'h' || key == Key_Left) {
@@ -1192,10 +1194,9 @@ void FakeVimHandler::Private::handleExCommand(const QString &cmd0)
showRedMessage(tr("File '%1' exists (add ! to override)").arg(fileName));
} else if (file.open(QIODevice::ReadWrite)) {
QTextCursor tc = selectRange(beginLine, endLine);
qDebug() << "ANCHOR: " << tc.position() << tc.anchor()
<< tc.selection().toPlainText();
{ QTextStream ts(&file); ts << tc.selection().toPlainText(); }
file.close();
QString contents = tc.selection().toPlainText();
emit q->writeFile(fileName, contents);
// check by reading back
file.open(QIODevice::ReadOnly);
QByteArray ba = file.readAll();
showBlackMessage(tr("\"%1\" %2 %3L, %4C written")
@@ -1813,3 +1814,8 @@ void FakeVimHandler::quit()
{
d->quit();
}
void FakeVimHandler::setCurrentFileName(const QString &fileName)
{
d->m_currentFileName = fileName;
}

View File

@@ -58,6 +58,7 @@ public slots:
// FIXME: good idea?
void addWidget(QWidget *widget);
void removeWidget(QWidget *widget);
void setCurrentFileName(const QString &fileName);
// This executes an "ex" style command taking context
// information from \p widget;
@@ -72,6 +73,7 @@ signals:
void quitRequested(QWidget *);
void selectionChanged(QWidget *widget,
const QList<QTextEdit::ExtraSelection> &selection);
void writeFile(const QString &fileName, const QString &contents);
private:
bool eventFilter(QObject *ob, QEvent *ev);

View File

@@ -39,7 +39,9 @@
#include <coreplugin/actionmanager/actionmanager.h>
#include <coreplugin/coreconstants.h>
#include <coreplugin/editormanager/editormanager.h>
#include <coreplugin/filemanager.h>
#include <coreplugin/icore.h>
#include <coreplugin/ifile.h>
#include <coreplugin/messagemanager.h>
#include <coreplugin/modemanager.h>
#include <coreplugin/uniqueidmanager.h>
@@ -117,12 +119,14 @@ private slots:
void editorAboutToClose(Core::IEditor *);
void changeSelection(QWidget *widget,
const QList<QTextEdit::ExtraSelection> &selections);
void writeFile(const QString &fileName, const QString &contents);
private:
FakeVimPlugin *q;
FakeVimHandler *m_handler;
QAction *m_installHandlerAction;
Core::ICore *m_core;
Core::IFile *m_currentFile;
};
} // namespace Internal
@@ -134,6 +138,7 @@ FakeVimPluginPrivate::FakeVimPluginPrivate(FakeVimPlugin *plugin)
m_handler = 0;
m_installHandlerAction = 0;
m_core = 0;
m_currentFile = 0;
}
FakeVimPluginPrivate::~FakeVimPluginPrivate()
@@ -206,6 +211,12 @@ void FakeVimPluginPrivate::installHandler(QWidget *widget)
this, SLOT(changeSelection(QWidget*,QList<QTextEdit::ExtraSelection>)));
m_handler->addWidget(widget);
TextEditor::BaseTextEditor* editor =
qobject_cast<TextEditor::BaseTextEditor*>(widget);
if (editor) {
m_currentFile = editor->file();
m_handler->setCurrentFileName(editor->file()->fileName());
}
BaseTextEditor *bt = qobject_cast<BaseTextEditor *>(widget);
if (bt) {
@@ -225,12 +236,29 @@ void FakeVimPluginPrivate::installHandler(QWidget *widget)
}
}
void FakeVimPluginPrivate::writeFile(const QString &fileName,
const QString &contents)
{
if (m_currentFile && fileName == m_currentFile->fileName()) {
// Handle that as a special case for nicer interaction with core
m_core->fileManager()->blockFileChange(m_currentFile);
m_currentFile->save(fileName);
m_core->fileManager()->unblockFileChange(m_currentFile);
} else {
QFile file(fileName);
file.open(QIODevice::ReadWrite);
{ QTextStream ts(&file); ts << contents; }
file.close();
}
}
void FakeVimPluginPrivate::removeHandler(QWidget *widget)
{
Q_UNUSED(widget);
m_handler->removeWidget(widget);
Core::EditorManager::instance()->hideEditorInfoBar(
QLatin1String(Constants::MINI_BUFFER));
m_currentFile = 0;
}
void FakeVimPluginPrivate::editorOpened(Core::IEditor *editor)

View File

@@ -37,6 +37,9 @@
#include <QtCore/QObject>
#include <QtCore/QStringList>
#include <QtCore/QProcess>
#ifndef Q_OS_WIN
#include <QtCore/QTextCodec>
#endif
namespace ProjectExplorer {
namespace Internal {
@@ -88,7 +91,12 @@ private:
ConsoleProcess *m_consoleProcess;
Mode m_currentMode;
#ifdef Q_OS_WIN
WinGuiProcess *m_winGuiProcess;
#else
QTextCodec *m_outputCodec;
QTextCodec::ConverterState m_outputCodecState;
#endif
};
} // namespace Internal

View File

@@ -116,10 +116,7 @@ qint64 ApplicationLauncher::applicationPID() const
void ApplicationLauncher::readWinDebugOutput(const QString &output)
{
QString s = output;
if (s.endsWith(QLatin1Char('\n')))
s.chop(1);
emit appendOutput(s);
emit appendOutput(output);
}
void ApplicationLauncher::processStopped()

View File

@@ -41,6 +41,7 @@ using namespace ProjectExplorer::Internal;
ApplicationLauncher::ApplicationLauncher(QObject *parent)
: QObject(parent)
{
m_outputCodec = QTextCodec::codecForLocale();
m_currentMode = Gui;
m_guiProcess = new QProcess(this);
m_guiProcess->setReadChannelMode(QProcess::MergedChannels);
@@ -132,13 +133,9 @@ void ApplicationLauncher::guiProcessError()
void ApplicationLauncher::readStandardOutput()
{
m_guiProcess->setReadChannel(QProcess::StandardOutput);
while (m_guiProcess->canReadLine()) {
QString line = QString::fromLocal8Bit(m_guiProcess->readLine());
if (line.endsWith(QLatin1Char('\n')))
line.chop(1);
emit appendOutput(line);
}
QByteArray data = m_guiProcess->readAllStandardOutput();
emit appendOutput(m_outputCodec->toUnicode(
data.constData(), data.length(), &m_outputCodecState));
}
void ApplicationLauncher::processStopped()

View File

@@ -141,7 +141,7 @@ void ApplicationRunControl::start()
m_executable, rc->commandLineArguments());
emit started();
emit addToOutputWindow(this, tr("Starting %1").arg(m_executable));
emit addToOutputWindow(this, tr("Starting %1...").arg(m_executable));
}
void ApplicationRunControl::stop()
@@ -162,7 +162,7 @@ void ApplicationRunControl::slotError(const QString & err)
void ApplicationRunControl::slotAddToOutputWindow(const QString &line)
{
emit addToOutputWindow(this, Qt::escape(line));
emit addToOutputWindowInline(this, line);
}
void ApplicationRunControl::processExited(int exitCode)

View File

@@ -215,6 +215,12 @@ void OutputPane::appendOutput(RunControl *rc, const QString &out)
ow->appendOutput(out);
}
void OutputPane::appendOutputInline(RunControl *rc, const QString &out)
{
OutputWindow *ow = m_outputWindows.value(rc);
ow->appendOutputInline(out);
}
void OutputPane::showTabFor(RunControl *rc)
{
OutputWindow *ow = m_outputWindows.value(rc);
@@ -318,7 +324,16 @@ OutputWindow::~OutputWindow()
void OutputWindow::appendOutput(const QString &out)
{
appendPlainText(out);
if (out.endsWith('\n'))
appendPlainText(out);
else
appendPlainText(out + '\n');
}
void OutputWindow::appendOutputInline(const QString &out)
{
moveCursor(QTextCursor::End);
insertPlainText(out);
}
void OutputWindow::insertLine()

View File

@@ -83,6 +83,7 @@ public:
// ApplicationOutputspecifics
void createNewOutputWindow(RunControl *rc);
void appendOutput(RunControl *rc, const QString &out);
void appendOutputInline(RunControl *rc, const QString &out);
void showTabFor(RunControl *rc);
public slots:
@@ -119,6 +120,7 @@ public:
~OutputWindow();
void appendOutput(const QString &out);
void appendOutputInline(const QString &out);
void insertLine();
};

View File

@@ -1084,6 +1084,8 @@ void ProjectExplorerPlugin::buildQueueFinished(bool success)
connect(control, SIGNAL(addToOutputWindow(RunControl *, const QString &)),
this, SLOT(addToApplicationOutputWindow(RunControl *, const QString &)));
connect(control, SIGNAL(addToOutputWindowInline(RunControl *, const QString &)),
this, SLOT(addToApplicationOutputWindowInline(RunControl *, const QString &)));
connect(control, SIGNAL(error(RunControl *, const QString &)),
this, SLOT(addErrorToApplicationOutputWindow(RunControl *, const QString &)));
connect(control, SIGNAL(finished()),
@@ -1379,6 +1381,11 @@ void ProjectExplorerPlugin::addToApplicationOutputWindow(RunControl *rc, const Q
m_outputPane->appendOutput(rc, line);
}
void ProjectExplorerPlugin::addToApplicationOutputWindowInline(RunControl *rc, const QString &line)
{
m_outputPane->appendOutputInline(rc, line);
}
void ProjectExplorerPlugin::addErrorToApplicationOutputWindow(RunControl *rc, const QString &error)
{
m_outputPane->appendOutput(rc, error);

View File

@@ -180,6 +180,7 @@ private slots:
void updateRunAction();
void addToApplicationOutputWindow(RunControl *, const QString &line);
void addToApplicationOutputWindowInline(RunControl *, const QString &line);
void addErrorToApplicationOutputWindow(RunControl *, const QString &error);
void updateTaskActions();

View File

@@ -143,6 +143,7 @@ public:
QSharedPointer<RunConfiguration> runConfiguration();
signals:
void addToOutputWindow(RunControl *, const QString &line);
void addToOutputWindowInline(RunControl *, const QString &line);
void error(RunControl *, const QString &error);
void started();
void finished();

View File

@@ -491,7 +491,7 @@ public:
class InfoItemModulesTest : public SPEInfoItem
{
public:
InfoItemModulesTest(): SPEInfoItem("qtestlib", QtModule)
InfoItemModulesTest(): SPEInfoItem("testlib", QtModule)
{
m_data.insert(keyIncludedByDefault, false);
}