1/* Copyright (C) 2006-2007 The Android Open Source Project
2**
3** This software is licensed under the terms of the GNU General Public
4** License version 2, as published by the Free Software Foundation, and
5** may be copied, distributed, and modified under those terms.
6**
7** This program is distributed in the hope that it will be useful,
8** but WITHOUT ANY WARRANTY; without even the implied warranty of
9** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
10** GNU General Public License for more details.
11*/
12
13#ifndef TRACE_COMMON_H
14#define TRACE_COMMON_H
15
16#include <inttypes.h>
17
18// This should be the same as OPC_BUF_SIZE
19#define kMaxInsnPerBB 512
20
21#define kMaxNumBasicBlocks 1024
22
23#define kMaxNumAddrs 1024
24
25#define kInsnBufferSize 1024
26
27#define kCompressedSize 8192
28
29#define kMethodEnter		0
30#define kMethodExit		1
31#define kMethodException	2
32#define kNativeEnter		4
33#define kNativeExit		5
34#define kNativeException	6
35
36// The trace identifier string must be less than 16 characters.
37#define TRACE_IDENT "qemu_trace_file"
38#define TRACE_VERSION 2
39
40typedef struct TraceHeader {
41    char	ident[16];
42    int		version;
43    uint32_t	start_sec;
44    uint32_t	start_usec;
45    uint32_t	pdate;
46    uint32_t	ptime;
47    uint32_t	num_used_pids;		// number of distinct process ids used
48    int		first_unused_pid;	// -1 if all 32,768 pids are used (unlikely)
49    uint8_t	padding[4];		// next field is 8-byte aligned
50    uint64_t	num_static_bb;
51    uint64_t	num_static_insn;
52    uint64_t	num_dynamic_bb;
53    uint64_t	num_dynamic_insn;
54    uint64_t	elapsed_usecs;
55} TraceHeader;
56
57typedef struct BBRec {
58    uint64_t	start_time;	// time of first occurrence
59    uint64_t	bb_num;		// basic block number
60    uint32_t	repeat;		// repeat count (= 0 if just one occurrence)
61    uint64_t	time_diff;	// diff from previous time (if repeat > 0)
62} BBRec;
63
64// Define a trace record for addresses that miss in the cache
65typedef struct AddrRec {
66    uint64_t	time;
67    uint32_t	addr;
68} AddrRec;
69
70// Define a trace record for the start time of each instruction
71typedef struct InsnRec {
72    uint64_t	time_diff;	// time difference from last instruction
73    uint32_t	repeat;		// repeat count
74} InsnRec;
75
76// Define record types for process id changes.
77#define kPidEndOfFile		0
78#define kPidFork		1
79#define kPidClone		2
80#define kPidSwitch		3
81#define kPidExec		4
82#define kPidMmap		5
83#define kPidExit		6
84#define kPidKthreadName		7
85#define kPidSymbolAdd		8
86#define kPidSymbolRemove	9
87#define kPidMunmap		10
88#define kPidNoAction		11
89#define kPidName		12
90
91#define bswap16(x) ((((x) & 0xff) << 8) | (((x) >> 8) & 0xff))
92
93#define bswap32(x) ((((x) & 0xff) << 24) | (((x) & 0xff00) << 8) \
94        | (((x) >> 8) & 0xff00) | (((x) >> 24) & 0xff))
95
96#define bswap64(x) (((x) << 56) | (((x) & 0xff00) << 40) \
97        | (((x) & 0xff0000) << 24) | (((x) & 0xff000000ull) << 8) \
98        | (((x) >> 8) & 0xff000000ull) | (((x) >> 24) & 0xff0000) \
99        | (((x) >> 40) & 0xff00) | ((x) >> 56))
100
101#if BYTE_ORDER == LITTLE_ENDIAN
102#define hostToLE16(x)	(x)
103#define hostToLE32(x)	(x)
104#define hostToLE64(x)	(x)
105#define LE16ToHost(x)	(x)
106#define LE32ToHost(x)	(x)
107#define LE64ToHost(x)	(x)
108#define convert16(x)
109#define convert32(x)
110#define convert64(x)
111#else
112#define hostToLE16(x)	bswap16(x)
113#define hostToLE32(x)	bswap32(x)
114#define hostToLE64(x)	bswap64(x)
115#define LE16ToHost(x)	bswap16(x)
116#define LE32ToHost(x)	bswap32(x)
117#define LE64ToHost(x)	bswap64(x)
118#define convert16(x) (x = bswap16(x))
119#define convert32(x) (x = bswap32(x))
120#define convert64(x) (x = bswap64(x))
121#endif
122
123/* XXX: we wrap 16-bit thumb instructions into 32-bit undefined ARM instructions
124 *      for simplicity reasons. See section 3.13.1 section of the ARM ARM for details
125 *      on the undefined instruction space we're using
126 */
127static __inline__ int   insn_is_thumb(uint32_t   insn)
128{
129    return ((insn & 0xfff000f0) == 0xf7f000f0);
130}
131
132static __inline__ uint32_t  insn_wrap_thumb(uint32_t  insn)
133{
134    return 0xf7f000f0 | ((insn & 0xfff0) << 4) | (insn & 0x000f);
135}
136
137static __inline__ uint32_t  insn_unwrap_thumb(uint32_t  insn)
138{
139    return ((insn >> 4) & 0xfff0) | (insn & 0x000f);
140}
141
142#endif /* TRACE_COMMON_H */
143