2009-02-25 09:15:00 +01:00
|
|
|
/**************************************************************************
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
|
|
|
|
** This file is part of Qt Creator
|
|
|
|
|
**
|
2010-03-05 11:25:49 +01:00
|
|
|
** Copyright (c) 2010 Nokia Corporation and/or its subsidiary(-ies).
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2009-06-17 00:01:27 +10:00
|
|
|
** Contact: Nokia Corporation (qt-info@nokia.com)
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2010-12-17 16:01:08 +01:00
|
|
|
** No Commercial Usage
|
2008-12-02 14:17:16 +01:00
|
|
|
**
|
2010-12-17 16:01:08 +01:00
|
|
|
** This file contains pre-release code and may not be distributed.
|
|
|
|
|
** You may use this file in accordance with the terms and conditions
|
|
|
|
|
** contained in the Technology Preview License Agreement accompanying
|
|
|
|
|
** this package.
|
2008-12-02 14:17:16 +01:00
|
|
|
**
|
2009-02-25 09:15:00 +01:00
|
|
|
** GNU Lesser General Public License Usage
|
2008-12-02 14:17:16 +01:00
|
|
|
**
|
2009-02-25 09:15:00 +01:00
|
|
|
** Alternatively, this file may be used under the terms of the GNU Lesser
|
|
|
|
|
** General Public License version 2.1 as published by the Free Software
|
|
|
|
|
** Foundation and appearing in the file LICENSE.LGPL included in the
|
|
|
|
|
** packaging of this file. Please review the following information to
|
|
|
|
|
** ensure the GNU Lesser General Public License version 2.1 requirements
|
|
|
|
|
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
|
2008-12-02 14:17:16 +01:00
|
|
|
**
|
2010-12-17 16:01:08 +01:00
|
|
|
** In addition, as a special exception, Nokia gives you certain additional
|
|
|
|
|
** rights. These rights are described in the Nokia Qt LGPL Exception
|
|
|
|
|
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
|
|
|
|
|
**
|
|
|
|
|
** If you have questions regarding the use of this file, please contact
|
|
|
|
|
** Nokia at qt-info@nokia.com.
|
2008-12-02 12:01:29 +01:00
|
|
|
**
|
2009-02-25 09:15:00 +01:00
|
|
|
**************************************************************************/
|
2008-12-02 15:08:31 +01:00
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
#include "breakwindow.h"
|
2010-10-25 14:00:19 +02:00
|
|
|
#include "breakhandler.h"
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2009-03-18 09:03:47 +01:00
|
|
|
#include "debuggeractions.h"
|
2010-11-10 11:39:01 +01:00
|
|
|
#include "debuggercore.h"
|
2010-09-21 16:32:43 +02:00
|
|
|
#include "ui_breakpoint.h"
|
2008-12-02 12:01:29 +01:00
|
|
|
#include "ui_breakcondition.h"
|
|
|
|
|
|
2010-09-28 14:07:23 +02:00
|
|
|
#include <utils/pathchooser.h>
|
2009-06-11 13:40:44 +02:00
|
|
|
#include <utils/qtcassert.h>
|
2010-03-18 10:59:06 +01:00
|
|
|
#include <utils/savedaction.h>
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2009-05-05 10:14:35 +02:00
|
|
|
#include <QtCore/QDebug>
|
|
|
|
|
|
|
|
|
|
#include <QtGui/QAction>
|
|
|
|
|
#include <QtGui/QHeaderView>
|
2010-11-10 11:39:01 +01:00
|
|
|
#include <QtGui/QIntValidator>
|
|
|
|
|
#include <QtGui/QItemSelectionModel>
|
2009-05-05 10:14:35 +02:00
|
|
|
#include <QtGui/QKeyEvent>
|
|
|
|
|
#include <QtGui/QMenu>
|
|
|
|
|
#include <QtGui/QResizeEvent>
|
|
|
|
|
#include <QtGui/QToolButton>
|
|
|
|
|
#include <QtGui/QTreeView>
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
|
2010-06-16 11:08:54 +02:00
|
|
|
namespace Debugger {
|
|
|
|
|
namespace Internal {
|
2008-12-02 12:01:29 +01:00
|
|
|
|
2010-11-04 09:54:23 +01:00
|
|
|
|
2010-09-21 16:32:43 +02:00
|
|
|
///////////////////////////////////////////////////////////////////////
|
|
|
|
|
//
|
2010-11-16 11:42:20 +01:00
|
|
|
// BreakpointDialog: Show a dialog for editing breakpoints. Shows controls
|
|
|
|
|
// for the file-and-line, function and address parameters depending on the
|
|
|
|
|
// breakpoint type. The controls not applicable to the current type
|
|
|
|
|
// (say function name for file-and-line) are disabled and cleared out.
|
|
|
|
|
// However,the values are saved and restored once the respective mode
|
|
|
|
|
// is again choosen, which is done using m_savedParameters and
|
|
|
|
|
// setters/getters taking the parts mask enumeration parameter.
|
2010-09-21 16:32:43 +02:00
|
|
|
//
|
|
|
|
|
///////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
2010-11-16 11:42:20 +01:00
|
|
|
class BreakpointDialog : public QDialog
|
2010-09-21 16:32:43 +02:00
|
|
|
{
|
|
|
|
|
Q_OBJECT
|
|
|
|
|
public:
|
2010-10-04 16:00:25 +02:00
|
|
|
explicit BreakpointDialog(QWidget *parent);
|
2010-11-16 10:50:11 +01:00
|
|
|
bool showDialog(BreakpointParameters *data);
|
2010-09-21 16:32:43 +02:00
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
void setParameters(const BreakpointParameters &data);
|
2010-11-16 10:23:20 +01:00
|
|
|
BreakpointParameters parameters() const;
|
|
|
|
|
|
2010-09-21 16:32:43 +02:00
|
|
|
public slots:
|
2010-10-04 16:00:25 +02:00
|
|
|
void typeChanged(int index);
|
2010-11-16 10:23:20 +01:00
|
|
|
|
|
|
|
|
private:
|
2010-11-25 14:47:56 +01:00
|
|
|
enum DialogPart {
|
|
|
|
|
FileAndLinePart = 0x1,
|
|
|
|
|
FunctionPart = 0x2,
|
|
|
|
|
AddressPart = 0x4,
|
|
|
|
|
AllParts = FileAndLinePart|FunctionPart|AddressPart
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
void setPartsEnabled(unsigned partsMask, bool on);
|
2010-11-16 11:42:20 +01:00
|
|
|
void clearParts(unsigned partsMask);
|
2010-11-25 14:47:56 +01:00
|
|
|
void getParts(unsigned partsMask, BreakpointParameters *data) const;
|
|
|
|
|
void setParts(unsigned partsMask, const BreakpointParameters &data);
|
2010-11-16 11:42:20 +01:00
|
|
|
|
2010-11-16 10:23:20 +01:00
|
|
|
void setType(BreakpointType type);
|
|
|
|
|
BreakpointType type() const;
|
2010-11-16 11:42:20 +01:00
|
|
|
|
|
|
|
|
Ui::BreakpointDialog m_ui;
|
|
|
|
|
BreakpointParameters m_savedParameters;
|
|
|
|
|
BreakpointType m_previousType;
|
2010-09-21 16:32:43 +02:00
|
|
|
};
|
|
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
BreakpointDialog::BreakpointDialog(QWidget *parent)
|
|
|
|
|
: QDialog(parent), m_previousType(UnknownType)
|
2010-10-04 16:00:25 +02:00
|
|
|
{
|
2010-11-25 14:47:56 +01:00
|
|
|
// Match BreakpointType (omitting unknown type).
|
2010-11-16 11:42:20 +01:00
|
|
|
m_ui.setupUi(this);
|
2010-11-16 10:23:20 +01:00
|
|
|
QStringList types;
|
|
|
|
|
types << tr("File and Line Number") << tr("Function Name") << tr("Address")
|
|
|
|
|
<< tr("throw") << tr("catch") << tr("Function \"main()\"")
|
|
|
|
|
<< tr("Address (Watchpoint)");
|
|
|
|
|
QTC_ASSERT(types.size() == Watchpoint, return; )
|
2010-11-16 11:42:20 +01:00
|
|
|
m_ui.comboBoxType->addItems(types);
|
|
|
|
|
m_ui.pathChooserFileName->setExpectedKind(Utils::PathChooser::File);
|
|
|
|
|
connect(m_ui.comboBoxType, SIGNAL(activated(int)), SLOT(typeChanged(int)));
|
|
|
|
|
m_ui.lineEditIgnoreCount->setValidator(
|
|
|
|
|
new QIntValidator(0, 2147483647, m_ui.lineEditIgnoreCount));
|
2010-10-04 16:00:25 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-16 10:23:20 +01:00
|
|
|
void BreakpointDialog::setType(BreakpointType type)
|
|
|
|
|
{
|
2010-11-25 14:47:56 +01:00
|
|
|
const int comboIndex = type - 1; // Skip UnknownType.
|
2010-11-16 11:42:20 +01:00
|
|
|
if (comboIndex != m_ui.comboBoxType->currentIndex()) {
|
|
|
|
|
m_ui.comboBoxType->setCurrentIndex(comboIndex);
|
2010-11-16 10:23:20 +01:00
|
|
|
typeChanged(comboIndex);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
BreakpointType BreakpointDialog::type() const
|
2010-10-04 16:00:25 +02:00
|
|
|
{
|
2010-11-25 14:47:56 +01:00
|
|
|
const int type = m_ui.comboBoxType->currentIndex() + 1; // Skip unknown type.
|
2010-11-16 10:23:20 +01:00
|
|
|
return static_cast<BreakpointType>(type);
|
|
|
|
|
}
|
|
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
void BreakpointDialog::setParameters(const BreakpointParameters &data)
|
2010-11-16 10:23:20 +01:00
|
|
|
{
|
2010-11-25 14:47:56 +01:00
|
|
|
m_savedParameters = data;
|
|
|
|
|
setType(data.type);
|
|
|
|
|
setParts(AllParts, data);
|
|
|
|
|
m_ui.lineEditCondition->setText(QString::fromUtf8(data.condition));
|
|
|
|
|
m_ui.lineEditIgnoreCount->setText(QString::number(data.ignoreCount));
|
2010-12-14 13:00:02 +01:00
|
|
|
m_ui.lineEditThreadSpec->
|
|
|
|
|
setText(BreakHandler::displayFromThreadSpec(data.threadSpec));
|
2010-11-16 10:23:20 +01:00
|
|
|
}
|
2010-10-04 16:00:25 +02:00
|
|
|
|
2010-11-16 10:23:20 +01:00
|
|
|
BreakpointParameters BreakpointDialog::parameters() const
|
|
|
|
|
{
|
2010-11-25 14:47:56 +01:00
|
|
|
BreakpointParameters data(type());
|
|
|
|
|
getParts(AllParts, &data);
|
|
|
|
|
data.condition = m_ui.lineEditCondition->text().toUtf8();
|
|
|
|
|
data.ignoreCount = m_ui.lineEditIgnoreCount->text().toInt();
|
2010-12-14 13:00:02 +01:00
|
|
|
data.threadSpec =
|
|
|
|
|
BreakHandler::threadSpecFromDisplay(m_ui.lineEditThreadSpec->text());
|
2010-11-25 14:47:56 +01:00
|
|
|
return data;
|
2010-10-04 16:00:25 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-16 11:42:20 +01:00
|
|
|
void BreakpointDialog::setPartsEnabled(unsigned partsMask, bool e)
|
|
|
|
|
{
|
|
|
|
|
if (partsMask & FileAndLinePart) {
|
|
|
|
|
m_ui.labelFileName->setEnabled(e);
|
|
|
|
|
m_ui.pathChooserFileName->setEnabled(e);
|
|
|
|
|
m_ui.labelLineNumber->setEnabled(e);
|
|
|
|
|
m_ui.lineEditLineNumber->setEnabled(e);
|
|
|
|
|
m_ui.labelUseFullPath->setEnabled(e);
|
|
|
|
|
m_ui.checkBoxUseFullPath->setEnabled(e);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (partsMask & FunctionPart) {
|
|
|
|
|
m_ui.labelFunction->setEnabled(e);
|
|
|
|
|
m_ui.lineEditFunction->setEnabled(e);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (partsMask & AddressPart) {
|
|
|
|
|
m_ui.labelAddress->setEnabled(e);
|
|
|
|
|
m_ui.lineEditAddress->setEnabled(e);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void BreakpointDialog::clearParts(unsigned partsMask)
|
|
|
|
|
{
|
|
|
|
|
if (partsMask & FileAndLinePart) {
|
|
|
|
|
m_ui.pathChooserFileName->setPath(QString());
|
|
|
|
|
m_ui.lineEditLineNumber->clear();
|
|
|
|
|
m_ui.checkBoxUseFullPath->setChecked(false);
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (partsMask & FunctionPart)
|
|
|
|
|
m_ui.lineEditFunction->clear();
|
|
|
|
|
|
|
|
|
|
if (partsMask & AddressPart)
|
|
|
|
|
m_ui.lineEditAddress->clear();
|
|
|
|
|
}
|
|
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
void BreakpointDialog::getParts(unsigned partsMask, BreakpointParameters *data) const
|
2010-11-16 11:42:20 +01:00
|
|
|
{
|
2010-11-30 08:59:22 +01:00
|
|
|
data->enabled = m_ui.checkBoxEnabled->isChecked();
|
2010-12-16 13:02:59 +01:00
|
|
|
data->tracepoint = m_ui.checkBoxTracepoint->isChecked();
|
2010-11-30 08:59:22 +01:00
|
|
|
|
2010-11-16 11:42:20 +01:00
|
|
|
if (partsMask & FileAndLinePart) {
|
2010-11-25 14:47:56 +01:00
|
|
|
data->lineNumber = m_ui.lineEditLineNumber->text().toInt();
|
|
|
|
|
data->useFullPath = m_ui.checkBoxUseFullPath->isChecked();
|
|
|
|
|
data->fileName = m_ui.pathChooserFileName->path();
|
2010-11-16 11:42:20 +01:00
|
|
|
}
|
|
|
|
|
if (partsMask & FunctionPart)
|
2010-11-25 14:47:56 +01:00
|
|
|
data->functionName = m_ui.lineEditFunction->text();
|
2010-11-16 11:42:20 +01:00
|
|
|
|
|
|
|
|
if (partsMask & AddressPart)
|
2010-11-25 14:47:56 +01:00
|
|
|
data->address = m_ui.lineEditAddress->text().toULongLong(0, 0);
|
2010-11-16 11:42:20 +01:00
|
|
|
}
|
|
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
void BreakpointDialog::setParts(unsigned mask, const BreakpointParameters &data)
|
2010-11-16 11:42:20 +01:00
|
|
|
{
|
2010-11-30 08:59:22 +01:00
|
|
|
m_ui.checkBoxEnabled->setChecked(data.enabled);
|
2010-12-16 13:02:59 +01:00
|
|
|
m_ui.checkBoxUseFullPath->setChecked(data.useFullPath);
|
2010-11-30 08:59:22 +01:00
|
|
|
|
2010-11-16 11:42:20 +01:00
|
|
|
if (mask & FileAndLinePart) {
|
2010-11-25 14:47:56 +01:00
|
|
|
m_ui.pathChooserFileName->setPath(data.fileName);
|
|
|
|
|
m_ui.lineEditLineNumber->setText(QString::number(data.lineNumber));
|
2010-12-16 13:02:59 +01:00
|
|
|
m_ui.checkBoxTracepoint->setChecked(data.tracepoint);
|
2010-11-16 11:42:20 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (mask & FunctionPart)
|
2010-11-25 14:47:56 +01:00
|
|
|
m_ui.lineEditFunction->setText(data.functionName);
|
2010-11-16 11:42:20 +01:00
|
|
|
|
|
|
|
|
if (mask & AddressPart) {
|
2010-11-25 14:47:56 +01:00
|
|
|
if (data.address) {
|
|
|
|
|
m_ui.lineEditAddress->setText(
|
|
|
|
|
QString::fromAscii("0x%1").arg(data.address, 0, 16));
|
2010-11-16 11:42:20 +01:00
|
|
|
} else {
|
|
|
|
|
m_ui.lineEditAddress->clear();
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
2010-11-16 10:23:20 +01:00
|
|
|
void BreakpointDialog::typeChanged(int)
|
2010-10-04 16:00:25 +02:00
|
|
|
{
|
2010-11-16 11:42:20 +01:00
|
|
|
BreakpointType previousType = m_previousType;
|
|
|
|
|
const BreakpointType newType = type();
|
|
|
|
|
m_previousType = newType;
|
2010-11-25 14:47:56 +01:00
|
|
|
// Save current state.
|
|
|
|
|
switch(previousType) {
|
2010-11-16 11:42:20 +01:00
|
|
|
case UnknownType:
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByFileAndLine:
|
|
|
|
|
getParts(FileAndLinePart, &m_savedParameters);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByFunction:
|
|
|
|
|
getParts(FunctionPart, &m_savedParameters);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointAtThrow:
|
|
|
|
|
case BreakpointAtCatch:
|
|
|
|
|
case BreakpointAtMain:
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByAddress:
|
|
|
|
|
case Watchpoint:
|
|
|
|
|
getParts(AddressPart, &m_savedParameters);
|
|
|
|
|
break;
|
|
|
|
|
}
|
|
|
|
|
|
2010-11-25 14:47:56 +01:00
|
|
|
// Enable and set up new state from saved values.
|
|
|
|
|
switch (newType) {
|
2010-11-16 11:42:20 +01:00
|
|
|
case UnknownType:
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByFileAndLine:
|
|
|
|
|
setParts(FileAndLinePart, m_savedParameters);
|
|
|
|
|
setPartsEnabled(FileAndLinePart, true);
|
|
|
|
|
clearParts(FunctionPart|AddressPart);
|
|
|
|
|
setPartsEnabled(FunctionPart|AddressPart, false);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByFunction:
|
|
|
|
|
setParts(FunctionPart, m_savedParameters);
|
|
|
|
|
setPartsEnabled(FunctionPart, true);
|
|
|
|
|
clearParts(FileAndLinePart|AddressPart);
|
|
|
|
|
setPartsEnabled(FileAndLinePart|AddressPart, false);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointAtThrow:
|
|
|
|
|
case BreakpointAtCatch:
|
|
|
|
|
clearParts(AllParts);
|
|
|
|
|
setPartsEnabled(AllParts, false);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointAtMain:
|
|
|
|
|
m_ui.lineEditFunction->setText(QLatin1String("main")); // Just for display
|
|
|
|
|
clearParts(FileAndLinePart|AddressPart);
|
|
|
|
|
setPartsEnabled(AllParts, false);
|
|
|
|
|
break;
|
|
|
|
|
case BreakpointByAddress:
|
|
|
|
|
case Watchpoint:
|
|
|
|
|
setParts(AddressPart, m_savedParameters);
|
|
|
|
|
setPartsEnabled(AddressPart, true);
|
|
|
|
|
clearParts(FileAndLinePart|FunctionPart);
|
|
|
|
|
setPartsEnabled(FileAndLinePart|FunctionPart, false);
|
|
|
|
|
break;
|
|
|
|
|
}
|
2010-10-04 16:00:25 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-16 10:50:11 +01:00
|
|
|
bool BreakpointDialog::showDialog(BreakpointParameters *data)
|
2010-11-16 10:23:20 +01:00
|
|
|
{
|
2010-11-16 10:50:11 +01:00
|
|
|
setParameters(*data);
|
2010-11-16 10:23:20 +01:00
|
|
|
if (exec() != QDialog::Accepted)
|
|
|
|
|
return false;
|
|
|
|
|
|
|
|
|
|
// Check if changed.
|
|
|
|
|
const BreakpointParameters newParameters = parameters();
|
2010-11-16 10:50:11 +01:00
|
|
|
if (data->equals(newParameters))
|
2010-11-16 10:23:20 +01:00
|
|
|
return false;
|
|
|
|
|
|
2010-11-16 10:50:11 +01:00
|
|
|
*data = newParameters;
|
|
|
|
|
return true;
|
2010-11-16 10:23:20 +01:00
|
|
|
}
|
|
|
|
|
|
2010-12-17 13:49:49 +01:00
|
|
|
|
2009-06-12 11:54:01 +02:00
|
|
|
///////////////////////////////////////////////////////////////////////
|
|
|
|
|
//
|
|
|
|
|
// BreakWindow
|
|
|
|
|
//
|
|
|
|
|
///////////////////////////////////////////////////////////////////////
|
|
|
|
|
|
2010-06-16 11:08:54 +02:00
|
|
|
BreakWindow::BreakWindow(QWidget *parent)
|
|
|
|
|
: QTreeView(parent)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-06-16 11:08:54 +02:00
|
|
|
m_alwaysResizeColumnsToContents = false;
|
|
|
|
|
|
2010-11-10 16:33:11 +01:00
|
|
|
QAction *act = debuggerCore()->action(UseAlternatingRowColors);
|
2010-03-16 16:55:56 +01:00
|
|
|
setFrameStyle(QFrame::NoFrame);
|
2010-04-16 11:39:36 +02:00
|
|
|
setAttribute(Qt::WA_MacShowFocusRect, false);
|
2008-12-02 12:01:29 +01:00
|
|
|
setWindowTitle(tr("Breakpoints"));
|
2010-07-30 22:16:59 +02:00
|
|
|
setWindowIcon(QIcon(QLatin1String(":/debugger/images/debugger_breakpoints.png")));
|
2009-05-05 10:14:35 +02:00
|
|
|
setAlternatingRowColors(act->isChecked());
|
2008-12-02 12:01:29 +01:00
|
|
|
setRootIsDecorated(false);
|
|
|
|
|
setIconSize(QSize(10, 10));
|
2009-06-11 13:40:44 +02:00
|
|
|
setSelectionMode(QAbstractItemView::ExtendedSelection);
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
connect(this, SIGNAL(activated(QModelIndex)),
|
2010-11-10 16:33:11 +01:00
|
|
|
SLOT(rowActivated(QModelIndex)));
|
2009-05-05 10:14:35 +02:00
|
|
|
connect(act, SIGNAL(toggled(bool)),
|
2010-11-10 16:33:11 +01:00
|
|
|
SLOT(setAlternatingRowColorsHelper(bool)));
|
2010-11-25 14:47:56 +01:00
|
|
|
connect(debuggerCore()->action(UseAddressInBreakpointsView),
|
|
|
|
|
SIGNAL(toggled(bool)),
|
2010-11-10 16:33:11 +01:00
|
|
|
SLOT(showAddressColumn(bool)));
|
2009-10-01 11:22:44 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void BreakWindow::showAddressColumn(bool on)
|
|
|
|
|
{
|
2010-04-29 18:36:18 +02:00
|
|
|
setColumnHidden(7, !on);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2008-12-17 18:02:08 +01:00
|
|
|
void BreakWindow::keyPressEvent(QKeyEvent *ev)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2009-06-11 13:40:44 +02:00
|
|
|
if (ev->key() == Qt::Key_Delete) {
|
|
|
|
|
QItemSelectionModel *sm = selectionModel();
|
|
|
|
|
QTC_ASSERT(sm, return);
|
|
|
|
|
QModelIndexList si = sm->selectedIndexes();
|
|
|
|
|
if (si.isEmpty())
|
2010-11-24 11:44:43 +01:00
|
|
|
si.append(currentIndex());
|
|
|
|
|
const BreakpointIds ids = breakHandler()->findBreakpointsByIndex(si);
|
|
|
|
|
int row = qMin(model()->rowCount() - ids.size() - 1, currentIndex().row());
|
|
|
|
|
deleteBreakpoints(ids);
|
|
|
|
|
setCurrentIndex(si.at(0).sibling(row, 0));
|
2009-06-11 13:40:44 +02:00
|
|
|
}
|
2008-12-17 18:02:08 +01:00
|
|
|
QTreeView::keyPressEvent(ev);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2008-12-17 18:02:08 +01:00
|
|
|
void BreakWindow::resizeEvent(QResizeEvent *ev)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2008-12-17 18:02:08 +01:00
|
|
|
QTreeView::resizeEvent(ev);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2010-04-29 18:36:18 +02:00
|
|
|
void BreakWindow::mouseDoubleClickEvent(QMouseEvent *ev)
|
|
|
|
|
{
|
|
|
|
|
QModelIndex indexUnderMouse = indexAt(ev->pos());
|
2010-11-24 11:44:43 +01:00
|
|
|
if (indexUnderMouse.isValid() && indexUnderMouse.column() >= 4) {
|
|
|
|
|
BreakpointId id = breakHandler()->findBreakpointByIndex(indexUnderMouse);
|
|
|
|
|
editBreakpoints(BreakpointIds() << id);
|
|
|
|
|
}
|
2010-05-10 10:33:52 +02:00
|
|
|
QTreeView::mouseDoubleClickEvent(ev);
|
2010-04-29 18:36:18 +02:00
|
|
|
}
|
|
|
|
|
|
2010-12-17 13:49:49 +01:00
|
|
|
void BreakWindow::setModel(QAbstractItemModel *model)
|
|
|
|
|
{
|
|
|
|
|
QTreeView::setModel(model);
|
|
|
|
|
resizeColumnToContents(0); // Number
|
|
|
|
|
resizeColumnToContents(3); // Line
|
|
|
|
|
resizeColumnToContents(6); // Ignore count
|
|
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
void BreakWindow::contextMenuEvent(QContextMenuEvent *ev)
|
|
|
|
|
{
|
|
|
|
|
QMenu menu;
|
2009-06-11 13:40:44 +02:00
|
|
|
QItemSelectionModel *sm = selectionModel();
|
|
|
|
|
QTC_ASSERT(sm, return);
|
2010-11-24 11:44:43 +01:00
|
|
|
QModelIndexList selectedIndices = sm->selectedIndexes();
|
2009-06-11 13:40:44 +02:00
|
|
|
QModelIndex indexUnderMouse = indexAt(ev->pos());
|
2010-11-24 11:44:43 +01:00
|
|
|
if (selectedIndices.isEmpty() && indexUnderMouse.isValid())
|
|
|
|
|
selectedIndices.append(indexUnderMouse);
|
|
|
|
|
|
|
|
|
|
BreakHandler *handler = breakHandler();
|
|
|
|
|
BreakpointIds selectedIds = handler->findBreakpointsByIndex(selectedIndices);
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-06-16 11:08:54 +02:00
|
|
|
const int rowCount = model()->rowCount();
|
2010-11-04 09:54:23 +01:00
|
|
|
const unsigned engineCapabilities = BreakOnThrowAndCatchCapability;
|
2010-11-25 14:47:56 +01:00
|
|
|
// FIXME BP: model()->data(QModelIndex(), EngineCapabilitiesRole).toUInt();
|
2009-07-16 15:22:54 +02:00
|
|
|
|
2010-02-12 10:52:09 +01:00
|
|
|
QAction *deleteAction = new QAction(tr("Delete Breakpoint"), &menu);
|
2010-11-24 11:44:43 +01:00
|
|
|
deleteAction->setEnabled(!selectedIds.isEmpty());
|
2009-07-16 15:22:54 +02:00
|
|
|
|
2010-02-12 10:52:09 +01:00
|
|
|
QAction *deleteAllAction = new QAction(tr("Delete All Breakpoints"), &menu);
|
2010-09-14 17:15:01 +02:00
|
|
|
deleteAllAction->setEnabled(model()->rowCount() > 0);
|
2009-07-16 15:22:54 +02:00
|
|
|
|
2010-02-12 10:52:09 +01:00
|
|
|
// Delete by file: Find indices of breakpoints of the same file.
|
2009-07-16 15:22:54 +02:00
|
|
|
QAction *deleteByFileAction = 0;
|
2010-11-24 11:44:43 +01:00
|
|
|
BreakpointIds breakpointsInFile;
|
2009-07-16 15:22:54 +02:00
|
|
|
if (indexUnderMouse.isValid()) {
|
2010-02-12 10:52:09 +01:00
|
|
|
const QModelIndex index = indexUnderMouse.sibling(indexUnderMouse.row(), 2);
|
2010-11-24 11:44:43 +01:00
|
|
|
const QString file = index.data().toString();
|
2009-07-16 15:22:54 +02:00
|
|
|
if (!file.isEmpty()) {
|
|
|
|
|
for (int i = 0; i < rowCount; i++)
|
2010-11-24 11:44:43 +01:00
|
|
|
if (index.data().toString() == file)
|
|
|
|
|
breakpointsInFile.append(handler->findBreakpointByIndex(index));
|
|
|
|
|
if (breakpointsInFile.size() > 1) {
|
2010-02-12 10:52:09 +01:00
|
|
|
deleteByFileAction =
|
|
|
|
|
new QAction(tr("Delete Breakpoints of \"%1\"").arg(file), &menu);
|
2009-07-16 15:22:54 +02:00
|
|
|
deleteByFileAction->setEnabled(true);
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
if (!deleteByFileAction) {
|
2010-02-12 10:52:09 +01:00
|
|
|
deleteByFileAction = new QAction(tr("Delete Breakpoints of File"), &menu);
|
2009-07-16 15:22:54 +02:00
|
|
|
deleteByFileAction->setEnabled(false);
|
|
|
|
|
}
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-02-12 10:52:09 +01:00
|
|
|
QAction *adjustColumnAction =
|
|
|
|
|
new QAction(tr("Adjust Column Widths to Contents"), &menu);
|
|
|
|
|
|
|
|
|
|
QAction *alwaysAdjustAction =
|
|
|
|
|
new QAction(tr("Always Adjust Column Widths to Contents"), &menu);
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2009-07-16 15:22:54 +02:00
|
|
|
alwaysAdjustAction->setCheckable(true);
|
|
|
|
|
alwaysAdjustAction->setChecked(m_alwaysResizeColumnsToContents);
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-04-29 18:36:18 +02:00
|
|
|
QAction *editBreakpointAction =
|
|
|
|
|
new QAction(tr("Edit Breakpoint..."), &menu);
|
2010-11-24 11:44:43 +01:00
|
|
|
editBreakpointAction->setEnabled(!selectedIds.isEmpty());
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-11-04 09:54:23 +01:00
|
|
|
int threadId = 0;
|
|
|
|
|
// FIXME BP: m_engine->threadsHandler()->currentThreadId();
|
2010-04-30 14:18:10 +02:00
|
|
|
QString associateTitle = threadId == -1
|
|
|
|
|
? tr("Associate Breakpoint With All Threads")
|
|
|
|
|
: tr("Associate Breakpoint With Thread %1").arg(threadId);
|
|
|
|
|
QAction *associateBreakpointAction = new QAction(associateTitle, &menu);
|
2010-11-24 11:44:43 +01:00
|
|
|
associateBreakpointAction->setEnabled(!selectedIds.isEmpty());
|
2010-04-30 14:18:10 +02:00
|
|
|
|
2010-02-12 10:52:09 +01:00
|
|
|
QAction *synchronizeAction =
|
|
|
|
|
new QAction(tr("Synchronize Breakpoints"), &menu);
|
2010-11-10 11:39:01 +01:00
|
|
|
synchronizeAction->setEnabled(debuggerCore()->hasSnapshots());
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
bool enabled = selectedIds.isEmpty() || handler->isEnabled(selectedIds.at(0));
|
2010-11-10 16:33:11 +01:00
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
const QString str5 = selectedIds.size() > 1
|
2010-04-12 15:24:18 +02:00
|
|
|
? enabled
|
|
|
|
|
? tr("Disable Selected Breakpoints")
|
|
|
|
|
: tr("Enable Selected Breakpoints")
|
|
|
|
|
: enabled
|
|
|
|
|
? tr("Disable Breakpoint")
|
|
|
|
|
: tr("Enable Breakpoint");
|
2009-07-16 15:22:54 +02:00
|
|
|
QAction *toggleEnabledAction = new QAction(str5, &menu);
|
2010-11-24 11:44:43 +01:00
|
|
|
toggleEnabledAction->setEnabled(!selectedIds.isEmpty());
|
2009-07-16 15:22:54 +02:00
|
|
|
|
2010-09-21 16:32:43 +02:00
|
|
|
QAction *addBreakpointAction =
|
2010-09-28 13:14:14 +02:00
|
|
|
new QAction(tr("Add Breakpoint..."), this);
|
2010-02-11 17:29:10 +01:00
|
|
|
QAction *breakAtThrowAction =
|
|
|
|
|
new QAction(tr("Set Breakpoint at \"throw\""), this);
|
|
|
|
|
QAction *breakAtCatchAction =
|
|
|
|
|
new QAction(tr("Set Breakpoint at \"catch\""), this);
|
2009-07-16 15:22:54 +02:00
|
|
|
|
2010-09-28 13:14:14 +02:00
|
|
|
menu.addAction(addBreakpointAction);
|
2009-07-16 15:22:54 +02:00
|
|
|
menu.addAction(deleteAction);
|
2010-04-29 18:36:18 +02:00
|
|
|
menu.addAction(editBreakpointAction);
|
2010-04-30 14:18:10 +02:00
|
|
|
menu.addAction(associateBreakpointAction);
|
2009-07-16 15:22:54 +02:00
|
|
|
menu.addAction(toggleEnabledAction);
|
|
|
|
|
menu.addSeparator();
|
|
|
|
|
menu.addAction(deleteAllAction);
|
2010-11-10 16:33:11 +01:00
|
|
|
//menu.addAction(deleteByFileAction);
|
2009-03-10 17:30:11 +01:00
|
|
|
menu.addSeparator();
|
2009-07-16 15:22:54 +02:00
|
|
|
menu.addAction(synchronizeAction);
|
2010-02-11 17:29:10 +01:00
|
|
|
if (engineCapabilities & BreakOnThrowAndCatchCapability) {
|
2010-09-28 13:14:14 +02:00
|
|
|
menu.addSeparator();
|
2010-02-11 17:29:10 +01:00
|
|
|
menu.addAction(breakAtThrowAction);
|
|
|
|
|
menu.addAction(breakAtCatchAction);
|
|
|
|
|
}
|
2009-06-12 11:54:01 +02:00
|
|
|
menu.addSeparator();
|
2010-11-10 16:33:11 +01:00
|
|
|
menu.addAction(debuggerCore()->action(UseToolTipsInBreakpointsView));
|
|
|
|
|
menu.addAction(debuggerCore()->action(UseAddressInBreakpointsView));
|
2009-08-18 16:46:33 +02:00
|
|
|
menu.addAction(adjustColumnAction);
|
|
|
|
|
menu.addAction(alwaysAdjustAction);
|
|
|
|
|
menu.addSeparator();
|
2010-11-10 16:33:11 +01:00
|
|
|
menu.addAction(debuggerCore()->action(SettingsDialog));
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
QAction *act = menu.exec(ev->globalPos());
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
if (act == deleteAction)
|
|
|
|
|
deleteBreakpoints(selectedIds);
|
|
|
|
|
else if (act == deleteAllAction)
|
|
|
|
|
deleteBreakpoints(handler->allBreakpointIds());
|
|
|
|
|
else if (act == deleteByFileAction)
|
|
|
|
|
deleteBreakpoints(breakpointsInFile);
|
2009-07-16 15:22:54 +02:00
|
|
|
else if (act == adjustColumnAction)
|
2008-12-02 12:01:29 +01:00
|
|
|
resizeColumnsToContents();
|
2009-07-16 15:22:54 +02:00
|
|
|
else if (act == alwaysAdjustAction)
|
2008-12-02 12:01:29 +01:00
|
|
|
setAlwaysResizeColumnsToContents(!m_alwaysResizeColumnsToContents);
|
2010-04-29 18:36:18 +02:00
|
|
|
else if (act == editBreakpointAction)
|
2010-11-24 11:44:43 +01:00
|
|
|
editBreakpoints(selectedIds);
|
2010-04-30 14:18:10 +02:00
|
|
|
else if (act == associateBreakpointAction)
|
2010-11-24 11:44:43 +01:00
|
|
|
associateBreakpoint(selectedIds, threadId);
|
2009-07-16 15:22:54 +02:00
|
|
|
else if (act == synchronizeAction)
|
2010-11-10 16:33:11 +01:00
|
|
|
; //synchronizeBreakpoints();
|
2009-07-16 15:22:54 +02:00
|
|
|
else if (act == toggleEnabledAction)
|
2010-11-24 11:44:43 +01:00
|
|
|
setBreakpointsEnabled(selectedIds, !enabled);
|
2010-09-21 16:32:43 +02:00
|
|
|
else if (act == addBreakpointAction)
|
|
|
|
|
addBreakpoint();
|
2010-11-16 10:50:11 +01:00
|
|
|
else if (act == breakAtThrowAction)
|
|
|
|
|
handler->appendBreakpoint(BreakpointParameters(BreakpointAtThrow));
|
|
|
|
|
else if (act == breakAtCatchAction)
|
|
|
|
|
handler->appendBreakpoint(BreakpointParameters(BreakpointAtCatch));
|
2009-06-11 13:40:44 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
void BreakWindow::setBreakpointsEnabled(const BreakpointIds &ids, bool enabled)
|
2009-06-11 13:40:44 +02:00
|
|
|
{
|
2010-11-10 16:33:11 +01:00
|
|
|
BreakHandler *handler = breakHandler();
|
2010-11-24 11:44:43 +01:00
|
|
|
foreach (const BreakpointId id, ids)
|
2010-11-15 15:30:39 +01:00
|
|
|
handler->setEnabled(id, enabled);
|
2009-06-11 13:40:44 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
void BreakWindow::deleteBreakpoints(const BreakpointIds &ids)
|
2009-06-11 13:40:44 +02:00
|
|
|
{
|
2010-11-10 16:33:11 +01:00
|
|
|
BreakHandler *handler = breakHandler();
|
2010-11-24 11:44:43 +01:00
|
|
|
foreach (const BreakpointId id, ids)
|
2010-11-15 15:30:39 +01:00
|
|
|
handler->removeBreakpoint(id);
|
2009-07-16 15:22:54 +02:00
|
|
|
}
|
2009-06-11 13:40:44 +02:00
|
|
|
|
2010-11-15 14:12:05 +01:00
|
|
|
void BreakWindow::editBreakpoint(BreakpointId id, QWidget *parent)
|
2010-09-21 16:32:43 +02:00
|
|
|
{
|
2010-10-06 10:32:36 +02:00
|
|
|
BreakpointDialog dialog(parent);
|
2010-11-16 11:06:09 +01:00
|
|
|
BreakpointParameters data = breakHandler()->breakpointData(id);
|
2010-11-16 10:50:11 +01:00
|
|
|
if (dialog.showDialog(&data))
|
2010-11-16 11:06:09 +01:00
|
|
|
breakHandler()->setBreakpointData(id, data);
|
2010-09-28 13:14:14 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void BreakWindow::addBreakpoint()
|
|
|
|
|
{
|
2010-11-16 10:50:11 +01:00
|
|
|
BreakpointParameters data(BreakpointByFileAndLine);
|
2010-11-15 14:12:05 +01:00
|
|
|
BreakpointDialog dialog(this);
|
|
|
|
|
if (dialog.showDialog(&data))
|
2010-11-10 16:33:11 +01:00
|
|
|
breakHandler()->appendBreakpoint(data);
|
2010-09-21 16:32:43 +02:00
|
|
|
}
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
void BreakWindow::editBreakpoints(const BreakpointIds &ids)
|
2008-12-02 12:01:29 +01:00
|
|
|
{
|
2010-11-24 11:44:43 +01:00
|
|
|
QTC_ASSERT(!ids.isEmpty(), return);
|
2010-11-04 09:54:23 +01:00
|
|
|
|
2010-11-15 15:30:39 +01:00
|
|
|
const BreakpointId id = ids.at(0);
|
2010-11-10 16:33:11 +01:00
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
if (ids.size() == 1) {
|
2010-11-10 16:33:11 +01:00
|
|
|
editBreakpoint(id, this);
|
2010-09-28 13:14:14 +02:00
|
|
|
return;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
// This allows to change properties of multiple breakpoints at a time.
|
2008-12-02 12:01:29 +01:00
|
|
|
QDialog dlg(this);
|
|
|
|
|
Ui::BreakCondition ui;
|
|
|
|
|
ui.setupUi(&dlg);
|
2010-09-28 13:14:14 +02:00
|
|
|
dlg.setWindowTitle(tr("Edit Breakpoint Properties"));
|
2010-11-04 09:54:23 +01:00
|
|
|
ui.lineEditIgnoreCount->setValidator(
|
|
|
|
|
new QIntValidator(0, 2147483647, ui.lineEditIgnoreCount));
|
2010-10-06 10:32:36 +02:00
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
BreakHandler *handler = breakHandler();
|
2010-11-10 16:33:11 +01:00
|
|
|
const QString oldCondition = QString::fromLatin1(handler->condition(id));
|
|
|
|
|
const QString oldIgnoreCount = QString::number(handler->ignoreCount(id));
|
2010-12-14 13:00:02 +01:00
|
|
|
const QString oldThreadSpec =
|
|
|
|
|
BreakHandler::displayFromThreadSpec(handler->threadSpec(id));
|
2010-10-06 10:32:36 +02:00
|
|
|
|
|
|
|
|
ui.lineEditCondition->setText(oldCondition);
|
|
|
|
|
ui.lineEditIgnoreCount->setText(oldIgnoreCount);
|
|
|
|
|
ui.lineEditThreadSpec->setText(oldThreadSpec);
|
2008-12-02 12:01:29 +01:00
|
|
|
|
|
|
|
|
if (dlg.exec() == QDialog::Rejected)
|
|
|
|
|
return;
|
|
|
|
|
|
2010-10-06 10:32:36 +02:00
|
|
|
const QString newCondition = ui.lineEditCondition->text();
|
|
|
|
|
const QString newIgnoreCount = ui.lineEditIgnoreCount->text();
|
|
|
|
|
const QString newThreadSpec = ui.lineEditThreadSpec->text();
|
|
|
|
|
|
|
|
|
|
if (newCondition == oldCondition && newIgnoreCount == oldIgnoreCount
|
|
|
|
|
&& newThreadSpec == oldThreadSpec)
|
|
|
|
|
return;
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
foreach (const BreakpointId id, ids) {
|
2010-11-10 16:33:11 +01:00
|
|
|
handler->setCondition(id, newCondition.toLatin1());
|
|
|
|
|
handler->setIgnoreCount(id, newIgnoreCount.toInt());
|
2010-12-14 13:00:02 +01:00
|
|
|
handler->setThreadSpec(id,
|
|
|
|
|
BreakHandler::threadSpecFromDisplay(newThreadSpec));
|
2009-06-11 13:40:44 +02:00
|
|
|
}
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2010-11-24 11:44:43 +01:00
|
|
|
void BreakWindow::associateBreakpoint(const BreakpointIds &ids, int threadId)
|
2010-04-30 14:18:10 +02:00
|
|
|
{
|
2010-11-10 16:33:11 +01:00
|
|
|
BreakHandler *handler = breakHandler();
|
2010-11-24 11:44:43 +01:00
|
|
|
foreach (const BreakpointId id, ids)
|
2010-11-30 13:39:01 +01:00
|
|
|
handler->setThreadSpec(id, threadId);
|
2010-04-30 14:18:10 +02:00
|
|
|
}
|
|
|
|
|
|
2008-12-02 12:01:29 +01:00
|
|
|
void BreakWindow::resizeColumnsToContents()
|
|
|
|
|
{
|
2009-10-01 11:22:44 +02:00
|
|
|
for (int i = model()->columnCount(); --i >= 0; )
|
|
|
|
|
resizeColumnToContents(i);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
void BreakWindow::setAlwaysResizeColumnsToContents(bool on)
|
|
|
|
|
{
|
|
|
|
|
m_alwaysResizeColumnsToContents = on;
|
2010-01-29 21:33:57 +01:00
|
|
|
QHeaderView::ResizeMode mode = on
|
2008-12-02 12:01:29 +01:00
|
|
|
? QHeaderView::ResizeToContents : QHeaderView::Interactive;
|
2009-10-01 11:22:44 +02:00
|
|
|
for (int i = model()->columnCount(); --i >= 0; )
|
|
|
|
|
header()->setResizeMode(i, mode);
|
2008-12-02 12:01:29 +01:00
|
|
|
}
|
|
|
|
|
|
2010-06-16 11:08:54 +02:00
|
|
|
void BreakWindow::rowActivated(const QModelIndex &index)
|
|
|
|
|
{
|
2010-11-10 16:33:11 +01:00
|
|
|
breakHandler()->gotoLocation(breakHandler()->findBreakpointByIndex(index));
|
2010-06-16 11:08:54 +02:00
|
|
|
}
|
|
|
|
|
|
|
|
|
|
} // namespace Internal
|
|
|
|
|
} // namespace Debugger
|
2010-09-21 16:32:43 +02:00
|
|
|
|
|
|
|
|
#include "breakwindow.moc"
|