[Development] Tracing Qt

Philip Ashmore contact at philipashmore.com
Sat Aug 24 01:24:00 CEST 2013


On 23/08/13 12:59, Blasche Alexander wrote:
> Hi Robin,
> 
> I am not sure whether you are aware of http://qt.gitorious.org/qtplayground/qlogger
> 
> It is pretty much what you describe. It was even close to a merge into qtcore already (only rejected due to feature freeze). It gives you a complete API including ways to integrate with qDebug/qWarning, runtime activation, little to no overhead when deactivated and there was reasonably broad agreement already. Also see:
> 
> http://lists.qt-project.org/pipermail/development/2012-December/008886.html
> 
> If you have spare cycles to actually make this happen I would propose you start with a 95% done system rather than new.
> 
> --
> Alex
For a tracing system to be useful and stand a chance of being adopted by
the libraries used by Qt as well as Qt itself, it shouldn't be part of Qt.

My humble attempt is available as part of v3c:

http://sourceforge.net/projects/v3c/

It has commits going back to 2011 but I deleted the earlier ones so it's
even older.

You can control tracing at compile time, link time and runtime.
You can cache trace output and only dump it if it's noteworthy, e.g. if
something went wrong or a corner case is hit.

This uses a stringstream to cache the trace output.

This will be available in the next version - the one I'm using with my
projects now (the version in SourceForge has the TraceCache macro but I
never got around to using/testing it until recently).

Some examples:
void fn(int a, int x)
{
    TraceWrap(__PRETTY_FUNCTION__ << " a: " << a);
    trace << "the value of x is " << x << '.' << endl;
}

It has a pluggable architecture, but the main application decides if
trace output goes to cout, cerr or a file or nowhere.

It doesn't have module-level trace control but that could be added.

Regards,
Philip Ashmore
> 
> ________________________________________
> From: development-bounces+alexander.blasche=digia.com at qt-project.org [development-bounces+alexander.blasche=digia.com at qt-project.org] on behalf of Robin Burchell [robin+qt at viroteck.net]
> Sent: Friday, August 23, 2013 13:20
> To: development at qt-project.org
> Cc: Poenitz Andre
> Subject: [Development] Tracing Qt
> 
> Hi,
> 
> (apologies in advance for the wall of text)
> 
> It's inevitable when working with Qt that sooner or later, you
> probably have a desire to work on tracing Qt - or at least part of it.
> Qt Creator's QML profiler is one such very prominent example of an
> area where this may be useful, but there are many others: usually
> sprinkled around Qt hidden behind various defines, environment
> variables, and other hard-to-find places. This makes digging into a
> problem somewhat hard, unless you are (or can be handheld by) a Qt
> expert when you start digging.
> 
> It's also a bit of a problem in that each of these methods uses
> different ways to communicate information, meaning it is difficult to
> write tooling to inspect this data and visualise it. We also miss out
> on tracing in a number of areas that *could* potentially be valuable,
> such as touch event processing, the event loop, the sky's the limit.
> 
> Thanks to Carsten and Andre for their input in hashing the details of
> this proposal out.
> 
> Proposal
> ========
> 
> Let's look at unifying tracing inside Qt. Let's add code to Qt itself
> to enable easy introspection of what exactly is going on.
> 
> When looking at tracing, it can be boiled down into two levels - an
> area (which may be a feature being inspected, or a subsystem - for
> instance, QML performance, vsync timestamps, ...) containing events,
> so from this, we can gather that we need a way to categorise logging
> by area, and the capability to switch logging on by area.
> 
> An area should be associated with a simple numeric identifier to avoid
> expensive code when manipulating events, but there will be some form
> of name => id mapping (for the environment variable below, for
> instance).
> 
> Suggested area-based API:
> enum TraceArea {
>     TraceAreaDrawing (drawing event, frame event)
>     ... other areas as required
>     TraceAreaUser = 1000 // held for possible future expansion into
> allowing dynamic area registration
> }
> 
> QT_ENABLE_TRACE=inputevents,frameevents,magicalmonkeyevents
> rationale: providing system-wide defaults enables tracing of
> system-wide behaviour is very useful. Being able to inspect exactly
> what an entire set of Qt-based applications are doing while a user is
> interacting with it would be a useful thing.
> 
> enable_trace(TraceArea area)
> disable_trace(TraceArea area)
> rationale: a developer may want to turn tracing of an individual area
> on/off at runtime, as they start something they are particularly
> interested in tracing. This has some inspiration in
> CALLGRIND_START_INSTRUMENTATION/CALLGRIND_STOP_INSTRUMENTATION also.
> 
> Along with this user-facing API, we also need some mechanism to enable
> different applications of the tracing data (for instance, the QML
> profiler from Creator, Android's systrace
> https://developer.android.com/tools/help/systrace.html, plain console
> logging, etc). Multiple tracers should be able to handle a single
> area. Tracers would live in seperate plugins.
> 
> Example tracer API:
> class QTracer { virtual void logStart() = 0; virtual void logEnd() = 0; }
> 
> QTracer subclasses would register their interest in a particular event
> type on construction:
> 
> struct MyCoolConsoleTracer : public QTracer {
>     MyCoolConsoleTracer() : QTracer() {
>         q_register_tracer_for_area(this, TraceAreaDrawing); // we are
> interested in this particular event type
>     }
> 
>     virtual void logStart() {
>         qDebug() << "Trace event for drawing, start: " <<
> QDateTime::currentMSecsSinceEpoch()
>     }
>     virtual void logEnd() {
>         qDebug() << "Trace event for drawing, end: " <<
> QDateTime::currentMSecsSinceEpoch()
>     }
> };
> 
> The invocation of tracer subclasses is controlled by a simple RAII class:
> 
> struct QTraceEvent {
>     QTraceEvent(TraceArea area); // invokes logStart on all interested tracers
>     ~QTraceEvent(); // invokes logEnd on all interested tracers
> }
> 
> Example use being something like:
> 
> void draw() {
>     QTraceEvent e(TraceAreaDrawing);
>     // do painting
>     paintOnScreen();
> }
> 
> Thoughts, flames, cookies?
> 
> BR,
> Robin
> (with jolla hat on)
> _______________________________________________
> Development mailing list
> Development at qt-project.org
> http://lists.qt-project.org/mailman/listinfo/development
> _______________________________________________
> Development mailing list
> Development at qt-project.org
> http://lists.qt-project.org/mailman/listinfo/development
> 



More information about the Development mailing list