LibreOffice Module comphelper (master) 1
traceevent.hxx
Go to the documentation of this file.
1/* -*- Mode: C; tab-width: 4; indent-tabs-mode: nil; c-basic-offset: 4; fill-column: 100 -*- */
2/*
3 * This file is part of the LibreOffice project.
4 *
5 * This Source Code Form is subject to the terms of the Mozilla Public
6 * License, v. 2.0. If a copy of the MPL was not distributed with this
7 * file, You can obtain one at http://mozilla.org/MPL/2.0/.
8*/
9
10#ifndef INCLUDED_COMPHELPER_TRACEEVENT_HXX
11#define INCLUDED_COMPHELPER_TRACEEVENT_HXX
12
13#include <sal/config.h>
14
15#include <atomic>
16#include <map>
17#include <memory>
18#include <utility>
19#include <vector>
20
21#include <osl/process.h>
22#include <osl/thread.h>
23#include <osl/time.h>
24#include <com/sun/star/uno/Sequence.h>
26#include <rtl/ustrbuf.hxx>
27#include <rtl/ustring.hxx>
28
29// implementation of XToolkitExperimental profiling API
30
31namespace comphelper
32{
34{
35private:
36 static int getPid()
37 {
38 oslProcessInfo aProcessInfo;
39 aProcessInfo.Size = sizeof(oslProcessInfo);
40 if (osl_getProcessInfo(nullptr, osl_Process_IDENTIFIER, &aProcessInfo)
41 == osl_Process_E_None)
42 return aProcessInfo.Ident;
43 return -1;
44 }
45
46 static std::size_t s_nBufferSize;
47 static void (*s_pBufferFullCallback)();
48
49protected:
50 static std::atomic<bool> s_bRecording; // true during recording
51
52 static void addRecording(const OUString& sObject);
53
54 static long long getNow()
55 {
56 TimeValue systemTime;
57 osl_getSystemTime(&systemTime);
58 return static_cast<long long>(systemTime.Seconds) * 1000000 + systemTime.Nanosec / 1000;
59 }
60
61 static OUString createArgsString(const std::map<OUString, OUString>& args)
62 {
63 if (args.size() == 0)
64 return "";
65
66 OUStringBuffer sResult(",\"args\":{");
67 bool first = true;
68 for (auto& i : args)
69 {
70 if (!first)
71 sResult.append(',');
72 sResult.append("\"" + i.first + "\":\"" + i.second + "\"");
73 first = false;
74 }
75 sResult.append('}');
76
77 return sResult.makeStringAndClear();
78 }
79
80 const int m_nPid;
81 const OUString m_sArgs;
82
83 TraceEvent(OUString sArgs)
84 : m_nPid(s_bRecording ? getPid() : 1)
85 , m_sArgs(std::move(sArgs))
86 {
87 }
88
89 TraceEvent(const std::map<OUString, OUString>& aArgs)
90 : TraceEvent(createArgsString(aArgs))
91 {
92 }
93
94public:
95 static void addInstantEvent(const char* sName, const std::map<OUString, OUString>& args
96 = std::map<OUString, OUString>());
97
98 static void startRecording();
99 static void stopRecording();
100 static void setBufferSizeAndCallback(std::size_t bufferSize, void (*bufferFullCallback)());
101
102 static std::vector<OUString> getEventVectorAndClear();
103
104 static css::uno::Sequence<OUString> getRecordingAndClear();
105};
106
108{
109protected:
110 const char* m_sName;
111
112 NamedEvent(const char* sName, const OUString& sArgs)
113 : TraceEvent(sArgs)
114 , m_sName(sName ? sName : "(null)")
115 {
116 }
117
118 NamedEvent(const char* sName, const std::map<OUString, OUString>& aArgs)
119 : TraceEvent(aArgs)
120 , m_sName(sName ? sName : "(null)")
121 {
122 }
123};
124
125// An AsyncEvent generates an 'S' (start) event when constructed and a 'F' (finish) event when it
126// is destructed.
127
128// The Trace Event specification claims that these event types are deprecated and replaces by
129// nestable 'b' (begin) and 'e' (end) events, but Chrome does not seem to support those.
130
131// To generate a pair of 'S' and 'F' events, create an AsyncEvent object using the AsyncEvent(const
132// char* sName) constructor when you want the 'S' event to be generated, and destroy it when you
133// want the corresponding 'F' event to be generated.
134
136 public std::enable_shared_from_this<AsyncEvent>
137{
138 static int s_nIdCounter;
139 int m_nId;
141
142 AsyncEvent(const char* sName, int nId, const std::map<OUString, OUString>& args)
144 , m_nId(nId)
145 , m_bBeginRecorded(false)
146 {
147 if (!s_bRecording)
148 return;
149
150 long long nNow = getNow();
151
152 // Generate a "Start" (type S) event
154 "\"name\":\""
155 + OUString(m_sName, strlen(m_sName), RTL_TEXTENCODING_UTF8)
156 + "\","
157 "\"ph\":\"S\""
158 ","
159 "\"id\":"
160 + OUString::number(m_nId) + m_sArgs
161 + ","
162 "\"ts\":"
163 + OUString::number(nNow)
164 + ","
165 "\"pid\":"
166 + OUString::number(m_nPid)
167 + ","
168 "\"tid\":"
169 + OUString::number(osl_getThreadIdentifier(nullptr)) + "},");
170 m_bBeginRecorded = true;
171 }
172
174 {
175 if (!m_bBeginRecorded)
176 return;
177
178 m_bBeginRecorded = false;
179
180 long long nNow = getNow();
181 // Generate a "Finish" (type F) event
183 "\"name\":\""
184 + OUString(m_sName, strlen(m_sName), RTL_TEXTENCODING_UTF8)
185 + "\","
186 "\"ph\":\"F\""
187 ","
188 "\"id\":"
189 + OUString::number(m_nId) + m_sArgs
190 + ","
191 "\"ts\":"
192 + OUString::number(nNow)
193 + ","
194 "\"pid\":"
195 + OUString::number(m_nPid)
196 + ","
197 "\"tid\":"
198 + OUString::number(osl_getThreadIdentifier(nullptr)) + "},");
199 }
200
201public:
202 AsyncEvent(const char* sName,
203 const std::map<OUString, OUString>& args = std::map<OUString, OUString>())
204 : AsyncEvent(sName, s_nIdCounter++, args)
205 {
206 }
207
208 ~AsyncEvent() { generateEnd(); }
209
210 void finish() { generateEnd(); }
211};
212
213} // namespace comphelper
214
215#endif // INCLUDED_COMPHELPER_TRACEEVENT_HXX
216
217/* vim:set shiftwidth=4 softtabstop=4 expandtab: */
AsyncEvent(const char *sName, const std::map< OUString, OUString > &args=std::map< OUString, OUString >())
Definition: traceevent.hxx:202
AsyncEvent(const char *sName, int nId, const std::map< OUString, OUString > &args)
Definition: traceevent.hxx:142
NamedEvent(const char *sName, const std::map< OUString, OUString > &aArgs)
Definition: traceevent.hxx:118
NamedEvent(const char *sName, const OUString &sArgs)
Definition: traceevent.hxx:112
TraceEvent(OUString sArgs)
Definition: traceevent.hxx:83
const OUString m_sArgs
Definition: traceevent.hxx:81
static std::size_t s_nBufferSize
Definition: traceevent.hxx:46
static void addRecording(const OUString &sObject)
Definition: traceevent.cxx:41
static std::atomic< bool > s_bRecording
Definition: traceevent.hxx:50
static long long getNow()
Definition: traceevent.hxx:54
TraceEvent(const std::map< OUString, OUString > &aArgs)
Definition: traceevent.hxx:89
static OUString createArgsString(const std::map< OUString, OUString > &args)
Definition: traceevent.hxx:61
#define COMPHELPER_DLLPUBLIC
OUString m_sName
OUString sName
int i
constexpr OUStringLiteral first
args
sal_Int16 nId