xref: /netbsd-src/external/gpl3/gdb/dist/sim/common/sim-trace.h (revision b7b7574d3bf8eeb51a1fa3977b59142ec6434a55)
1 /* Simulator tracing/debugging support.
2    Copyright (C) 1997-2014 Free Software Foundation, Inc.
3    Contributed by Cygnus Support.
4 
5 This file is part of GDB, the GNU debugger.
6 
7 This program is free software; you can redistribute it and/or modify
8 it under the terms of the GNU General Public License as published by
9 the Free Software Foundation; either version 3 of the License, or
10 (at your option) any later version.
11 
12 This program is distributed in the hope that it will be useful,
13 but WITHOUT ANY WARRANTY; without even the implied warranty of
14 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
15 GNU General Public License for more details.
16 
17 You should have received a copy of the GNU General Public License
18 along with this program.  If not, see <http://www.gnu.org/licenses/>.  */
19 
20 /* This file is meant to be included by sim-basics.h.  */
21 
22 #ifndef SIM_TRACE_H
23 #define SIM_TRACE_H
24 
25 /* Standard traceable entities.  */
26 
27 enum {
28   /* Trace insn execution.  */
29   TRACE_INSN_IDX = 1,
30 
31   /* Trace insn decoding.
32      ??? This is more of a simulator debugging operation and might best be
33      moved to --debug-decode.  */
34   TRACE_DECODE_IDX,
35 
36   /* Trace insn extraction.
37      ??? This is more of a simulator debugging operation and might best be
38      moved to --debug-extract.  */
39   TRACE_EXTRACT_IDX,
40 
41   /* Trace insn execution but include line numbers.  */
42   TRACE_LINENUM_IDX,
43 
44   /* Trace memory operations.
45      The difference between this and TRACE_CORE_IDX is (I think) that this
46      is intended to apply to a higher level.  TRACE_CORE_IDX applies to the
47      low level core operations.  */
48   TRACE_MEMORY_IDX,
49 
50   /* Include model performance data in tracing output.  */
51   TRACE_MODEL_IDX,
52 
53   /* Trace ALU operations.  */
54   TRACE_ALU_IDX,
55 
56   /* Trace memory core operations.  */
57   TRACE_CORE_IDX,
58 
59   /* Trace events.  */
60   TRACE_EVENTS_IDX,
61 
62   /* Trace fpu operations.  */
63   TRACE_FPU_IDX,
64 
65   /* Trace vpu operations.  */
66   TRACE_VPU_IDX,
67 
68   /* Trace branching.  */
69   TRACE_BRANCH_IDX,
70 
71   /* Trace syscalls.  */
72   TRACE_SYSCALL_IDX,
73 
74   /* Add information useful for debugging the simulator to trace output.  */
75   TRACE_DEBUG_IDX,
76 
77   /* Simulator specific trace bits begin here.  */
78   TRACE_NEXT_IDX,
79 
80 };
81 /* Maximum number of traceable entities.  */
82 #ifndef MAX_TRACE_VALUES
83 #define MAX_TRACE_VALUES 32
84 #endif
85 
86 /* The -t option only prints useful values.  It's easy to type and shouldn't
87    splat on the screen everything under the sun making nothing easy to
88    find.  */
89 #define TRACE_USEFUL_MASK \
90 ((1 << TRACE_INSN_IDX) \
91  | (1 << TRACE_LINENUM_IDX) \
92  | (1 << TRACE_MEMORY_IDX) \
93  | (1 << TRACE_MODEL_IDX))
94 
95 /* Masks so WITH_TRACE can have symbolic values.
96    The case choice here is on purpose.  The lowercase parts are args to
97    --with-trace.  */
98 #define TRACE_insn     (1 << TRACE_INSN_IDX)
99 #define TRACE_decode   (1 << TRACE_DECODE_IDX)
100 #define TRACE_extract  (1 << TRACE_EXTRACT_IDX)
101 #define TRACE_linenum  (1 << TRACE_LINENUM_IDX)
102 #define TRACE_memory   (1 << TRACE_MEMORY_IDX)
103 #define TRACE_model    (1 << TRACE_MODEL_IDX)
104 #define TRACE_alu      (1 << TRACE_ALU_IDX)
105 #define TRACE_core     (1 << TRACE_CORE_IDX)
106 #define TRACE_events   (1 << TRACE_EVENTS_IDX)
107 #define TRACE_fpu      (1 << TRACE_FPU_IDX)
108 #define TRACE_vpu      (1 << TRACE_VPU_IDX)
109 #define TRACE_branch   (1 << TRACE_BRANCH_IDX)
110 #define TRACE_syscall  (1 << TRACE_SYSCALL_IDX)
111 #define TRACE_debug    (1 << TRACE_DEBUG_IDX)
112 
113 /* Preprocessor macros to simplify tests of WITH_TRACE.  */
114 #define WITH_TRACE_INSN_P	(WITH_TRACE & TRACE_insn)
115 #define WITH_TRACE_DECODE_P	(WITH_TRACE & TRACE_decode)
116 #define WITH_TRACE_EXTRACT_P	(WITH_TRACE & TRACE_extract)
117 #define WITH_TRACE_LINENUM_P	(WITH_TRACE & TRACE_linenum)
118 #define WITH_TRACE_MEMORY_P	(WITH_TRACE & TRACE_memory)
119 #define WITH_TRACE_MODEL_P	(WITH_TRACE & TRACE_model)
120 #define WITH_TRACE_ALU_P	(WITH_TRACE & TRACE_alu)
121 #define WITH_TRACE_CORE_P	(WITH_TRACE & TRACE_core)
122 #define WITH_TRACE_EVENTS_P	(WITH_TRACE & TRACE_events)
123 #define WITH_TRACE_FPU_P	(WITH_TRACE & TRACE_fpu)
124 #define WITH_TRACE_VPU_P	(WITH_TRACE & TRACE_vpu)
125 #define WITH_TRACE_BRANCH_P	(WITH_TRACE & TRACE_branch)
126 #define WITH_TRACE_SYSCALL_P	(WITH_TRACE & TRACE_syscall)
127 #define WITH_TRACE_DEBUG_P	(WITH_TRACE & TRACE_debug)
128 
129 /* Tracing install handler.  */
130 MODULE_INSTALL_FN trace_install;
131 
132 /* Struct containing all system and cpu trace data.
133 
134    System trace data is stored with the associated module.
135    System and cpu tracing must share the same space of bitmasks as they
136    are arguments to --with-trace.  One could have --with-trace and
137    --with-cpu-trace or some such but that's an over-complication at this point
138    in time.  Also, there may be occasions where system and cpu tracing may
139    wish to share a name.  */
140 
141 typedef struct _trace_data {
142 
143   /* Global summary of all the current trace options */
144   char trace_any_p;
145 
146   /* Boolean array of specified tracing flags.  */
147   /* ??? It's not clear that using an array vs a bit mask is faster.
148      Consider the case where one wants to test whether any of several bits
149      are set.  */
150   char trace_flags[MAX_TRACE_VALUES];
151 #define TRACE_FLAGS(t) ((t)->trace_flags)
152 
153   /* Tracing output goes to this or stderr if NULL.
154      We can't store `stderr' here as stderr goes through a callback.  */
155   FILE *trace_file;
156 #define TRACE_FILE(t) ((t)->trace_file)
157 
158   /* Buffer to store the prefix to be printed before any trace line.  */
159   char trace_prefix[256];
160 #define TRACE_PREFIX(t) ((t)->trace_prefix)
161 
162   /* Buffer to save the inputs for the current instruction.  Use a
163      union to force the buffer into correct alignment */
164   union {
165     unsigned8 i8;
166     unsigned16 i16;
167     unsigned32 i32;
168     unsigned64 i64;
169   } trace_input_data[16];
170   unsigned8 trace_input_fmt[16];
171   unsigned8 trace_input_size[16];
172   int trace_input_idx;
173 #define TRACE_INPUT_DATA(t) ((t)->trace_input_data)
174 #define TRACE_INPUT_FMT(t) ((t)->trace_input_fmt)
175 #define TRACE_INPUT_SIZE(t) ((t)->trace_input_size)
176 #define TRACE_INPUT_IDX(t) ((t)->trace_input_idx)
177 
178   /* Category of trace being performed */
179   int trace_idx;
180 #define TRACE_IDX(t) ((t)->trace_idx)
181 
182   /* Trace range.
183      ??? Not all cpu's support this.  */
184   ADDR_RANGE range;
185 #define TRACE_RANGE(t) (& (t)->range)
186 } TRACE_DATA;
187 
188 /* System tracing support.  */
189 
190 #define STATE_TRACE_FLAGS(sd) TRACE_FLAGS (STATE_TRACE_DATA (sd))
191 
192 /* Return non-zero if tracing of IDX is enabled for non-cpu specific
193    components.  The "S" in "STRACE" refers to "System".  */
194 #define STRACE_P(sd,idx) \
195 ((WITH_TRACE & (1 << (idx))) != 0 \
196  && STATE_TRACE_FLAGS (sd)[idx] != 0)
197 
198 /* Non-zero if --trace-<xxxx> was specified for SD.  */
199 #define STRACE_DEBUG_P(sd)	STRACE_P (sd, TRACE_DEBUG_IDX)
200 
201 /* CPU tracing support.  */
202 
203 #define CPU_TRACE_FLAGS(cpu) TRACE_FLAGS (CPU_TRACE_DATA (cpu))
204 
205 /* Return non-zero if tracing of IDX is enabled for CPU.  */
206 #define TRACE_P(cpu,idx) \
207 ((WITH_TRACE & (1 << (idx))) != 0 \
208  && CPU_TRACE_FLAGS (cpu)[idx] != 0)
209 
210 /* Non-zero if --trace-<xxxx> was specified for CPU.  */
211 #define TRACE_ANY_P(cpu)	((WITH_TRACE) && (CPU_TRACE_DATA (cpu)->trace_any_p))
212 #define TRACE_INSN_P(cpu)	TRACE_P (cpu, TRACE_INSN_IDX)
213 #define TRACE_DECODE_P(cpu)	TRACE_P (cpu, TRACE_DECODE_IDX)
214 #define TRACE_EXTRACT_P(cpu)	TRACE_P (cpu, TRACE_EXTRACT_IDX)
215 #define TRACE_LINENUM_P(cpu)	TRACE_P (cpu, TRACE_LINENUM_IDX)
216 #define TRACE_MEMORY_P(cpu)	TRACE_P (cpu, TRACE_MEMORY_IDX)
217 #define TRACE_MODEL_P(cpu)	TRACE_P (cpu, TRACE_MODEL_IDX)
218 #define TRACE_ALU_P(cpu)	TRACE_P (cpu, TRACE_ALU_IDX)
219 #define TRACE_CORE_P(cpu)	TRACE_P (cpu, TRACE_CORE_IDX)
220 #define TRACE_EVENTS_P(cpu)	TRACE_P (cpu, TRACE_EVENTS_IDX)
221 #define TRACE_FPU_P(cpu)	TRACE_P (cpu, TRACE_FPU_IDX)
222 #define TRACE_VPU_P(cpu)	TRACE_P (cpu, TRACE_VPU_IDX)
223 #define TRACE_BRANCH_P(cpu)	TRACE_P (cpu, TRACE_BRANCH_IDX)
224 #define TRACE_SYSCALL_P(cpu)	TRACE_P (cpu, TRACE_SYSCALL_IDX)
225 #define TRACE_DEBUG_P(cpu)	TRACE_P (cpu, TRACE_DEBUG_IDX)
226 
227 /* Tracing functions.  */
228 
229 /* Prime the trace buffers ready for any trace output.
230    Must be called prior to any other trace operation */
231 extern void trace_prefix (SIM_DESC sd,
232 			  sim_cpu *cpu,
233 			  sim_cia cia,
234 			  address_word pc,
235 			  int print_linenum_p,
236 			  const char *file_name,
237 			  int line_nr,
238 			  const char *fmt,
239 			  ...)
240        __attribute__((format (printf, 8, 9)));
241 
242 /* Generic trace print, assumes trace_prefix() has been called */
243 
244 extern void trace_generic (SIM_DESC sd,
245 			   sim_cpu *cpu,
246 			   int trace_idx,
247 			   const char *fmt,
248 			   ...)
249      __attribute__((format (printf, 4, 5)));
250 
251 typedef enum {
252   trace_fmt_invalid,
253   trace_fmt_word,
254   trace_fmt_fp,
255   trace_fmt_fpu,
256   trace_fmt_string,
257   trace_fmt_bool,
258   trace_fmt_addr,
259   trace_fmt_instruction_incomplete,
260 } data_fmt;
261 
262 /* Trace a varying number of word sized inputs/outputs.  trace_result*
263    must be called to close the trace operation. */
264 
265 extern void save_data (SIM_DESC sd,
266 		       TRACE_DATA *data,
267 		       data_fmt fmt,
268 		       long size,
269 		       const void *buf);
270 
271 extern void trace_input0 (SIM_DESC sd,
272 			  sim_cpu *cpu,
273 			  int trace_idx);
274 
275 extern void trace_input_word1 (SIM_DESC sd,
276 			       sim_cpu *cpu,
277 			       int trace_idx,
278 			       unsigned_word d0);
279 
280 extern void trace_input_word2 (SIM_DESC sd,
281 			       sim_cpu *cpu,
282 			       int trace_idx,
283 			       unsigned_word d0,
284 			       unsigned_word d1);
285 
286 extern void trace_input_word3 (SIM_DESC sd,
287 				       sim_cpu *cpu,
288 				       int trace_idx,
289 				       unsigned_word d0,
290 				       unsigned_word d1,
291 				       unsigned_word d2);
292 
293 extern void trace_input_word4 (SIM_DESC sd,
294 			       sim_cpu *cpu,
295 			       int trace_idx,
296 			       unsigned_word d0,
297 			       unsigned_word d1,
298 			       unsigned_word d2,
299 			       unsigned_word d3);
300 
301 extern void trace_input_addr1 (SIM_DESC sd,
302 			       sim_cpu *cpu,
303 			       int trace_idx,
304 			       address_word d0);
305 
306 extern void trace_input_bool1 (SIM_DESC sd,
307 			       sim_cpu *cpu,
308 			       int trace_idx,
309 			       int d0);
310 
311 extern void trace_input_fp1 (SIM_DESC sd,
312 			     sim_cpu *cpu,
313 			     int trace_idx,
314 			     fp_word f0);
315 
316 extern void trace_input_fp2 (SIM_DESC sd,
317 			     sim_cpu *cpu,
318 			     int trace_idx,
319 			     fp_word f0,
320 			     fp_word f1);
321 
322 extern void trace_input_fp3 (SIM_DESC sd,
323 			     sim_cpu *cpu,
324 			     int trace_idx,
325 			     fp_word f0,
326 			     fp_word f1,
327 			     fp_word f2);
328 
329 extern void trace_input_fpu1 (SIM_DESC sd,
330 			      sim_cpu *cpu,
331 			      int trace_idx,
332 			      struct _sim_fpu *f0);
333 
334 extern void trace_input_fpu2 (SIM_DESC sd,
335 			      sim_cpu *cpu,
336 			      int trace_idx,
337 			      struct _sim_fpu *f0,
338 			      struct _sim_fpu *f1);
339 
340 extern void trace_input_fpu3 (SIM_DESC sd,
341 			      sim_cpu *cpu,
342 			      int trace_idx,
343 			      struct _sim_fpu *f0,
344 			      struct _sim_fpu *f1,
345 			      struct _sim_fpu *f2);
346 
347 /* Other trace_input{_<fmt><nr-inputs>} functions can go here */
348 
349 extern void trace_result0 (SIM_DESC sd,
350 			   sim_cpu *cpu,
351 			   int trace_idx);
352 
353 extern void trace_result_word1 (SIM_DESC sd,
354 				sim_cpu *cpu,
355 				int trace_idx,
356 				unsigned_word r0);
357 
358 extern void trace_result_word2 (SIM_DESC sd,
359 				sim_cpu *cpu,
360 				int trace_idx,
361 				unsigned_word r0,
362 				unsigned_word r1);
363 
364 extern void trace_result_word4 (SIM_DESC sd,
365 				sim_cpu *cpu,
366 				int trace_idx,
367 				unsigned_word r0,
368 				unsigned_word r1,
369 				unsigned_word r2,
370 				unsigned_word r3);
371 
372 extern void trace_result_bool1 (SIM_DESC sd,
373 				sim_cpu *cpu,
374 				int trace_idx,
375 				int r0);
376 
377 extern void trace_result_addr1 (SIM_DESC sd,
378 				sim_cpu *cpu,
379 				int trace_idx,
380 				address_word r0);
381 
382 extern void trace_result_fp1 (SIM_DESC sd,
383 			      sim_cpu *cpu,
384 			      int trace_idx,
385 			      fp_word f0);
386 
387 extern void trace_result_fp2 (SIM_DESC sd,
388 			      sim_cpu *cpu,
389 			      int trace_idx,
390 			      fp_word f0,
391 			      fp_word f1);
392 
393 extern void trace_result_fpu1 (SIM_DESC sd,
394 			       sim_cpu *cpu,
395 			       int trace_idx,
396 			       struct _sim_fpu *f0);
397 
398 extern void trace_result_string1 (SIM_DESC sd,
399 				  sim_cpu *cpu,
400 				  int trace_idx,
401 				  char *str0);
402 
403 extern void trace_result_word1_string1 (SIM_DESC sd,
404 					sim_cpu *cpu,
405 					int trace_idx,
406 					unsigned_word r0,
407 					char *s0);
408 
409 /* Other trace_result{_<type><nr-results>} */
410 
411 
412 /* Macros for tracing ALU instructions */
413 
414 #define TRACE_ALU_INPUT0() \
415 do { \
416   if (TRACE_ALU_P (CPU)) \
417     trace_input0 (SD, CPU, TRACE_ALU_IDX); \
418 } while (0)
419 
420 #define TRACE_ALU_INPUT1(V0) \
421 do { \
422   if (TRACE_ALU_P (CPU)) \
423     trace_input_word1 (SD, CPU, TRACE_ALU_IDX, (V0)); \
424 } while (0)
425 
426 #define TRACE_ALU_INPUT2(V0,V1) \
427 do { \
428   if (TRACE_ALU_P (CPU)) \
429     trace_input_word2 (SD, CPU, TRACE_ALU_IDX, (V0), (V1)); \
430 } while (0)
431 
432 #define TRACE_ALU_INPUT3(V0,V1,V2) \
433 do { \
434   if (TRACE_ALU_P (CPU)) \
435     trace_input_word3 (SD, CPU, TRACE_ALU_IDX, (V0), (V1), (V2)); \
436 } while (0)
437 
438 #define TRACE_ALU_INPUT4(V0,V1,V2,V3) \
439 do { \
440   if (TRACE_ALU_P (CPU)) \
441     trace_input_word4 (SD, CPU, TRACE_ALU_IDX, (V0), (V1), (V2), (V3)); \
442 } while (0)
443 
444 #define TRACE_ALU_RESULT(R0) TRACE_ALU_RESULT1(R0)
445 
446 #define TRACE_ALU_RESULT0() \
447 do { \
448   if (TRACE_ALU_P (CPU)) \
449     trace_result0 (SD, CPU, TRACE_ALU_IDX); \
450 } while (0)
451 
452 #define TRACE_ALU_RESULT1(R0) \
453 do { \
454   if (TRACE_ALU_P (CPU)) \
455     trace_result_word1 (SD, CPU, TRACE_ALU_IDX, (R0)); \
456 } while (0)
457 
458 #define TRACE_ALU_RESULT2(R0,R1) \
459 do { \
460   if (TRACE_ALU_P (CPU)) \
461     trace_result_word2 (SD, CPU, TRACE_ALU_IDX, (R0), (R1)); \
462 } while (0)
463 
464 #define TRACE_ALU_RESULT4(R0,R1,R2,R3) \
465 do { \
466   if (TRACE_ALU_P (CPU)) \
467     trace_result_word4 (SD, CPU, TRACE_ALU_IDX, (R0), (R1), (R2), (R3)); \
468 } while (0)
469 
470 /* Macros for tracing inputs to comparative branch instructions. */
471 
472 #define TRACE_BRANCH_INPUT1(V0) \
473 do { \
474   if (TRACE_BRANCH_P (CPU)) \
475     trace_input_word1 (SD, CPU, TRACE_BRANCH_IDX, (V0)); \
476 } while (0)
477 
478 #define TRACE_BRANCH_INPUT2(V0,V1) \
479 do { \
480   if (TRACE_BRANCH_P (CPU)) \
481     trace_input_word2 (SD, CPU, TRACE_BRANCH_IDX, (V0), (V1)); \
482 } while (0)
483 
484 /* Macros for tracing FPU instructions */
485 
486 #define TRACE_FP_INPUT0() \
487 do { \
488   if (TRACE_FPU_P (CPU)) \
489     trace_input0 (SD, CPU, TRACE_FPU_IDX); \
490 } while (0)
491 
492 #define TRACE_FP_INPUT1(V0) \
493 do { \
494   if (TRACE_FPU_P (CPU)) \
495     trace_input_fp1 (SD, CPU, TRACE_FPU_IDX, (V0)); \
496 } while (0)
497 
498 #define TRACE_FP_INPUT2(V0,V1) \
499 do { \
500   if (TRACE_FPU_P (CPU)) \
501     trace_input_fp2 (SD, CPU, TRACE_FPU_IDX, (V0), (V1)); \
502 } while (0)
503 
504 #define TRACE_FP_INPUT3(V0,V1,V2) \
505 do { \
506   if (TRACE_FPU_P (CPU)) \
507     trace_input_fp3 (SD, CPU, TRACE_FPU_IDX, (V0), (V1), (V2)); \
508 } while (0)
509 
510 #define TRACE_FP_INPUT_WORD1(V0) \
511 do { \
512   if (TRACE_FPU_P (CPU)) \
513     trace_input_word1 (SD, CPU, TRACE_FPU_IDX, (V0)); \
514 } while (0)
515 
516 #define TRACE_FP_RESULT(R0) \
517 do { \
518   if (TRACE_FPU_P (CPU)) \
519     trace_result_fp1 (SD, CPU, TRACE_FPU_IDX, (R0)); \
520 } while (0)
521 
522 #define TRACE_FP_RESULT2(R0,R1) \
523 do { \
524   if (TRACE_FPU_P (CPU)) \
525     trace_result_fp2 (SD, CPU, TRACE_FPU_IDX, (R0), (R1)); \
526 } while (0)
527 
528 #define TRACE_FP_RESULT_BOOL(R0) \
529 do { \
530   if (TRACE_FPU_P (CPU)) \
531     trace_result_bool1 (SD, CPU, TRACE_FPU_IDX, (R0)); \
532 } while (0)
533 
534 #define TRACE_FP_RESULT_WORD(R0) \
535 do { \
536   if (TRACE_FPU_P (CPU)) \
537     trace_result_word1 (SD, CPU, TRACE_FPU_IDX, (R0)); \
538 } while (0)
539 
540 
541 /* Macros for tracing branches */
542 
543 #define TRACE_BRANCH_INPUT(COND) \
544 do { \
545   if (TRACE_BRANCH_P (CPU)) \
546     trace_input_bool1 (SD, CPU, TRACE_BRANCH_IDX, (COND)); \
547 } while (0)
548 
549 #define TRACE_BRANCH_RESULT(DEST) \
550 do { \
551   if (TRACE_BRANCH_P (CPU)) \
552     trace_result_addr1 (SD, CPU, TRACE_BRANCH_IDX, (DEST)); \
553 } while (0)
554 
555 
556 /* The function trace_one_insn has been replaced by the function pair
557    trace_prefix() + trace_generic() */
558 extern void trace_one_insn (SIM_DESC sd,
559 			    sim_cpu * cpu,
560 			    address_word cia,
561 			    int print_linenum_p,
562 			    const char *file_name,
563 			    int line_nr,
564 			    const char *unit,
565 			    const char *fmt,
566 			    ...)
567      __attribute__((format (printf, 8, 9)));
568 
569 extern void trace_printf (SIM_DESC, sim_cpu *, const char *, ...)
570      __attribute__((format (printf, 3, 4)));
571 
572 extern void trace_vprintf (SIM_DESC, sim_cpu *, const char *, va_list);
573 
574 /* Debug support.
575    This is included here because there isn't enough of it to justify
576    a sim-debug.h.  */
577 
578 /* Return non-zero if debugging of IDX for CPU is enabled.  */
579 #define DEBUG_P(cpu, idx) \
580 ((WITH_DEBUG & (1 << (idx))) != 0 \
581  && CPU_DEBUG_FLAGS (cpu)[idx] != 0)
582 
583 /* Non-zero if "--debug-insn" specified.  */
584 #define DEBUG_INSN_P(cpu) DEBUG_P (cpu, DEBUG_INSN_IDX)
585 
586 extern void debug_printf (sim_cpu *, const char *, ...)
587      __attribute__((format (printf, 2, 3)));
588 
589 #endif /* SIM_TRACE_H */
590