forked from aristanetworks/quicktrace-public
-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathQtFmtGeneric.h
307 lines (274 loc) · 19.3 KB
/
QtFmtGeneric.h
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
// Copyright (c) 2021, Arista Networks, Inc.
// All rights reserved.
// Redistribution and use in source and binary forms, with or without modification,
// are permitted provided that the following conditions are met:
// * Redistributions of source code must retain the above copyright notice,
// this list of conditions and the following disclaimer.
// * Redistributions in binary form must reproduce the above copyright notice,
// this list of conditions and the following disclaimer in the documentation
// and/or other materials provided with the distribution.
// * Neither the name of Arista Networks nor the names of its contributors may
// be used to endorse or promote products derived from this software without
// specific prior written permission.
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
// ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
// WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
// IN NO EVENT SHALL ARISTA NETWORKS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR
// BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
// CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN
// ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
// SUCH DAMAGE.
#ifndef QUICKTRACE_QTFMT_H
#define QUICKTRACE_QTFMT_H
#include <QuickTrace/QuickTrace.h>
namespace QuickTrace {
// This function decodes a std-style format specification, turning {} and {:x}
// to corresponding calls to QVAR and QHEX, and copying anything else.
// To escape '{' and '}', use {{ and }}.
// If className is a nullptr, we'll omit tracing the className and the funcName.
// If className is an empty, we'll only trace the function name.
void msgDesc( QuickTrace::MsgDesc & qtmd,
const char * className,
const char * funcName,
const char * fmtString ) noexcept;
template< typename... Ts >
constexpr void
msgIdInit( QuickTrace::MsgDesc & qtmd,
const char * className,
const char * funcName,
const char * fmtString,
Ts &&... args ) noexcept {
( ( qtmd.formatString() << std::forward< Ts >( args ) ), ... );
msgDesc( qtmd, className, funcName, fmtString );
qtmd.finish();
}
template< typename... Ts >
constexpr uint64_t
fmtMsg( QuickTrace::RingBuf & rb,
QuickTrace::TraceFile * tf,
QuickTrace::MsgId id,
Ts &&... args ) noexcept {
uint64_t tsc = rb.startMsg( tf, id );
( ( rb << std::forward< Ts >( args ) ), ... );
rb.endMsg();
return tsc;
}
} // namespace QuickTrace
#define QTFMT_H_MSGID_INIT_FMT( _qtf, _msgId, className, funcName, fmtString, ... ) \
if ( unlikely( !!( _qtf ) && !( _qtf )->msgIdInitialized( _msgId ) ) ) { \
QuickTrace::MsgDesc _qtmd( _qtf, &_msgId, __FILE__, __LINE__ ); \
QuickTrace::msgIdInit( \
_qtmd, className, funcName, fmtString, ##__VA_ARGS__ ); \
}
#define QTFMT_MSGID_VAR( \
_qtf, _msgId, _rb, _n, className, funcName, fmtString, ... ) \
QTFMT_H_MSGID_INIT_FMT( \
_qtf, _msgId, className, funcName, fmtString, ##__VA_ARGS__ ); \
QuickTrace::RingBuf & _rb = ( _qtf )->log( _n ); \
QuickTrace::fmtMsg( _rb, _qtf, _msgId, ##__VA_ARGS__ );
#define QTFMT_H_MSGID( _qtf, _msgId, _n, className, funcName, fmtString, ... ) \
QTFMT_MSGID_VAR( _qtf, \
_msgId, \
qtvar( _rb ), \
_n, \
className, \
funcName, \
fmtString, \
##__VA_ARGS__ )
#define QTFMT_INTERNAL_H( _qtf, _n, className, fmtString, ... ) \
do { \
static QuickTrace::MsgId _msgId; \
if ( likely( !!( _qtf ) ) ) { \
QTFMT_H_MSGID( \
_qtf, _msgId, _n, className, __func__, fmtString, ##__VA_ARGS__ ); \
} \
} while ( 0 )
// qtraceClassName is a macro that will be defined by non-generic users, and will be
// used to inject an appropriate class name.
#define QTFMT_H( _qtf, _n, fmtString, ... ) \
QTFMT_INTERNAL_H( _qtf, _n, qtraceClassName, fmtString, ##__VA_ARGS__ )
#define QTFMT0( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT1( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT2( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT3( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT4( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT5( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT6( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT7( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT8( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT9( fmtString, ... ) \
QTFMT_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
#define QTFMT0_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 0, fmtString, ##__VA_ARGS__ )
#define QTFMT1_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 1, fmtString, ##__VA_ARGS__ )
#define QTFMT2_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 2, fmtString, ##__VA_ARGS__ )
#define QTFMT3_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 3, fmtString, ##__VA_ARGS__ )
#define QTFMT4_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 4, fmtString, ##__VA_ARGS__ )
#define QTFMT5_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 5, fmtString, ##__VA_ARGS__ )
#define QTFMT6_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 6, fmtString, ##__VA_ARGS__ )
#define QTFMT7_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 7, fmtString, ##__VA_ARGS__ )
#define QTFMT8_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 8, fmtString, ##__VA_ARGS__ )
#define QTFMT9_F( fmtString, ... ) \
QTFMT_H( ( hdl )->getFile(), 9, fmtString, ##__VA_ARGS__ )
#define QTFMT_FUNC_H( _qtf, _n, fmtString, ... ) \
QTFMT_INTERNAL_H( _qtf, _n, "", fmtString, ##__VA_ARGS__ )
#define QTFMT0_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT1_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT2_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT3_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT4_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT5_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT6_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT7_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT8_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT9_FUNC( fmtString, ... ) \
QTFMT_FUNC_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
#define QTFMT_RAW_H( _qtf, _n, fmtString, ... ) \
QTFMT_INTERNAL_H( _qtf, _n, nullptr, fmtString, ##__VA_ARGS__ )
#define QTFMT0_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT1_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT2_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT3_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT4_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT5_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT6_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT7_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT8_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT9_RAW( fmtString, ... ) \
QTFMT_RAW_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
#define QTFMT_ASSERT( _cond, fmtString, ... ) \
if ( unlikely( !( _cond ) ) ) { \
QTFMT0( fmtString, ##__VA_ARGS__ ) \
assert( _cond ); \
}
#define QTFMT_PROF_INTERNAL_H( _qtf, _n, className, fmtString, ... ) \
QTFMT_PROF_H_VAR( \
_qtf, qtvar( msgid ), _n, className, __func__, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF_H( _qtf, _n, fmtString, ... ) \
QTFMT_PROF_INTERNAL_H( _qtf, _n, qtraceClassName, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF_H_VAR( _qtf, _msgId, _n, className, funcName, fmtString, ... ) \
static QuickTrace::MsgId _msgId; \
QTFMT_PROF_H_MSGID_VAR( _qtf, \
_msgId, \
qtvar( tsc ), \
_n, \
className, \
funcName, \
fmtString, \
##__VA_ARGS__ )
#define QTFMT_PROF_H_MSGID_VAR( \
_qtf, _msgId, _tsc, _n, className, funcName, fmtString, ... ) \
uint64_t _tsc; \
if ( likely( !!( _qtf ) ) ) { \
QTFMT_H_MSGID_INIT_FMT( \
_qtf, _msgId, className, funcName, fmtString, ##__VA_ARGS__ ); \
QuickTrace::RingBuf & _rb = ( _qtf )->log( _n ); \
qtvar( tsc ) = QuickTrace::fmtMsg( _rb, _qtf, _msgId, ##__VA_ARGS__ ); \
} else { \
_tsc = 0; \
} \
QuickTrace::BlockTimerMsg qtvar( bt )( ( _qtf ), _msgId, _tsc )
#define QTFMT_PROF0( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF1( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF2( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF3( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF4( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF5( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF6( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF7( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF8( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF9( fmtString, ... ) \
QTFMT_PROF_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF_FUNC_H( _qtf, _n, fmtString, ... ) \
QTFMT_PROF_INTERNAL_H( _qtf, _n, "", fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF0_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF1_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF2_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF3_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF4_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF5_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF6_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF7_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF8_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF9_FUNC( fmtString, ... ) \
QTFMT_PROF_FUNC_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF_RAW_H( _qtf, _n, fmtString, ... ) \
QTFMT_PROF_INTERNAL_H( _qtf, _n, nullptr, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF0_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 0, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF1_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 1, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF2_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 2, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF3_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 3, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF4_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 4, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF5_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 5, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF6_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 6, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF7_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 7, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF8_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 8, fmtString, ##__VA_ARGS__ )
#define QTFMT_PROF9_RAW( fmtString, ... ) \
QTFMT_PROF_RAW_H( QuickTrace::theTraceFile, 9, fmtString, ##__VA_ARGS__ )
// TODO: QPROF_F
// TODO: QPROF_S
#endif // QUICKTRACE_QTFMT_H