T.h 16.5 KB
Newer Older
1
2
3
4
5
6
7
8
9
#ifndef _T_T_T_
#define _T_T_T_

#if T_TRACER

#include <stdint.h>

#include "T_defs.h"

Cedric Roux's avatar
Cedric Roux committed
10
11
12
13
#ifdef T_SEND_TIME
#include <time.h>
#endif

14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
/* T message IDs */
#include "T_IDs.h"

/* known type - this is where you add new types */

#define T_INT(x) int, (x)
#define T_FLOAT(x) float, (x)
#define T_BUFFER(x, len) buffer, ((T_buffer){addr:(x), length:(len)})
#define T_STRING(x) string, (x)
#define T_PRINTF(...) printf, (__VA_ARGS__)

/* for each known type a T_PUT_XX macro is defined */

#define T_PUT_int(argnum, val) \
  do { \
    int T_PUT_var = (val); \
    T_CHECK_SIZE(sizeof(int), argnum); \
    memcpy(T_LOCAL_buf + T_LOCAL_size, &T_PUT_var, sizeof(int)); \
    T_LOCAL_size += sizeof(int); \
  } while (0)

Cedric Roux's avatar
Cedric Roux committed
35
36
37
38
39
40
41
42
#define T_PUT_ulong(argnum, val) \
  do { \
    unsigned long T_PUT_var = (val); \
    T_CHECK_SIZE(sizeof(unsigned long), argnum); \
    memcpy(T_LOCAL_buf + T_LOCAL_size, &T_PUT_var, sizeof(unsigned long)); \
    T_LOCAL_size += sizeof(unsigned long); \
  } while (0)

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
#define T_PUT_float(argnum, val) \
  do { \
    float T_PUT_var = (val); \
    T_CHECK_SIZE(sizeof(float), argnum); \
    memcpy(T_LOCAL_buf + T_LOCAL_size, &T_PUT_var, sizeof(float)); \
    T_LOCAL_size += sizeof(float); \
  } while (0)

#define T_PUT_buffer(argnum, val) \
  do { \
    T_buffer T_PUT_buffer_var = (val); \
    T_PUT_int(argnum, T_PUT_buffer_var.length); \
    T_CHECK_SIZE(T_PUT_buffer_var.length, argnum); \
    memcpy(T_LOCAL_buf + T_LOCAL_size, T_PUT_buffer_var.addr, \
           T_PUT_buffer_var.length); \
    T_LOCAL_size += T_PUT_buffer_var.length; \
  } while (0)

#define T_PUT_string(argnum, val) \
  do { \
    char *T_PUT_var = (val); \
    int T_PUT_len = strlen(T_PUT_var) + 1; \
    T_CHECK_SIZE(T_PUT_len, argnum); \
    memcpy(T_LOCAL_buf + T_LOCAL_size, T_PUT_var, T_PUT_len); \
    T_LOCAL_size += T_PUT_len; \
  } while (0)

#define T_PUT_printf_deref(...) __VA_ARGS__

#define T_PUT_printf(argnum, x) \
  do { \
    int T_PUT_len = snprintf(T_LOCAL_buf + T_LOCAL_size, \
                             T_BUFFER_MAX - T_LOCAL_size, T_PUT_printf_deref x); \
    if (T_PUT_len < 0) { \
      printf("%s:%d:%s: you can't read this, or can you?", \
               __FILE__, __LINE__, __FUNCTION__); \
      abort(); \
    } \
    if (T_PUT_len >= T_BUFFER_MAX - T_LOCAL_size) { \
      printf("%s:%d:%s: cannot put argument %d in T macro, not enough space" \
               ", consider increasing T_BUFFER_MAX (%d)\n", \
               __FILE__, __LINE__, __FUNCTION__, argnum, T_BUFFER_MAX); \
      abort(); \
    } \
    T_LOCAL_size += T_PUT_len + 1; \
  } while (0)

/* structure type to detect that you pass a known type as first arg of T */
struct T_header;

/* to define message ID */
#define T_ID(x) ((struct T_header *)(uintptr_t)(x))

/* T macro tricks */

#define TN(...) TN_N(__VA_ARGS__,33,32,31,30,29,28,27,26,25,24,23,22,21,\
        20,19,18,17,16,15,14,13,12,11,10,9,8,7,6,5,4,3,2,1,0)(__VA_ARGS__)
#define TN_N(n0,n1,n2,n3,n4,n5,n6,n7,n8,n9,n10,n11,n12,n13,n14,n15,n16,n17,\
        n18,n19,n20,n21,n22,n23,n24,n25,n26,n27,n28,n29,n30,n31,n32,n,...) T##n
#define T(...) TN(__VA_ARGS__)

/* type used to send arbitrary buffer data */
typedef struct {
  void *addr;
  int length;
} T_buffer;

extern volatile int *T_freelist_head;
extern T_cache_t *T_cache;

Cedric Roux's avatar
Cedric Roux committed
113
114
115
116
117
118
119
120
121
122
/* When running the basic simulator, we may fill the T cache too fast.
 * Let's not crash if it's full, just wait.
 */
#if BASIC_SIMULATOR
#  define T_BASIC_SIMULATOR_WAIT \
     while (T_cache[T_LOCAL_slot].busy) usleep(100)
#else
#  define T_BASIC_SIMULATOR_WAIT /* */
#endif

123
124
125
126
127
128
129
130
/* used at header of Tn, allocates buffer */
#define T_LOCAL_DATA \
  char *T_LOCAL_buf; \
  int T_LOCAL_size = 0; \
  int T_LOCAL_slot; \
  T_LOCAL_slot = __sync_fetch_and_add(T_freelist_head, 1) \
                 & (T_CACHE_SIZE - 1); \
  (void)__sync_fetch_and_and(T_freelist_head, T_CACHE_SIZE - 1); \
Cedric Roux's avatar
Cedric Roux committed
131
  T_BASIC_SIMULATOR_WAIT; \
132
133
134
135
136
137
138
139
140
  if (T_cache[T_LOCAL_slot].busy) { \
    printf("%s:%d:%s: T cache is full - consider increasing its size\n", \
           __FILE__, __LINE__, __FUNCTION__); \
    abort(); \
  } \
  T_LOCAL_buf = T_cache[T_LOCAL_slot].buffer;

#define T_ACTIVE(x) T_active[(intptr_t)x]

141
#define T_COMMIT() \
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
  T_cache[T_LOCAL_slot].length = T_LOCAL_size; \
  __sync_synchronize(); \
  T_cache[T_LOCAL_slot].busy = 1; \

#define T_CHECK_SIZE(len, argnum) \
  if (T_LOCAL_size + (len) > T_BUFFER_MAX) { \
    printf("%s:%d:%s: cannot put argument %d in T macro, not enough space" \
             ", consider increasing T_BUFFER_MAX (%d)\n", \
             __FILE__, __LINE__, __FUNCTION__, argnum, T_BUFFER_MAX); \
    abort(); \
  }

#if 0
#define T_PUT(type, var, argnum) \
  do { \
    if (T_LOCAL_size + sizeof(var) > T_BUFFER_MAX) { \
      printf("%s:%d:%s: cannot put argument %d in T macro, not enough space" \
               ", consider increasing T_BUFFER_MAX (%d)\n", \
               __FILE__, __LINE__, __FUNCTION__, argnum, T_BUFFER_MAX); \
      abort(); \
    } \
    memcpy(T_LOCAL_buf + T_LOCAL_size, &var, sizeof(var)); \
    T_LOCAL_size += sizeof(var); \
  } while (0)
#endif

#if 0
#define T_PROCESS(x, argnum) \
  do { \
    T_PUT(typeof(x), x, argnum); \
  } while (0)
#endif

#if 0
#define T_PROCESS(x, argnum) \
  do { \
    if (__builtin_types_compatible_p(typeof(x), int)) \
      { T_PUT(int, (intptr_t)(x), argnum); printf("int\n"); } \
    else if (__builtin_types_compatible_p(typeof(x), short)) \
      { T_PUT(short, (intptr_t)(x), argnum); printf("short\n"); } \
    else if (__builtin_types_compatible_p(typeof(x), float)) \
      { T_PUT(float, (x), argnum); printf("float\n"); } \
    else if (__builtin_types_compatible_p(typeof(x), char *)) \
      { T_PUT(char *, (char *)(intptr_t)(x), argnum); printf("char *\n"); } \
    else if (__builtin_types_compatible_p(typeof(x), float *)) \
      { T_PUT(float *, (float *)(intptr_t)(x), argnum); printf("float *\n"); } \
    else if (__builtin_types_compatible_p(typeof(x), void *)) \
      { T_PUT(void *, (void *)(intptr_t)(x), argnum); printf("void *\n"); } \
    else { \
      printf("%s:%d:%s: unsupported type for argument %d in T macro\n", \
               __FILE__, __LINE__, __FUNCTION__, argnum); \
      abort(); \
    } \
  } while (0)
#endif

Cedric Roux's avatar
Cedric Roux committed
198
199
200
201
202
203
204
/* we have 4 versions of T_HEADER:
 * - bad quality C++ version with time
 * - good quality C version with time
 * - bad quality C++ version without time
 * - good quality C version without time
 */

Cedric Roux's avatar
Cedric Roux committed
205
206
#ifdef T_SEND_TIME

Cedric Roux's avatar
Cedric Roux committed
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
#ifdef __cplusplus

/* C++ version of T_HEADER with time */
#define T_HEADER(x) \
  do { \
    struct timespec T_HEADER_time; \
    if (clock_gettime(CLOCK_REALTIME, &T_HEADER_time)) abort(); \
    memcpy(T_LOCAL_buf, &T_HEADER_time, sizeof(struct timespec)); \
    T_LOCAL_size += sizeof(struct timespec); \
    T_PUT_int(1, (int)(uintptr_t)(x)); \
  } while (0)

#else /* #ifdef __cplusplus */

/* C version of T_HEADER with time */
Cedric Roux's avatar
Cedric Roux committed
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
#define T_HEADER(x) \
  do { \
    if (!__builtin_types_compatible_p(typeof(x), struct T_header *)) { \
      printf("%s:%d:%s: " \
             "bad use of T, pass a message ID as first parameter\n", \
             __FILE__, __LINE__, __FUNCTION__); \
      abort(); \
    } \
    struct timespec T_HEADER_time; \
    if (clock_gettime(CLOCK_REALTIME, &T_HEADER_time)) abort(); \
    memcpy(T_LOCAL_buf, &T_HEADER_time, sizeof(struct timespec)); \
    T_LOCAL_size += sizeof(struct timespec); \
    T_PUT_int(1, (int)(uintptr_t)(x)); \
  } while (0)

Cedric Roux's avatar
Cedric Roux committed
237
238
#endif /* #ifdef __cplusplus */

Cedric Roux's avatar
Cedric Roux committed
239
240
#else /* #ifdef T_SEND_TIME */

Cedric Roux's avatar
Cedric Roux committed
241
242
243
244
245
246
247
248
249
250
251
#ifdef __cplusplus

/* C++ version of T_HEADER without time */
#define T_HEADER(x) \
  do { \
    T_PUT_int(1, (int)(uintptr_t)(x)); \
  } while (0)

#else /* #ifdef __cplusplus */

/* C version of T_HEADER without time */
252
253
254
255
256
257
258
259
260
261
262
#define T_HEADER(x) \
  do { \
    if (!__builtin_types_compatible_p(typeof(x), struct T_header *)) { \
      printf("%s:%d:%s: " \
             "bad use of T, pass a message ID as first parameter\n", \
             __FILE__, __LINE__, __FUNCTION__); \
      abort(); \
    } \
    T_PUT_int(1, (int)(uintptr_t)(x)); \
  } while (0)

Cedric Roux's avatar
Cedric Roux committed
263
264
#endif /* #ifdef __cplusplus */

Cedric Roux's avatar
Cedric Roux committed
265
266
#endif /* #ifdef T_SEND_TIME */

267
268
269
270
271
#define T1(t) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
272
      T_COMMIT(); \
273
274
275
276
277
278
279
280
281
    } \
  } while (0)

#define T3(t,t0,x0) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
282
      T_COMMIT(); \
283
284
285
286
287
288
289
290
291
292
    } \
  } while (0)

#define T5(t,t0,x0,t1,x1) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
293
      T_COMMIT(); \
294
295
296
297
298
299
300
301
302
303
304
    } \
  } while (0)

#define T7(t,t0,x0,t1,x1,t2,x2) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
305
      T_COMMIT(); \
306
307
308
309
310
311
312
313
314
315
316
317
    } \
  } while (0)

#define T9(t,t0,x0,t1,x1,t2,x2,t3,x3) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
318
      T_COMMIT(); \
319
320
321
322
323
324
325
326
327
328
329
330
331
    } \
  } while (0)

#define T11(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
332
      T_COMMIT(); \
333
334
335
336
337
338
339
340
341
342
343
344
345
346
    } \
  } while (0)

#define T13(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
347
      T_COMMIT(); \
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
    } \
  } while (0)

#define T15(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
363
      T_COMMIT(); \
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
    } \
  } while (0)

#define T17(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
380
      T_COMMIT(); \
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
    } \
  } while (0)

#define T19(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
398
      T_COMMIT(); \
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
    } \
  } while (0)

#define T21(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
417
      T_COMMIT(); \
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
    } \
  } while (0)

#define T23(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
437
      T_COMMIT(); \
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
    } \
  } while (0)

#define T25(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10,t11,x11) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
      T_PUT_##t11(13, x11); \
458
      T_COMMIT(); \
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
    } \
  } while (0)

#define T27(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10,t11,x11,t12,x12) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
      T_PUT_##t11(13, x11); \
      T_PUT_##t12(14, x12); \
480
      T_COMMIT(); \
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
    } \
  } while (0)

#define T29(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10,t11,x11,t12,x12,t13,x13) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
      T_PUT_##t11(13, x11); \
      T_PUT_##t12(14, x12); \
      T_PUT_##t13(15, x13); \
503
      T_COMMIT(); \
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
    } \
  } while (0)

#define T31(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10,t11,x11,t12,x12,t13,x13,t14,x14) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
      T_PUT_##t11(13, x11); \
      T_PUT_##t12(14, x12); \
      T_PUT_##t13(15, x13); \
      T_PUT_##t14(16, x14); \
527
      T_COMMIT(); \
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
    } \
  } while (0)

#define T33(t,t0,x0,t1,x1,t2,x2,t3,x3,t4,x4,t5,x5,t6,x6,t7,x7,t8,x8,t9,x9,t10,x10,t11,x11,t12,x12,t13,x13,t14,x14,t15,x15) \
  do { \
    if (T_ACTIVE(t)) { \
      T_LOCAL_DATA \
      T_HEADER(t); \
      T_PUT_##t0(2, x0); \
      T_PUT_##t1(3, x1); \
      T_PUT_##t2(4, x2); \
      T_PUT_##t3(5, x3); \
      T_PUT_##t4(6, x4); \
      T_PUT_##t5(7, x5); \
      T_PUT_##t6(8, x6); \
      T_PUT_##t7(9, x7); \
      T_PUT_##t8(10, x8); \
      T_PUT_##t9(11, x9); \
      T_PUT_##t10(12, x10); \
      T_PUT_##t11(13, x11); \
      T_PUT_##t12(14, x12); \
      T_PUT_##t13(15, x13); \
      T_PUT_##t14(16, x14); \
      T_PUT_##t15(17, x15); \
552
      T_COMMIT(); \
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
    } \
  } while (0)

#define T_CALL_ERROR \
  do { \
    printf("%s:%d:%s: error calling T, you have to use T_INT() or T_XX()\n", \
           __FILE__, __LINE__, __FUNCTION__); \
  } while (0)

#define T2(...) T_CALL_ERROR
#define T4(...) T_CALL_ERROR
#define T6(...) T_CALL_ERROR
#define T8(...) T_CALL_ERROR
#define T10(...) T_CALL_ERROR
#define T12(...) T_CALL_ERROR
#define T14(...) T_CALL_ERROR
#define T16(...) T_CALL_ERROR
#define T18(...) T_CALL_ERROR
#define T20(...) T_CALL_ERROR
#define T22(...) T_CALL_ERROR
#define T24(...) T_CALL_ERROR
#define T26(...) T_CALL_ERROR
#define T28(...) T_CALL_ERROR
#define T30(...) T_CALL_ERROR
#define T32(...) T_CALL_ERROR

Cedric Roux's avatar
Cedric Roux committed
579
580
581
582
583
584
585
586
587
588
589
590
591
/* special cases for VCD logs */

#define T_VCD_VARIABLE(var, val) \
  do { \
    if (T_ACTIVE(((var) + VCD_FIRST_VARIABLE))) { \
      if ((var) > VCD_NUM_VARIABLES) { \
        printf("%s:%d:%s: VCD data out of synch for the T, contact" \
               " the authors!\n", __FILE__, __LINE__, __FUNCTION__); \
        abort(); \
      } \
      T_LOCAL_DATA \
      T_HEADER(T_ID((var) + VCD_FIRST_VARIABLE)); \
      T_PUT_ulong(1, (val)); \
592
      T_COMMIT(); \
Cedric Roux's avatar
Cedric Roux committed
593
594
595
596
597
598
599
600
601
602
603
604
605
606
    } \
  } while (0)

#define T_VCD_FUNCTION(fun, val) \
  do { \
    if (T_ACTIVE(((fun) + VCD_FIRST_FUNCTION))) { \
      if ((fun) > VCD_NUM_FUNCTIONS) { \
        printf("%s:%d:%s: VCD data out of synch for the T, contact" \
               " the authors!\n", __FILE__, __LINE__, __FUNCTION__); \
        abort(); \
      } \
      T_LOCAL_DATA \
      T_HEADER(T_ID((fun) + VCD_FIRST_FUNCTION)); \
      T_PUT_int(1, (val)); \
607
      T_COMMIT(); \
Cedric Roux's avatar
Cedric Roux committed
608
609
610
    } \
  } while (0)

611
612
extern int *T_active;

613
void T_init(int remote_port, int wait_for_tracer, int dont_fork);
614
615
616
617
618
619
620
621
622

#else /* T_TRACER */

/* if T_TRACER is not defined or is 0, the T is deactivated */
#define T(...) /**/

#endif /* T_TRACER */

#endif /* _T_T_T_ */