0001
0002
0003
0004
0005
0006
0007 #ifndef INCLUDE__UTIL_PERF_CS_ETM_H__
0008 #define INCLUDE__UTIL_PERF_CS_ETM_H__
0009
0010 #include "util/event.h"
0011 #include <linux/bits.h>
0012
0013 struct perf_session;
0014
0015
0016
0017
0018
0019 enum {
0020
0021 CS_HEADER_VERSION,
0022
0023 CS_PMU_TYPE_CPUS,
0024 CS_ETM_SNAPSHOT,
0025 CS_HEADER_VERSION_MAX,
0026 };
0027
0028
0029
0030
0031
0032
0033
0034
0035
0036
0037 #define CS_HEADER_CURRENT_VERSION 1
0038
0039
0040 enum {
0041 CS_ETM_MAGIC,
0042 CS_ETM_CPU,
0043
0044 CS_ETM_NR_TRC_PARAMS,
0045 CS_ETM_COMMON_BLK_MAX_V1,
0046 };
0047
0048
0049 enum {
0050
0051 CS_ETM_ETMCR = CS_ETM_COMMON_BLK_MAX_V1,
0052 CS_ETM_ETMTRACEIDR,
0053
0054 CS_ETM_ETMCCER,
0055 CS_ETM_ETMIDR,
0056 CS_ETM_PRIV_MAX,
0057 };
0058
0059
0060 #define CS_ETM_NR_TRC_PARAMS_V0 (CS_ETM_ETMIDR - CS_ETM_ETMCR + 1)
0061
0062
0063 enum {
0064
0065 CS_ETMV4_TRCCONFIGR = CS_ETM_COMMON_BLK_MAX_V1,
0066 CS_ETMV4_TRCTRACEIDR,
0067
0068 CS_ETMV4_TRCIDR0,
0069 CS_ETMV4_TRCIDR1,
0070 CS_ETMV4_TRCIDR2,
0071 CS_ETMV4_TRCIDR8,
0072 CS_ETMV4_TRCAUTHSTATUS,
0073 CS_ETMV4_PRIV_MAX,
0074 };
0075
0076
0077 #define CS_ETMV4_NR_TRC_PARAMS_V0 (CS_ETMV4_TRCAUTHSTATUS - CS_ETMV4_TRCCONFIGR + 1)
0078
0079
0080
0081
0082
0083 enum {
0084 CS_ETE_TRCDEVARCH = CS_ETMV4_PRIV_MAX,
0085 CS_ETE_PRIV_MAX
0086 };
0087
0088
0089
0090
0091
0092
0093 enum {
0094 CS_ETMV3_EXC_NONE = 0,
0095 CS_ETMV3_EXC_DEBUG_HALT = 1,
0096 CS_ETMV3_EXC_SMC = 2,
0097 CS_ETMV3_EXC_HYP = 3,
0098 CS_ETMV3_EXC_ASYNC_DATA_ABORT = 4,
0099 CS_ETMV3_EXC_JAZELLE_THUMBEE = 5,
0100 CS_ETMV3_EXC_PE_RESET = 8,
0101 CS_ETMV3_EXC_UNDEFINED_INSTR = 9,
0102 CS_ETMV3_EXC_SVC = 10,
0103 CS_ETMV3_EXC_PREFETCH_ABORT = 11,
0104 CS_ETMV3_EXC_DATA_FAULT = 12,
0105 CS_ETMV3_EXC_GENERIC = 13,
0106 CS_ETMV3_EXC_IRQ = 14,
0107 CS_ETMV3_EXC_FIQ = 15,
0108 };
0109
0110
0111
0112
0113
0114
0115
0116 enum {
0117 CS_ETMV4_EXC_RESET = 0,
0118 CS_ETMV4_EXC_DEBUG_HALT = 1,
0119 CS_ETMV4_EXC_CALL = 2,
0120 CS_ETMV4_EXC_TRAP = 3,
0121 CS_ETMV4_EXC_SYSTEM_ERROR = 4,
0122 CS_ETMV4_EXC_INST_DEBUG = 6,
0123 CS_ETMV4_EXC_DATA_DEBUG = 7,
0124 CS_ETMV4_EXC_ALIGNMENT = 10,
0125 CS_ETMV4_EXC_INST_FAULT = 11,
0126 CS_ETMV4_EXC_DATA_FAULT = 12,
0127 CS_ETMV4_EXC_IRQ = 14,
0128 CS_ETMV4_EXC_FIQ = 15,
0129 CS_ETMV4_EXC_END = 31,
0130 };
0131
0132 enum cs_etm_sample_type {
0133 CS_ETM_EMPTY,
0134 CS_ETM_RANGE,
0135 CS_ETM_DISCONTINUITY,
0136 CS_ETM_EXCEPTION,
0137 CS_ETM_EXCEPTION_RET,
0138 };
0139
0140 enum cs_etm_isa {
0141 CS_ETM_ISA_UNKNOWN,
0142 CS_ETM_ISA_A64,
0143 CS_ETM_ISA_A32,
0144 CS_ETM_ISA_T32,
0145 };
0146
0147 struct cs_etm_queue;
0148
0149 struct cs_etm_packet {
0150 enum cs_etm_sample_type sample_type;
0151 enum cs_etm_isa isa;
0152 u64 start_addr;
0153 u64 end_addr;
0154 u32 instr_count;
0155 u32 last_instr_type;
0156 u32 last_instr_subtype;
0157 u32 flags;
0158 u32 exception_number;
0159 u8 last_instr_cond;
0160 u8 last_instr_taken_branch;
0161 u8 last_instr_size;
0162 u8 trace_chan_id;
0163 int cpu;
0164 };
0165
0166 #define CS_ETM_PACKET_MAX_BUFFER 1024
0167
0168
0169
0170
0171
0172
0173
0174
0175
0176 #define CS_ETM_PER_THREAD_TRACEID 0
0177
0178 struct cs_etm_packet_queue {
0179 u32 packet_count;
0180 u32 head;
0181 u32 tail;
0182 u32 instr_count;
0183 u64 cs_timestamp;
0184 u64 next_cs_timestamp;
0185 struct cs_etm_packet packet_buffer[CS_ETM_PACKET_MAX_BUFFER];
0186 };
0187
0188 #define KiB(x) ((x) * 1024)
0189 #define MiB(x) ((x) * 1024 * 1024)
0190
0191 #define CS_ETM_INVAL_ADDR 0xdeadbeefdeadbeefUL
0192
0193 #define BMVAL(val, lsb, msb) ((val & GENMASK(msb, lsb)) >> lsb)
0194
0195 #define CS_ETM_HEADER_SIZE (CS_HEADER_VERSION_MAX * sizeof(u64))
0196
0197 #define __perf_cs_etmv3_magic 0x3030303030303030ULL
0198 #define __perf_cs_etmv4_magic 0x4040404040404040ULL
0199 #define __perf_cs_ete_magic 0x5050505050505050ULL
0200 #define CS_ETMV3_PRIV_SIZE (CS_ETM_PRIV_MAX * sizeof(u64))
0201 #define CS_ETMV4_PRIV_SIZE (CS_ETMV4_PRIV_MAX * sizeof(u64))
0202 #define CS_ETE_PRIV_SIZE (CS_ETE_PRIV_MAX * sizeof(u64))
0203
0204 #ifdef HAVE_CSTRACE_SUPPORT
0205 int cs_etm__process_auxtrace_info(union perf_event *event,
0206 struct perf_session *session);
0207 int cs_etm__get_cpu(u8 trace_chan_id, int *cpu);
0208 int cs_etm__get_pid_fmt(u8 trace_chan_id, u64 *pid_fmt);
0209 int cs_etm__etmq_set_tid(struct cs_etm_queue *etmq,
0210 pid_t tid, u8 trace_chan_id);
0211 bool cs_etm__etmq_is_timeless(struct cs_etm_queue *etmq);
0212 void cs_etm__etmq_set_traceid_queue_timestamp(struct cs_etm_queue *etmq,
0213 u8 trace_chan_id);
0214 struct cs_etm_packet_queue
0215 *cs_etm__etmq_get_packet_queue(struct cs_etm_queue *etmq, u8 trace_chan_id);
0216 #else
0217 static inline int
0218 cs_etm__process_auxtrace_info(union perf_event *event __maybe_unused,
0219 struct perf_session *session __maybe_unused)
0220 {
0221 return -1;
0222 }
0223
0224 static inline int cs_etm__get_cpu(u8 trace_chan_id __maybe_unused,
0225 int *cpu __maybe_unused)
0226 {
0227 return -1;
0228 }
0229
0230 static inline int cs_etm__etmq_set_tid(
0231 struct cs_etm_queue *etmq __maybe_unused,
0232 pid_t tid __maybe_unused,
0233 u8 trace_chan_id __maybe_unused)
0234 {
0235 return -1;
0236 }
0237
0238 static inline bool cs_etm__etmq_is_timeless(
0239 struct cs_etm_queue *etmq __maybe_unused)
0240 {
0241
0242 return true;
0243 }
0244
0245 static inline void cs_etm__etmq_set_traceid_queue_timestamp(
0246 struct cs_etm_queue *etmq __maybe_unused,
0247 u8 trace_chan_id __maybe_unused) {}
0248
0249 static inline struct cs_etm_packet_queue *cs_etm__etmq_get_packet_queue(
0250 struct cs_etm_queue *etmq __maybe_unused,
0251 u8 trace_chan_id __maybe_unused)
0252 {
0253 return NULL;
0254 }
0255 #endif
0256
0257 #endif