forked from qt-creator/qt-creator
debugger: speed up QDate, QTime, QDateTime dumpers
Change-Id: I9ed3961d047738bd3add87b1f00d548df1fb01d8 Reviewed-on: http://codereview.qt.nokia.com/3609 Reviewed-by: hjk <qthjk@ovi.com>
This commit is contained in:
@@ -66,8 +66,11 @@ Hex2EncodedUtf8, \
|
|||||||
Hex8EncodedBigEndian, \
|
Hex8EncodedBigEndian, \
|
||||||
Hex4EncodedBigEndian, \
|
Hex4EncodedBigEndian, \
|
||||||
Hex4EncodedLittleEndianWithoutQuotes, \
|
Hex4EncodedLittleEndianWithoutQuotes, \
|
||||||
Hex2EncodedLocal8Bit \
|
Hex2EncodedLocal8Bit, \
|
||||||
= range(14)
|
JulianDate, \
|
||||||
|
MillisecondsSinceMidnight, \
|
||||||
|
JulianDateAndMillisecondsSinceMidnight \
|
||||||
|
= range(17)
|
||||||
|
|
||||||
# Display modes
|
# Display modes
|
||||||
StopDisplay, \
|
StopDisplay, \
|
||||||
|
@@ -139,14 +139,10 @@ def qdump__QModelIndex(d, value):
|
|||||||
|
|
||||||
|
|
||||||
def qdump__QDate(d, value):
|
def qdump__QDate(d, value):
|
||||||
if int(value["jd"]) == 0:
|
d.putValue(value["jd"], JulianDate)
|
||||||
d.putValue("(null)")
|
|
||||||
d.putNumChild(0)
|
|
||||||
return
|
|
||||||
qt = d.ns + "Qt::"
|
|
||||||
d.putStringValue(call(value, "toString", qt + "TextDate"))
|
|
||||||
d.putNumChild(1)
|
d.putNumChild(1)
|
||||||
if d.isExpanded():
|
if d.isExpanded():
|
||||||
|
qt = d.ns + "Qt::"
|
||||||
# FIXME: This improperly uses complex return values.
|
# FIXME: This improperly uses complex return values.
|
||||||
with Children(d):
|
with Children(d):
|
||||||
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
||||||
@@ -157,14 +153,10 @@ def qdump__QDate(d, value):
|
|||||||
|
|
||||||
|
|
||||||
def qdump__QTime(d, value):
|
def qdump__QTime(d, value):
|
||||||
if int(value["mds"]) == -1:
|
d.putValue(value["mds"], MillisecondsSinceMidnight)
|
||||||
d.putValue("(null)")
|
|
||||||
d.putNumChild(0)
|
|
||||||
return
|
|
||||||
qt = d.ns + "Qt::"
|
|
||||||
d.putStringValue(call(value, "toString", qt + "TextDate"))
|
|
||||||
d.putNumChild(1)
|
d.putNumChild(1)
|
||||||
if d.isExpanded():
|
if d.isExpanded():
|
||||||
|
qt = d.ns + "Qt::"
|
||||||
# FIXME: This improperly uses complex return values.
|
# FIXME: This improperly uses complex return values.
|
||||||
with Children(d):
|
with Children(d):
|
||||||
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
||||||
@@ -178,19 +170,17 @@ def qdump__QTime(d, value):
|
|||||||
def qdump__QDateTime(d, value):
|
def qdump__QDateTime(d, value):
|
||||||
try:
|
try:
|
||||||
# Fails without debug info.
|
# Fails without debug info.
|
||||||
if int(value["d"]["d"].dereference()["time"]["mds"]) == -1:
|
p = value["d"]["d"].dereference()
|
||||||
d.putValue("(null)")
|
|
||||||
d.putNumChild(0)
|
|
||||||
return
|
|
||||||
except:
|
except:
|
||||||
d.putPlainChildren(value)
|
d.putPlainChildren(value)
|
||||||
return
|
return
|
||||||
qt = d.ns + "Qt::"
|
d.putValue("%s/%s" % (p["date"]["jd"], p["time"]["mds"]),
|
||||||
d.putStringValue(call(value, "toString", qt + "TextDate"))
|
JulianDateAndMillisecondsSinceMidnight)
|
||||||
d.putNumChild(1)
|
d.putNumChild(1)
|
||||||
if d.isExpanded():
|
if d.isExpanded():
|
||||||
# FIXME: This improperly uses complex return values.
|
# FIXME: This improperly uses complex return values.
|
||||||
with Children(d):
|
with Children(d):
|
||||||
|
qt = d.ns + "Qt::"
|
||||||
d.putCallItem("toTime_t", value, "toTime_t")
|
d.putCallItem("toTime_t", value, "toTime_t")
|
||||||
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
d.putCallItem("toString", value, "toString", qt + "TextDate")
|
||||||
d.putCallItem("(ISO)", value, "toString", qt + "ISODate")
|
d.putCallItem("(ISO)", value, "toString", qt + "ISODate")
|
||||||
|
@@ -274,25 +274,25 @@ static QString niceTypeHelper(const QByteArray &typeIn)
|
|||||||
return simplified;
|
return simplified;
|
||||||
}
|
}
|
||||||
|
|
||||||
static QString removeNamespaces(QString str, const QByteArray &ns)
|
QString WatchModel::removeNamespaces(QString str) const
|
||||||
{
|
{
|
||||||
if (!debuggerCore()->boolSetting(ShowStdNamespace))
|
if (!debuggerCore()->boolSetting(ShowStdNamespace))
|
||||||
str.remove(QLatin1String("std::"));
|
str.remove(QLatin1String("std::"));
|
||||||
if (!debuggerCore()->boolSetting(ShowQtNamespace)) {
|
if (!debuggerCore()->boolSetting(ShowQtNamespace)) {
|
||||||
const QString qtNamespace = QString::fromLatin1(ns);
|
const QString qtNamespace = QString::fromLatin1(engine()->qtNamespace());
|
||||||
if (!qtNamespace.isEmpty())
|
if (!qtNamespace.isEmpty())
|
||||||
str.remove(qtNamespace);
|
str.remove(qtNamespace);
|
||||||
}
|
}
|
||||||
return str;
|
return str;
|
||||||
}
|
}
|
||||||
|
|
||||||
static QString removeInitialNamespace(QString str, const QByteArray &ns)
|
QString WatchModel::removeInitialNamespace(QString str) const
|
||||||
{
|
{
|
||||||
if (str.startsWith(QLatin1String("std::"))
|
if (str.startsWith(QLatin1String("std::"))
|
||||||
&& debuggerCore()->boolSetting(ShowStdNamespace))
|
&& debuggerCore()->boolSetting(ShowStdNamespace))
|
||||||
str = str.mid(5);
|
str = str.mid(5);
|
||||||
if (!debuggerCore()->boolSetting(ShowQtNamespace)) {
|
if (!debuggerCore()->boolSetting(ShowQtNamespace)) {
|
||||||
const QString qtNamespace = QString::fromLatin1(ns);
|
const QByteArray qtNamespace = engine()->qtNamespace();
|
||||||
if (!qtNamespace.isEmpty() && str.startsWith(qtNamespace))
|
if (!qtNamespace.isEmpty() && str.startsWith(qtNamespace))
|
||||||
str = str.mid(qtNamespace.size());
|
str = str.mid(qtNamespace.size());
|
||||||
}
|
}
|
||||||
@@ -395,41 +395,45 @@ static QString quoteUnprintable(const QString &str)
|
|||||||
return encoded;
|
return encoded;
|
||||||
}
|
}
|
||||||
|
|
||||||
static QString formattedValue(const WatchData &data, int format)
|
QString WatchModel::formattedValue(const WatchData &data) const
|
||||||
{
|
{
|
||||||
|
const QByteArray qtNamespace = engine()->qtNamespace();
|
||||||
|
const QString &value = data.value;
|
||||||
|
|
||||||
|
int format = itemFormat(data);
|
||||||
if (isIntType(data.type)) {
|
if (isIntType(data.type)) {
|
||||||
if (data.value.isEmpty())
|
if (value.isEmpty())
|
||||||
return data.value;
|
return value;
|
||||||
// Do not reformat booleans (reported as 'true, false').
|
// Do not reformat booleans (reported as 'true, false').
|
||||||
const QChar firstChar = data.value.at(0);
|
const QChar firstChar = value.at(0);
|
||||||
if (!firstChar.isDigit() && firstChar != QLatin1Char('-'))
|
if (!firstChar.isDigit() && firstChar != QLatin1Char('-'))
|
||||||
return data.value;
|
return value;
|
||||||
// Append quoted, printable character also for decimal.
|
// Append quoted, printable character also for decimal.
|
||||||
if (data.type.endsWith("char")) {
|
if (data.type.endsWith("char")) {
|
||||||
bool ok;
|
bool ok;
|
||||||
const int code = data.value.toInt(&ok);
|
const int code = value.toInt(&ok);
|
||||||
return ok ? reformatCharacter(code, format) : data.value;
|
return ok ? reformatCharacter(code, format) : value;
|
||||||
}
|
}
|
||||||
// Rest: Leave decimal as is
|
// Rest: Leave decimal as is
|
||||||
if (format <= 0)
|
if (format <= 0)
|
||||||
return data.value;
|
return value;
|
||||||
// Evil hack, covers 'unsigned' as well as quint64.
|
// Evil hack, covers 'unsigned' as well as quint64.
|
||||||
if (data.type.contains('u'))
|
if (data.type.contains('u'))
|
||||||
return reformatInteger(data.value.toULongLong(0, 0), format);
|
return reformatInteger(value.toULongLong(0, 0), format);
|
||||||
return reformatInteger(data.value.toLongLong(), format);
|
return reformatInteger(value.toLongLong(), format);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (data.type == "va_list")
|
if (data.type == "va_list")
|
||||||
return data.value;
|
return value;
|
||||||
|
|
||||||
if (!isPointerType(data.type) && !isVTablePointer(data.type)) {
|
if (!isPointerType(data.type) && !isVTablePointer(data.type)) {
|
||||||
bool ok = false;
|
bool ok = false;
|
||||||
qulonglong integer = data.value.toULongLong(&ok, 0);
|
qulonglong integer = value.toULongLong(&ok, 0);
|
||||||
if (ok)
|
if (ok)
|
||||||
return reformatInteger(integer, format);
|
return reformatInteger(integer, format);
|
||||||
}
|
}
|
||||||
|
|
||||||
QString result = data.value;
|
QString result = value;
|
||||||
if (result.startsWith(QLatin1Char('<'))) {
|
if (result.startsWith(QLatin1Char('<'))) {
|
||||||
if (result == QLatin1String("<Edit>"))
|
if (result == QLatin1String("<Edit>"))
|
||||||
result = WatchHandler::tr("<Edit>");
|
result = WatchHandler::tr("<Edit>");
|
||||||
@@ -446,7 +450,8 @@ static QString formattedValue(const WatchData &data, int format)
|
|||||||
bool ok;
|
bool ok;
|
||||||
const bool moreThan = result.at(1) == QLatin1Char('>');
|
const bool moreThan = result.at(1) == QLatin1Char('>');
|
||||||
const int numberPos = moreThan ? 2 : 1;
|
const int numberPos = moreThan ? 2 : 1;
|
||||||
const int size = result.mid(numberPos, result.indexOf(' ') - numberPos).toInt(&ok);
|
const int len = result.indexOf(' ') - numberPos;
|
||||||
|
const int size = result.mid(numberPos, len).toInt(&ok);
|
||||||
QTC_ASSERT(ok, qWarning("WatchHandler: Invalid item count '%s'",
|
QTC_ASSERT(ok, qWarning("WatchHandler: Invalid item count '%s'",
|
||||||
qPrintable(result)))
|
qPrintable(result)))
|
||||||
result = moreThan ?
|
result = moreThan ?
|
||||||
@@ -629,8 +634,8 @@ void WatchModel::emitDataChanged(int column, const QModelIndex &parentIndex)
|
|||||||
emitDataChanged(column, index(i, 0, parentIndex));
|
emitDataChanged(column, index(i, 0, parentIndex));
|
||||||
}
|
}
|
||||||
|
|
||||||
// Truncate value for item view, maintaining quotes
|
// Truncate value for item view, maintaining quotes.
|
||||||
static inline QString truncateValue(QString v)
|
static QString truncateValue(QString v)
|
||||||
{
|
{
|
||||||
enum { maxLength = 512 };
|
enum { maxLength = 512 };
|
||||||
if (v.size() < maxLength)
|
if (v.size() < maxLength)
|
||||||
@@ -699,7 +704,6 @@ QVariant WatchModel::data(const QModelIndex &idx, int role) const
|
|||||||
}
|
}
|
||||||
|
|
||||||
case Qt::DisplayRole: {
|
case Qt::DisplayRole: {
|
||||||
const QByteArray qtNameSpace = engine()->qtNamespace();
|
|
||||||
QString result;
|
QString result;
|
||||||
switch (idx.column()) {
|
switch (idx.column()) {
|
||||||
case 0:
|
case 0:
|
||||||
@@ -708,18 +712,18 @@ QVariant WatchModel::data(const QModelIndex &idx, int role) const
|
|||||||
else if (data.name == QLatin1String("*") && item->parent)
|
else if (data.name == QLatin1String("*") && item->parent)
|
||||||
result = QLatin1Char('*') + item->parent->name;
|
result = QLatin1Char('*') + item->parent->name;
|
||||||
else
|
else
|
||||||
result = removeInitialNamespace(data.name, qtNameSpace);
|
result = removeInitialNamespace(data.name);
|
||||||
break;
|
break;
|
||||||
case 1:
|
case 1:
|
||||||
result = removeInitialNamespace(truncateValue(
|
result = removeInitialNamespace(
|
||||||
formattedValue(data, itemFormat(data))), qtNameSpace);
|
truncateValue(formattedValue(data)));
|
||||||
if (data.referencingAddress) {
|
if (data.referencingAddress) {
|
||||||
result += QLatin1String(" @");
|
result += QLatin1String(" @");
|
||||||
result += QString::fromLatin1(data.hexAddress());
|
result += QString::fromLatin1(data.hexAddress());
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
case 2:
|
case 2:
|
||||||
result = removeNamespaces(displayType(data), qtNameSpace);
|
result = removeNamespaces(displayType(data));
|
||||||
break;
|
break;
|
||||||
default:
|
default:
|
||||||
break;
|
break;
|
||||||
@@ -787,7 +791,7 @@ QVariant WatchModel::data(const QModelIndex &idx, int role) const
|
|||||||
return m_handler->m_reportedTypeFormats.value(type);
|
return m_handler->m_reportedTypeFormats.value(type);
|
||||||
}
|
}
|
||||||
case LocalsTypeRole:
|
case LocalsTypeRole:
|
||||||
return removeNamespaces(displayType(data), engine()->qtNamespace());
|
return removeNamespaces(displayType(data));
|
||||||
case LocalsRawTypeRole:
|
case LocalsRawTypeRole:
|
||||||
return QString::fromLatin1(data.type);
|
return QString::fromLatin1(data.type);
|
||||||
case LocalsTypeFormatRole:
|
case LocalsTypeFormatRole:
|
||||||
|
@@ -121,6 +121,9 @@ signals:
|
|||||||
|
|
||||||
private:
|
private:
|
||||||
QString displayType(const WatchData &typeIn) const;
|
QString displayType(const WatchData &typeIn) const;
|
||||||
|
QString formattedValue(const WatchData &data) const;
|
||||||
|
QString removeInitialNamespace(QString str) const;
|
||||||
|
QString removeNamespaces(QString str) const;
|
||||||
void formatRequests(QByteArray *out, const WatchItem *item) const;
|
void formatRequests(QByteArray *out, const WatchItem *item) const;
|
||||||
DebuggerEngine *engine() const;
|
DebuggerEngine *engine() const;
|
||||||
int itemFormat(const WatchData &data) const;
|
int itemFormat(const WatchData &data) const;
|
||||||
|
@@ -55,12 +55,13 @@
|
|||||||
|
|
||||||
#include <extensionsystem/pluginmanager.h>
|
#include <extensionsystem/pluginmanager.h>
|
||||||
|
|
||||||
#include <QtCore/QDebug>
|
|
||||||
#include <QtCore/QTime>
|
|
||||||
#include <QtCore/QStringList>
|
|
||||||
#include <QtCore/QCoreApplication>
|
#include <QtCore/QCoreApplication>
|
||||||
#include <QtCore/QTextStream>
|
#include <QtCore/QDateTime>
|
||||||
|
#include <QtCore/QDebug>
|
||||||
#include <QtCore/QHash>
|
#include <QtCore/QHash>
|
||||||
|
#include <QtCore/QStringList>
|
||||||
|
#include <QtCore/QTextStream>
|
||||||
|
#include <QtCore/QTime>
|
||||||
|
|
||||||
#include <QtGui/QTextCursor>
|
#include <QtGui/QTextCursor>
|
||||||
#include <QtGui/QPlainTextEdit>
|
#include <QtGui/QPlainTextEdit>
|
||||||
@@ -518,6 +519,16 @@ QString quoteUnprintableLatin1(const QByteArray &ba)
|
|||||||
return res;
|
return res;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static QDate dateFromData(int jd)
|
||||||
|
{
|
||||||
|
return jd ? QDate::fromJulianDay(jd) : QDate();
|
||||||
|
}
|
||||||
|
|
||||||
|
static QTime timeFromData(int ms)
|
||||||
|
{
|
||||||
|
return ms == -1 ? QTime() : QTime(0, 0, 0, 0).addMSecs(ms);
|
||||||
|
}
|
||||||
|
|
||||||
QString decodeData(const QByteArray &ba, int encoding)
|
QString decodeData(const QByteArray &ba, int encoding)
|
||||||
{
|
{
|
||||||
switch (encoding) {
|
switch (encoding) {
|
||||||
@@ -613,6 +624,20 @@ QString decodeData(const QByteArray &ba, int encoding)
|
|||||||
const QByteArray decodedBa = QByteArray::fromHex(ba);
|
const QByteArray decodedBa = QByteArray::fromHex(ba);
|
||||||
return doubleQuote + QString::fromLocal8Bit(decodedBa) + doubleQuote;
|
return doubleQuote + QString::fromLocal8Bit(decodedBa) + doubleQuote;
|
||||||
}
|
}
|
||||||
|
case JulianDate: { // 14, an integer count
|
||||||
|
const QDate date = dateFromData(ba.toInt());
|
||||||
|
return date.toString(Qt::TextDate);
|
||||||
|
}
|
||||||
|
case MillisecondsSinceMidnight: {
|
||||||
|
const QTime time = timeFromData(ba.toInt());
|
||||||
|
return time.toString(Qt::TextDate);
|
||||||
|
}
|
||||||
|
case JulianDateAndMillisecondsSinceMidnight: {
|
||||||
|
const int p = ba.indexOf('/');
|
||||||
|
const QDate date = dateFromData(ba.left(p).toInt());
|
||||||
|
const QTime time = timeFromData(ba.mid(p + 1 ).toInt());
|
||||||
|
return QDateTime(date, time).toString(Qt::TextDate);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
qDebug() << "ENCODING ERROR: " << encoding;
|
qDebug() << "ENCODING ERROR: " << encoding;
|
||||||
return QCoreApplication::translate("Debugger", "<Encoding error>");
|
return QCoreApplication::translate("Debugger", "<Encoding error>");
|
||||||
|
@@ -56,20 +56,23 @@ class GdbMi;
|
|||||||
// Keep in sync with dumper.py
|
// Keep in sync with dumper.py
|
||||||
enum DebuggerEncoding
|
enum DebuggerEncoding
|
||||||
{
|
{
|
||||||
Unencoded8Bit = 0,
|
Unencoded8Bit = 0,
|
||||||
Base64Encoded8BitWithQuotes = 1,
|
Base64Encoded8BitWithQuotes = 1,
|
||||||
Base64Encoded16BitWithQuotes = 2,
|
Base64Encoded16BitWithQuotes = 2,
|
||||||
Base64Encoded32BitWithQuotes = 3,
|
Base64Encoded32BitWithQuotes = 3,
|
||||||
Base64Encoded16Bit = 4,
|
Base64Encoded16Bit = 4,
|
||||||
Base64Encoded8Bit = 5,
|
Base64Encoded8Bit = 5,
|
||||||
Hex2EncodedLatin1WithQuotes = 6,
|
Hex2EncodedLatin1WithQuotes = 6,
|
||||||
Hex4EncodedLittleEndianWithQuotes = 7,
|
Hex4EncodedLittleEndianWithQuotes = 7,
|
||||||
Hex8EncodedLittleEndianWithQuotes = 8,
|
Hex8EncodedLittleEndianWithQuotes = 8,
|
||||||
Hex2EncodedUtf8WithQuotes = 9,
|
Hex2EncodedUtf8WithQuotes = 9,
|
||||||
Hex8EncodedBigEndian = 10,
|
Hex8EncodedBigEndian = 10,
|
||||||
Hex4EncodedBigEndianWithQuotes = 11,
|
Hex4EncodedBigEndianWithQuotes = 11,
|
||||||
Hex4EncodedLittleEndianWithoutQuotes = 12,
|
Hex4EncodedLittleEndianWithoutQuotes = 12,
|
||||||
Hex2EncodedLocal8BitWithQuotes = 13
|
Hex2EncodedLocal8BitWithQuotes = 13,
|
||||||
|
JulianDate = 14,
|
||||||
|
MillisecondsSinceMidnight = 15,
|
||||||
|
JulianDateAndMillisecondsSinceMidnight = 16
|
||||||
};
|
};
|
||||||
|
|
||||||
bool isEditorDebuggable(Core::IEditor *editor);
|
bool isEditorDebuggable(Core::IEditor *editor);
|
||||||
|
@@ -40,13 +40,13 @@
|
|||||||
// lines containing the BREAK_HERE macro. This should be enabled
|
// lines containing the BREAK_HERE macro. This should be enabled
|
||||||
// during manual testing.
|
// during manual testing.
|
||||||
// Default: 1
|
// Default: 1
|
||||||
#define USE_AUTOBREAK 1
|
#define USE_AUTOBREAK 0
|
||||||
|
|
||||||
// With USE_UNINITIALIZE_AUTOBREAK, the debugger will stop automatically
|
// With USE_UNINITIALIZE_AUTOBREAK, the debugger will stop automatically
|
||||||
// on all lines containing the BREAK_UNINITIALIZED_HERE macro.
|
// on all lines containing the BREAK_UNINITIALIZED_HERE macro.
|
||||||
// This should be enabled during manual testing.
|
// This should be enabled during manual testing.
|
||||||
// Default: 1
|
// Default: 1
|
||||||
#define USE_UNINITIALIZED_AUTOBREAK 1
|
#define USE_UNINITIALIZED_AUTOBREAK 0
|
||||||
|
|
||||||
// With USE_PRIVATE tests that require private headers are enabled.
|
// With USE_PRIVATE tests that require private headers are enabled.
|
||||||
// Default: 1
|
// Default: 1
|
||||||
@@ -2758,7 +2758,7 @@ namespace basic {
|
|||||||
QDateTime time = QDateTime::currentDateTime();
|
QDateTime time = QDateTime::currentDateTime();
|
||||||
const int N = 10000;
|
const int N = 10000;
|
||||||
QDateTime bigv[N];
|
QDateTime bigv[N];
|
||||||
for (int i = 0; i < N; ++i) {
|
for (int i = 0; i < 10000; ++i) {
|
||||||
bigv[i] = time;
|
bigv[i] = time;
|
||||||
time.addDays(1);
|
time.addDays(1);
|
||||||
}
|
}
|
||||||
@@ -2772,7 +2772,7 @@ namespace basic {
|
|||||||
{
|
{
|
||||||
const int N = 10000;
|
const int N = 10000;
|
||||||
int bigv[N];
|
int bigv[N];
|
||||||
for (int i = 0; i < N; ++i)
|
for (int i = 0; i < 10000; ++i)
|
||||||
bigv[i] = i;
|
bigv[i] = i;
|
||||||
BREAK_HERE;
|
BREAK_HERE;
|
||||||
// Expand bigv.
|
// Expand bigv.
|
||||||
|
Reference in New Issue
Block a user