aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/libs/tracing/safecastable.h62
-rw-r--r--src/libs/tracing/traceevent.h10
-rw-r--r--src/libs/tracing/traceeventtype.h10
-rw-r--r--src/libs/tracing/tracing.pro1
-rw-r--r--src/libs/tracing/tracing.qbs1
-rw-r--r--src/plugins/qmlprofiler/qmlevent.h10
-rw-r--r--src/plugins/qmlprofiler/qmleventtype.cpp2
-rw-r--r--src/plugins/qmlprofiler/qmleventtype.h2
-rw-r--r--src/plugins/qmlprofiler/qmlprofilermodelmanager.cpp26
9 files changed, 106 insertions, 18 deletions
diff --git a/src/libs/tracing/safecastable.h b/src/libs/tracing/safecastable.h
new file mode 100644
index 0000000000..7c1fae2e7a
--- /dev/null
+++ b/src/libs/tracing/safecastable.h
@@ -0,0 +1,62 @@
+/****************************************************************************
+**
+** Copyright (C) 2018 The Qt Company Ltd.
+** Contact: https://www.qt.io/licensing/
+**
+** This file is part of Qt Creator.
+**
+** Commercial License Usage
+** Licensees holding valid commercial Qt licenses may use this file in
+** accordance with the commercial license agreement provided with the
+** Software or, alternatively, in accordance with the terms contained in
+** a written agreement between you and The Qt Company. For licensing terms
+** and conditions see https://www.qt.io/terms-conditions. For further
+** information use the contact form at https://www.qt.io/contact-us.
+**
+** GNU General Public License Usage
+** Alternatively, this file may be used under the terms of the GNU
+** General Public License version 3 as published by the Free Software
+** Foundation with exceptions as appearing in the file LICENSE.GPL3-EXCEPT
+** included in the packaging of this file. Please review the following
+** information to ensure the GNU General Public License requirements will
+** be met: https://www.gnu.org/licenses/gpl-3.0.html.
+**
+****************************************************************************/
+
+#pragma once
+
+namespace Timeline {
+
+template<class Base>
+class SafeCastable
+{
+public:
+ template<class Derived>
+ bool is() const
+ {
+ return static_cast<const Base *>(this)->classId() == Derived::staticClassId;
+ }
+
+ template<class Derived>
+ Derived &asRef()
+ {
+ Q_ASSERT(is<Derived>());
+ return static_cast<Derived &>(*this);
+ }
+
+ template<class Derived>
+ const Derived &asConstRef() const
+ {
+ Q_ASSERT(is<Derived>());
+ return static_cast<const Derived &>(*this);
+ }
+
+ template<class Derived>
+ Derived &&asRvalueRef()
+ {
+ Q_ASSERT(is<Derived>());
+ return static_cast<Derived &&>(*this);
+ }
+};
+
+} // namespace Timeline
diff --git a/src/libs/tracing/traceevent.h b/src/libs/tracing/traceevent.h
index 780ebf7ad9..7f097315eb 100644
--- a/src/libs/tracing/traceevent.h
+++ b/src/libs/tracing/traceevent.h
@@ -26,13 +26,14 @@
#pragma once
#include "tracing_global.h"
+#include "safecastable.h"
#include <QHash>
#include <QMetaType>
namespace Timeline {
-class TraceEvent
+class TraceEvent : public SafeCastable<TraceEvent>
{
public:
qint64 timestamp() const { return m_timestamp; }
@@ -43,9 +44,11 @@ public:
bool isValid() const { return m_typeIndex != -1; }
+ qint32 classId() const { return m_classId; }
+
protected:
- TraceEvent(qint64 timestamp = -1, qint32 typeIndex = -1)
- : m_timestamp(timestamp), m_typeIndex(typeIndex)
+ TraceEvent(qint32 classId, qint64 timestamp = -1, qint32 typeIndex = -1)
+ : m_timestamp(timestamp), m_typeIndex(typeIndex), m_classId(classId)
{}
TraceEvent(const TraceEvent &) = default;
@@ -56,6 +59,7 @@ protected:
private:
qint64 m_timestamp;
qint32 m_typeIndex;
+ qint32 m_classId;
};
} // namespace Timeline
diff --git a/src/libs/tracing/traceeventtype.h b/src/libs/tracing/traceeventtype.h
index 58a3e180cd..9a667d6fd7 100644
--- a/src/libs/tracing/traceeventtype.h
+++ b/src/libs/tracing/traceeventtype.h
@@ -26,6 +26,7 @@
#pragma once
#include "tracing_global.h"
+#include "safecastable.h"
#include <QHash>
#include <QMetaType>
@@ -33,7 +34,7 @@
namespace Timeline {
-class TraceEventType
+class TraceEventType : public SafeCastable<TraceEventType>
{
public:
const QString &displayName() const { return m_displayName; }
@@ -42,9 +43,11 @@ public:
quint8 feature() const { return m_feature; }
void setFeature(quint8 feature) { m_feature = feature; }
+ qint32 classId() const { return m_classId; }
+
protected:
- TraceEventType(quint8 feature = 255, const QString &displayName = QString())
- : m_displayName(displayName), m_feature(feature)
+ TraceEventType(qint32 classId, quint8 feature = 255, const QString &displayName = QString())
+ : m_displayName(displayName), m_classId(classId), m_feature(feature)
{}
TraceEventType(const TraceEventType &) = default;
@@ -54,6 +57,7 @@ protected:
private:
QString m_displayName;
+ qint32 m_classId;
quint8 m_feature;
};
diff --git a/src/libs/tracing/tracing.pro b/src/libs/tracing/tracing.pro
index 1ef079a20b..a12f03a860 100644
--- a/src/libs/tracing/tracing.pro
+++ b/src/libs/tracing/tracing.pro
@@ -25,6 +25,7 @@ SOURCES += \
HEADERS += \
$$PWD/flamegraph.h \
$$PWD/flamegraphattached.h \
+ $$PWD/safecastable.h \
$$PWD/tracing_global.h \
$$PWD/timelinemodel.h \
$$PWD/timelinemodel_p.h \
diff --git a/src/libs/tracing/tracing.qbs b/src/libs/tracing/tracing.qbs
index d91c765db0..4705d9adc7 100644
--- a/src/libs/tracing/tracing.qbs
+++ b/src/libs/tracing/tracing.qbs
@@ -17,6 +17,7 @@ Project {
"README",
"flamegraph.cpp", "flamegraph.h",
"flamegraphattached.h",
+ "safecastable.h",
"timelineabstractrenderer.cpp", "timelineabstractrenderer.h",
"timelineabstractrenderer_p.h",
"timelineformattime.cpp", "timelineformattime.h",
diff --git a/src/plugins/qmlprofiler/qmlevent.h b/src/plugins/qmlprofiler/qmlevent.h
index 23a62cb643..3f999d419e 100644
--- a/src/plugins/qmlprofiler/qmlevent.h
+++ b/src/plugins/qmlprofiler/qmlevent.h
@@ -39,24 +39,26 @@
namespace QmlProfiler {
struct QmlEvent : public Timeline::TraceEvent {
- QmlEvent() : m_dataType(Inline8Bit), m_dataLength(0) {}
+ static const qint32 staticClassId = 0x716d6c65; // 'qmle';
+
+ QmlEvent() : TraceEvent(staticClassId), m_dataType(Inline8Bit), m_dataLength(0) {}
template<typename Number>
QmlEvent(qint64 timestamp, int typeIndex, std::initializer_list<Number> list)
- : TraceEvent(timestamp, typeIndex)
+ : TraceEvent(staticClassId, timestamp, typeIndex)
{
assignNumbers<std::initializer_list<Number>, Number>(list);
}
QmlEvent(qint64 timestamp, int typeIndex, const QString &data)
- : TraceEvent(timestamp, typeIndex)
+ : TraceEvent(staticClassId, timestamp, typeIndex)
{
assignNumbers<QByteArray, qint8>(data.toUtf8());
}
template<typename Number>
QmlEvent(qint64 timestamp, int typeIndex, const QVector<Number> &data)
- : TraceEvent(timestamp, typeIndex)
+ : TraceEvent(staticClassId, timestamp, typeIndex)
{
assignNumbers<QVector<Number>, Number>(data);
}
diff --git a/src/plugins/qmlprofiler/qmleventtype.cpp b/src/plugins/qmlprofiler/qmleventtype.cpp
index 9cb99c0081..88a3d6dd47 100644
--- a/src/plugins/qmlprofiler/qmleventtype.cpp
+++ b/src/plugins/qmlprofiler/qmleventtype.cpp
@@ -79,7 +79,7 @@ QDataStream &operator<<(QDataStream &stream, const QmlEventType &type)
QmlEventType::QmlEventType(Message message, RangeType rangeType, int detailType,
const QmlEventLocation &location, const QString &data,
const QString displayName) :
- TraceEventType(qmlFeatureFromType(message, rangeType, detailType)),
+ TraceEventType(staticClassId, qmlFeatureFromType(message, rangeType, detailType)),
m_data(data), m_location(location), m_message(message),
m_rangeType(rangeType), m_detailType(detailType)
{
diff --git a/src/plugins/qmlprofiler/qmleventtype.h b/src/plugins/qmlprofiler/qmleventtype.h
index 6c3fc53e06..1e038e634e 100644
--- a/src/plugins/qmlprofiler/qmleventtype.h
+++ b/src/plugins/qmlprofiler/qmleventtype.h
@@ -37,6 +37,8 @@ namespace QmlProfiler {
class QmlEventType : public Timeline::TraceEventType {
public:
+ static const qint32 staticClassId = 0x716d6c74; // 'qmlt';
+
QmlEventType(Message message = MaximumMessage, RangeType rangeType = MaximumRangeType,
int detailType = -1, const QmlEventLocation &location = QmlEventLocation(),
const QString &data = QString(), const QString displayName = QString());
diff --git a/src/plugins/qmlprofiler/qmlprofilermodelmanager.cpp b/src/plugins/qmlprofiler/qmlprofilermodelmanager.cpp
index c54c7f0981..2d02c10afd 100644
--- a/src/plugins/qmlprofiler/qmlprofilermodelmanager.cpp
+++ b/src/plugins/qmlprofiler/qmlprofilermodelmanager.cpp
@@ -148,8 +148,9 @@ void QmlProfilerModelManager::registerFeatures(quint64 features, QmlEventLoader
{
const TraceEventLoader traceEventLoader = eventLoader ? [eventLoader](
const Timeline::TraceEvent &event, const Timeline::TraceEventType &type) {
- return eventLoader(static_cast<const QmlEvent &>(event),
- static_cast<const QmlEventType &>(type));
+ QTC_ASSERT(event.is<QmlEvent>(), return);
+ QTC_ASSERT(type.is<QmlEventType>(), return);
+ eventLoader(event.asConstRef<QmlEvent>(), type.asConstRef<QmlEventType>());
} : TraceEventLoader();
Timeline::TimelineTraceManager::registerFeatures(features, traceEventLoader, initializer,
@@ -158,7 +159,10 @@ void QmlProfilerModelManager::registerFeatures(quint64 features, QmlEventLoader
const QmlEventType &QmlProfilerModelManager::eventType(int typeId) const
{
- return static_cast<const QmlEventType &>(TimelineTraceManager::eventType(typeId));
+ static const QmlEventType invalid;
+ const Timeline::TraceEventType &type = TimelineTraceManager::eventType(typeId);
+ QTC_ASSERT(type.is<QmlEventType>(), return invalid);
+ return type.asConstRef<QmlEventType>();
}
void QmlProfilerModelManager::replayEvents(TraceEventLoader loader, Initializer initializer,
@@ -190,7 +194,8 @@ void QmlProfilerModelManager::replayQmlEvents(QmlEventLoader loader,
if (future.isCanceled())
return false;
- loader(static_cast<QmlEvent &&>(event), eventType(event.typeIndex()));
+ QTC_ASSERT(event.is<QmlEvent>(), return false);
+ loader(event.asRvalueRef<QmlEvent>(), eventType(event.typeIndex()));
return true;
});
@@ -462,13 +467,19 @@ void QmlProfilerEventTypeStorage::set(int typeId, Timeline::TraceEventType &&typ
const size_t index = static_cast<size_t>(typeId);
if (m_types.size() <= index)
m_types.resize(index + 1);
- m_types[index] = std::move(static_cast<QmlEventType &&>(type));
+ QTC_ASSERT(type.is<QmlEventType>(), return);
+ m_types[index] = std::move(type.asRvalueRef<QmlEventType>());
}
int QmlProfilerEventTypeStorage::append(Timeline::TraceEventType &&type)
{
const size_t index = m_types.size();
- m_types.push_back(std::move(static_cast<QmlEventType &&>(type)));
+ if (type.is<QmlEventType>()) {
+ m_types.push_back(std::move(type.asRvalueRef<QmlEventType>()));
+ } else {
+ QTC_CHECK(false);
+ m_types.push_back(QmlEventType());
+ }
QTC_ASSERT(index <= std::numeric_limits<int>::max(), return std::numeric_limits<int>::max());
return static_cast<int>(index);
}
@@ -495,7 +506,8 @@ QmlProfilerEventStorage::QmlProfilerEventStorage(
int QmlProfilerEventStorage::append(Timeline::TraceEvent &&event)
{
- m_file.append(std::move(static_cast<QmlEvent &&>(event)));
+ QTC_ASSERT(event.is<QmlEvent>(), return m_size);
+ m_file.append(std::move(event.asRvalueRef<QmlEvent>()));
return m_size++;
}