xref: /OK3568_Linux_fs/kernel/tools/perf/util/intel-pt-decoder/intel-pt-log.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1*4882a593Smuzhiyun // SPDX-License-Identifier: GPL-2.0-only
2*4882a593Smuzhiyun /*
3*4882a593Smuzhiyun  * intel_pt_log.c: Intel Processor Trace support
4*4882a593Smuzhiyun  * Copyright (c) 2013-2014, Intel Corporation.
5*4882a593Smuzhiyun  */
6*4882a593Smuzhiyun 
7*4882a593Smuzhiyun #include <stdio.h>
8*4882a593Smuzhiyun #include <stdint.h>
9*4882a593Smuzhiyun #include <inttypes.h>
10*4882a593Smuzhiyun #include <stdarg.h>
11*4882a593Smuzhiyun #include <stdbool.h>
12*4882a593Smuzhiyun #include <string.h>
13*4882a593Smuzhiyun 
14*4882a593Smuzhiyun #include "intel-pt-log.h"
15*4882a593Smuzhiyun #include "intel-pt-insn-decoder.h"
16*4882a593Smuzhiyun 
17*4882a593Smuzhiyun #include "intel-pt-pkt-decoder.h"
18*4882a593Smuzhiyun 
19*4882a593Smuzhiyun #define MAX_LOG_NAME 256
20*4882a593Smuzhiyun 
21*4882a593Smuzhiyun static FILE *f;
22*4882a593Smuzhiyun static char log_name[MAX_LOG_NAME];
23*4882a593Smuzhiyun bool intel_pt_enable_logging;
24*4882a593Smuzhiyun 
intel_pt_log_fp(void)25*4882a593Smuzhiyun void *intel_pt_log_fp(void)
26*4882a593Smuzhiyun {
27*4882a593Smuzhiyun 	return f;
28*4882a593Smuzhiyun }
29*4882a593Smuzhiyun 
intel_pt_log_enable(void)30*4882a593Smuzhiyun void intel_pt_log_enable(void)
31*4882a593Smuzhiyun {
32*4882a593Smuzhiyun 	intel_pt_enable_logging = true;
33*4882a593Smuzhiyun }
34*4882a593Smuzhiyun 
intel_pt_log_disable(void)35*4882a593Smuzhiyun void intel_pt_log_disable(void)
36*4882a593Smuzhiyun {
37*4882a593Smuzhiyun 	if (f)
38*4882a593Smuzhiyun 		fflush(f);
39*4882a593Smuzhiyun 	intel_pt_enable_logging = false;
40*4882a593Smuzhiyun }
41*4882a593Smuzhiyun 
intel_pt_log_set_name(const char * name)42*4882a593Smuzhiyun void intel_pt_log_set_name(const char *name)
43*4882a593Smuzhiyun {
44*4882a593Smuzhiyun 	strncpy(log_name, name, MAX_LOG_NAME - 5);
45*4882a593Smuzhiyun 	strcat(log_name, ".log");
46*4882a593Smuzhiyun }
47*4882a593Smuzhiyun 
intel_pt_print_data(const unsigned char * buf,int len,uint64_t pos,int indent)48*4882a593Smuzhiyun static void intel_pt_print_data(const unsigned char *buf, int len, uint64_t pos,
49*4882a593Smuzhiyun 				int indent)
50*4882a593Smuzhiyun {
51*4882a593Smuzhiyun 	int i;
52*4882a593Smuzhiyun 
53*4882a593Smuzhiyun 	for (i = 0; i < indent; i++)
54*4882a593Smuzhiyun 		fprintf(f, " ");
55*4882a593Smuzhiyun 
56*4882a593Smuzhiyun 	fprintf(f, "  %08" PRIx64 ": ", pos);
57*4882a593Smuzhiyun 	for (i = 0; i < len; i++)
58*4882a593Smuzhiyun 		fprintf(f, " %02x", buf[i]);
59*4882a593Smuzhiyun 	for (; i < 16; i++)
60*4882a593Smuzhiyun 		fprintf(f, "   ");
61*4882a593Smuzhiyun 	fprintf(f, " ");
62*4882a593Smuzhiyun }
63*4882a593Smuzhiyun 
intel_pt_print_no_data(uint64_t pos,int indent)64*4882a593Smuzhiyun static void intel_pt_print_no_data(uint64_t pos, int indent)
65*4882a593Smuzhiyun {
66*4882a593Smuzhiyun 	int i;
67*4882a593Smuzhiyun 
68*4882a593Smuzhiyun 	for (i = 0; i < indent; i++)
69*4882a593Smuzhiyun 		fprintf(f, " ");
70*4882a593Smuzhiyun 
71*4882a593Smuzhiyun 	fprintf(f, "  %08" PRIx64 ": ", pos);
72*4882a593Smuzhiyun 	for (i = 0; i < 16; i++)
73*4882a593Smuzhiyun 		fprintf(f, "   ");
74*4882a593Smuzhiyun 	fprintf(f, " ");
75*4882a593Smuzhiyun }
76*4882a593Smuzhiyun 
intel_pt_log_open(void)77*4882a593Smuzhiyun static int intel_pt_log_open(void)
78*4882a593Smuzhiyun {
79*4882a593Smuzhiyun 	if (!intel_pt_enable_logging)
80*4882a593Smuzhiyun 		return -1;
81*4882a593Smuzhiyun 
82*4882a593Smuzhiyun 	if (f)
83*4882a593Smuzhiyun 		return 0;
84*4882a593Smuzhiyun 
85*4882a593Smuzhiyun 	if (!log_name[0])
86*4882a593Smuzhiyun 		return -1;
87*4882a593Smuzhiyun 
88*4882a593Smuzhiyun 	f = fopen(log_name, "w+");
89*4882a593Smuzhiyun 	if (!f) {
90*4882a593Smuzhiyun 		intel_pt_enable_logging = false;
91*4882a593Smuzhiyun 		return -1;
92*4882a593Smuzhiyun 	}
93*4882a593Smuzhiyun 
94*4882a593Smuzhiyun 	return 0;
95*4882a593Smuzhiyun }
96*4882a593Smuzhiyun 
__intel_pt_log_packet(const struct intel_pt_pkt * packet,int pkt_len,uint64_t pos,const unsigned char * buf)97*4882a593Smuzhiyun void __intel_pt_log_packet(const struct intel_pt_pkt *packet, int pkt_len,
98*4882a593Smuzhiyun 			   uint64_t pos, const unsigned char *buf)
99*4882a593Smuzhiyun {
100*4882a593Smuzhiyun 	char desc[INTEL_PT_PKT_DESC_MAX];
101*4882a593Smuzhiyun 
102*4882a593Smuzhiyun 	if (intel_pt_log_open())
103*4882a593Smuzhiyun 		return;
104*4882a593Smuzhiyun 
105*4882a593Smuzhiyun 	intel_pt_print_data(buf, pkt_len, pos, 0);
106*4882a593Smuzhiyun 	intel_pt_pkt_desc(packet, desc, INTEL_PT_PKT_DESC_MAX);
107*4882a593Smuzhiyun 	fprintf(f, "%s\n", desc);
108*4882a593Smuzhiyun }
109*4882a593Smuzhiyun 
__intel_pt_log_insn(struct intel_pt_insn * intel_pt_insn,uint64_t ip)110*4882a593Smuzhiyun void __intel_pt_log_insn(struct intel_pt_insn *intel_pt_insn, uint64_t ip)
111*4882a593Smuzhiyun {
112*4882a593Smuzhiyun 	char desc[INTEL_PT_INSN_DESC_MAX];
113*4882a593Smuzhiyun 	size_t len = intel_pt_insn->length;
114*4882a593Smuzhiyun 
115*4882a593Smuzhiyun 	if (intel_pt_log_open())
116*4882a593Smuzhiyun 		return;
117*4882a593Smuzhiyun 
118*4882a593Smuzhiyun 	if (len > INTEL_PT_INSN_BUF_SZ)
119*4882a593Smuzhiyun 		len = INTEL_PT_INSN_BUF_SZ;
120*4882a593Smuzhiyun 	intel_pt_print_data(intel_pt_insn->buf, len, ip, 8);
121*4882a593Smuzhiyun 	if (intel_pt_insn_desc(intel_pt_insn, desc, INTEL_PT_INSN_DESC_MAX) > 0)
122*4882a593Smuzhiyun 		fprintf(f, "%s\n", desc);
123*4882a593Smuzhiyun 	else
124*4882a593Smuzhiyun 		fprintf(f, "Bad instruction!\n");
125*4882a593Smuzhiyun }
126*4882a593Smuzhiyun 
__intel_pt_log_insn_no_data(struct intel_pt_insn * intel_pt_insn,uint64_t ip)127*4882a593Smuzhiyun void __intel_pt_log_insn_no_data(struct intel_pt_insn *intel_pt_insn,
128*4882a593Smuzhiyun 				 uint64_t ip)
129*4882a593Smuzhiyun {
130*4882a593Smuzhiyun 	char desc[INTEL_PT_INSN_DESC_MAX];
131*4882a593Smuzhiyun 
132*4882a593Smuzhiyun 	if (intel_pt_log_open())
133*4882a593Smuzhiyun 		return;
134*4882a593Smuzhiyun 
135*4882a593Smuzhiyun 	intel_pt_print_no_data(ip, 8);
136*4882a593Smuzhiyun 	if (intel_pt_insn_desc(intel_pt_insn, desc, INTEL_PT_INSN_DESC_MAX) > 0)
137*4882a593Smuzhiyun 		fprintf(f, "%s\n", desc);
138*4882a593Smuzhiyun 	else
139*4882a593Smuzhiyun 		fprintf(f, "Bad instruction!\n");
140*4882a593Smuzhiyun }
141*4882a593Smuzhiyun 
__intel_pt_log(const char * fmt,...)142*4882a593Smuzhiyun void __intel_pt_log(const char *fmt, ...)
143*4882a593Smuzhiyun {
144*4882a593Smuzhiyun 	va_list args;
145*4882a593Smuzhiyun 
146*4882a593Smuzhiyun 	if (intel_pt_log_open())
147*4882a593Smuzhiyun 		return;
148*4882a593Smuzhiyun 
149*4882a593Smuzhiyun 	va_start(args, fmt);
150*4882a593Smuzhiyun 	vfprintf(f, fmt, args);
151*4882a593Smuzhiyun 	va_end(args);
152*4882a593Smuzhiyun }
153