tools: acrntrace: output trace data as raw data

Benefits of outputing trace data as raw data:
  - Smaller trace data size
  - More convenient to add new trace entry. There is no need to change acrntrace
    when we add new trace entry to HV. All we need do is to update the analysis
    scripts to deal with this situation.

Trace data size(with 1 UOS):
~57M   -- with patch
~137M  -- without patch

Signed-off-by: Kaige Fu <kaige.fu@intel.com>
Reviewed-by: Yan, Like <like.yan@intel.com>
Reviewed-by: Geoffroy Van Cutsem <geoffroy.vancutsem@intel.com>
This commit is contained in:
Kaige Fu 2018-06-25 22:37:59 +08:00 committed by lijinxia
parent bfe47a7a91
commit a35a650f5f
5 changed files with 36 additions and 200 deletions

View File

@ -16,7 +16,6 @@
#include <string.h>
#include "acrntrace.h"
#include "trace_event.h"
/* for opt */
static uint64_t period = 10000;
@ -177,7 +176,7 @@ static void reader_fn(param_t * param)
{
int ret;
uint32_t cpuid = param->cpuid;
FILE *fp = param->trace_filep;
int fd = param->trace_fd;
shared_buf_t *sbuf = param->sbuf;
trace_ev_t e;
@ -191,25 +190,9 @@ static void reader_fn(param_t * param)
if (flags & FLAG_CLEAR_BUF)
sbuf_clear_buffered(sbuf);
/* write cpu freq to the first line of output file */
fprintf(fp, "CPU Freq: %f\n", get_cpu_freq());
while (1) {
do {
ret = sbuf_get(sbuf, (void *)&e);
if (ret == 0)
break;
else if (ret < 0) {
pr_err("sbuf[%u] read error: %d\n", cpuid, ret);
return;
}
fprintf(fp, "%u | %lu | ", cpuid, e.tsc);
switch (e.id) {
/* defined in trace_event.h */
/* for each ev type */
ALL_CASES;
}
ret = sbuf_write(fd, sbuf);
} while (ret > 0);
usleep(period);
@ -245,8 +228,9 @@ static int create_reader(reader_struct * reader, uint32_t cpu)
snprintf(trace_file_name, TRACE_FILE_NAME_LEN, "%s/%d", trace_file_dir,
cpu);
reader->param.trace_filep = fopen(trace_file_name, "w+");
if (!reader->param.trace_filep) {
reader->param.trace_fd = open(trace_file_name,
O_WRONLY | O_CREAT | O_TRUNC, 0644);
if (!reader->param.trace_fd) {
pr_err("Failed to open %s, err %d\n", trace_file_name, errno);
return -3;
}
@ -283,10 +267,8 @@ static void destory_reader(reader_struct * reader)
reader->dev_fd = 0;
}
if (reader->param.trace_filep) {
fflush(reader->param.trace_filep);
fclose(reader->param.trace_filep);
reader->param.trace_filep = NULL;
if (reader->param.trace_fd) {
close(reader->param.trace_fd);
}
}

View File

@ -73,7 +73,7 @@ typedef struct {
typedef struct {
uint32_t cpuid;
int exit_flag;
FILE *trace_filep;
int trace_fd;
shared_buf_t *sbuf;
pthread_mutex_t *sbuf_lock;
} param_t;

View File

@ -6,6 +6,8 @@
#include <asm/errno.h>
#include <string.h>
#include <unistd.h>
#include <stdio.h>
#include <stdbool.h>
#include "sbuf.h"
@ -43,6 +45,31 @@ int sbuf_get(shared_buf_t *sbuf, uint8_t *data)
return sbuf->ele_size;
}
int sbuf_write(int fd, shared_buf_t *sbuf)
{
const void *start;
int written;
if (sbuf == NULL)
return -EINVAL;
if (sbuf_is_empty(sbuf)) {
return 0;
}
start = (void *)sbuf + SBUF_HEAD_SIZE + sbuf->head;
written = write(fd, start, sbuf->ele_size);
if ( written != sbuf->ele_size) {
printf("Failed to write. Expect written size %d, returned %d\n",
sbuf->ele_size, written);
return -1;
}
sbuf->head = sbuf_next_ptr(sbuf->head, sbuf->ele_size, sbuf->size);
return sbuf->ele_size;
}
int sbuf_clear_buffered(shared_buf_t *sbuf)
{
if (sbuf == NULL)

View File

@ -66,5 +66,6 @@ static inline void sbuf_add_flags(shared_buf_t *sbuf, uint64_t flags)
}
int sbuf_get(shared_buf_t *sbuf, uint8_t *data);
int sbuf_write(int fd, shared_buf_t *sbuf);
int sbuf_clear_buffered(shared_buf_t *sbuf);
#endif /* SHARED_BUF_H */

View File

@ -1,174 +0,0 @@
/*
* Copyright (C) 2018 Intel Corporation. All rights reserved.
*
* SPDX-License-Identifier: BSD-3-Clause
*/
#ifndef TRACE_EVENT_H
#define TRACE_EVENT_H
#define GEN_CASE(id) case (id):{ id##_FMT; break; }
/* TIMER */
#define TRACE_TIMER_ACTION_ADDED 0x1
#define TRACE_TIMER_ACTION_PCKUP 0x2
#define TRACE_TIMER_ACTION_UPDAT 0x3
#define TRACE_TIMER_IRQ 0x4
#define TRACE_VM_EXIT 0x10
#define TRACE_VM_ENTER 0X11
#define TRC_VMEXIT_ENTRY 0x10000
#define TRC_VMEXIT_EXCEPTION_OR_NMI (TRC_VMEXIT_ENTRY + 0x00000000)
#define TRC_VMEXIT_EXTERNAL_INTERRUPT (TRC_VMEXIT_ENTRY + 0x00000001)
#define TRC_VMEXIT_INTERRUPT_WINDOW (TRC_VMEXIT_ENTRY + 0x00000002)
#define TRC_VMEXIT_CPUID (TRC_VMEXIT_ENTRY + 0x00000004)
#define TRC_VMEXIT_RDTSC (TRC_VMEXIT_ENTRY + 0x00000010)
#define TRC_VMEXIT_VMCALL (TRC_VMEXIT_ENTRY + 0x00000012)
#define TRC_VMEXIT_CR_ACCESS (TRC_VMEXIT_ENTRY + 0x0000001C)
#define TRC_VMEXIT_IO_INSTRUCTION (TRC_VMEXIT_ENTRY + 0x0000001E)
#define TRC_VMEXIT_RDMSR (TRC_VMEXIT_ENTRY + 0x0000001F)
#define TRC_VMEXIT_WRMSR (TRC_VMEXIT_ENTRY + 0x00000020)
#define TRC_VMEXIT_EPT_VIOLATION (TRC_VMEXIT_ENTRY + 0x00000030)
#define TRC_VMEXIT_EPT_MISCONFIGURATION (TRC_VMEXIT_ENTRY + 0x00000031)
#define TRC_VMEXIT_RDTSCP (TRC_VMEXIT_ENTRY + 0x00000033)
#define TRC_VMEXIT_APICV_WRITE (TRC_VMEXIT_ENTRY + 0x00000038)
#define TRC_VMEXIT_APICV_ACCESS (TRC_VMEXIT_ENTRY + 0x00000039)
#define TRC_VMEXIT_APICV_VIRT_EOI (TRC_VMEXIT_ENTRY + 0x0000003A)
#define TRC_VMEXIT_UNHANDLED 0x20000
#define TRACE_CUSTOM 0xFC
#define TRACE_FUNC_ENTER 0xFD
#define TRACE_FUNC_EXIT 0xFE
#define TRACE_STR 0xFF
/* TRACE_EVENTID_MAX 256 */
#define PR(fmt, ...) fprintf((fp), fmt, ##__VA_ARGS__);
#define TRACE_TIMER_ACTION_ADDED_FMT \
{PR("TIMER_ACTION ADDED: ID %d, deadline %lx total %d\n", \
(e).a, ((uint64_t)((e).c)<<32)|(e).b, (e).d); }
#define TRACE_TIMER_ACTION_PCKUP_FMT \
{PR("TIMER_ACTION PCKUP: ID %d, deadline %lx total %d\n", \
(e).a, ((uint64_t)((e).c)<<32)|(e).b, (e).d); }
#define TRACE_TIMER_ACTION_UPDAT_FMT \
{PR("TIMER_ACTION UPDAT: ID %d, deadline %lx total %d\n", \
(e).a, ((unsigned long)((e).c)<<32)|(e).b, (e).d); }
#define TRACE_TIMER_IRQ_FMT \
PR("TIMER_IRQ total: %lx\n", (e).e)
#define TRACE_CUSTOM_FMT \
PR("CUSTOM: 0x%lx 0x%lx\n", (e).e, (e).f)
#define TRACE_FUNC_ENTER_FMT \
PR("ENTER: %s\n", (e).str)
#define TRACE_FUNC_EXIT_FMT \
PR("EXIT : %s\n", (e).str)
#define TRACE_STR_FMT \
PR("STR: %s\n", (e).str)
#define TRACE_VM_EXIT_FMT \
PR("VM_EXIT: exit_reason 0x%016lx, guest_rip 0x%016lx\n", \
(e).e, (e).f)
#define TRACE_VM_ENTER_FMT \
PR("VM_ENTER:\n")
#define TRC_VMEXIT_EXCEPTION_OR_NMI_FMT \
PR("VMEXIT_EXCEPTION_OR_NMI: \
vec 0x%08x, err_code 0x%08x, type %d\n", \
(e).a, (e).b, (e).c)
#define TRC_VMEXIT_EXTERNAL_INTERRUPT_FMT \
PR("VMEXIT_EXTERNAL_INTERRUPT: vec 0x%08lx\n", (e).e)
#define TRC_VMEXIT_INTERRUPT_WINDOW_FMT \
PR("VMEXIT_INTERRUPT_WINDOW:\n")
#define TRC_VMEXIT_CPUID_FMT \
PR("VMEXIT_CPUID: vcpuid %lu\n", (e).e)
#define TRC_VMEXIT_RDTSC_FMT \
PR("VMEXIT_RDTSC: host_tsc 0x%016lx, tsc_offset 0x%016lx\n", \
(e).e, (e).f)
#define TRC_VMEXIT_VMCALL_FMT \
PR("VMEXIT_VMCALL: vmid %lu, hypercall_id %lu\n", \
(e).e, (e).f)
#define TRC_VMEXIT_CR_ACCESS_FMT \
PR("VMEXIT_CR_ACCESS: op %s, rn_nr %lu\n", \
(e).e?"Read":"Write", (e).f)
#define TRC_VMEXIT_IO_INSTRUCTION_FMT \
PR("VMEXIT_IO_INSTRUCTION: \
port %u, dir %u, sz %u, cur_ctx_idx %u\n", \
(e).a, (e).b, (e).c, (e).d)
#define TRC_VMEXIT_RDMSR_FMT \
PR("VMEXIT_RDMSR: msr 0x%08lx, val 0x%08lx\n", \
(e).e, (e).f)
#define TRC_VMEXIT_WRMSR_FMT \
PR("VMEXIT_WRMSR: msr 0x%08lx, val 0x%08lx\n", \
(e).e, (e).f)
#define TRC_VMEXIT_EPT_VIOLATION_FMT \
PR("VMEXIT_EPT_VIOLATION: qual 0x%016lx, gpa 0x%016lx\n", \
(e).e, (e).f)
#define TRC_VMEXIT_EPT_MISCONFIGURATION_FMT \
PR("VMEXIT_EPT_MISCONFIGURATION:\n")
#define TRC_VMEXIT_RDTSCP_FMT \
PR("VMEXIT_RDTSCP: guest_tsc 0x%lx, tsc_aux 0x%lx\n", \
(e).e, (e).f)
#define TRC_VMEXIT_APICV_WRITE_FMT \
PR("VMEXIT_APICV_WRITE: offset 0x%lx\n", (e).e)
#define TRC_VMEXIT_APICV_ACCESS_FMT \
PR("VMEXIT_APICV_ACCESS:\n")
#define TRC_VMEXIT_APICV_VIRT_EOI_FMT \
PR("VMEXIT_APICV_VIRT_EOI: vec 0x%08lx\n", (e).e)
#define TRC_VMEXIT_UNHANDLED_FMT \
PR("VMEXIT_UNHANDLED: 0x%08lx\n", (e).e)
#define ALL_CASES \
GEN_CASE(TRACE_TIMER_ACTION_ADDED); \
GEN_CASE(TRACE_TIMER_ACTION_PCKUP); \
GEN_CASE(TRACE_TIMER_ACTION_UPDAT); \
GEN_CASE(TRACE_TIMER_IRQ); \
GEN_CASE(TRACE_CUSTOM); \
GEN_CASE(TRACE_STR); \
GEN_CASE(TRACE_FUNC_ENTER); \
GEN_CASE(TRACE_FUNC_EXIT); \
GEN_CASE(TRACE_VM_EXIT); \
GEN_CASE(TRACE_VM_ENTER); \
GEN_CASE(TRC_VMEXIT_EXCEPTION_OR_NMI); \
GEN_CASE(TRC_VMEXIT_EXTERNAL_INTERRUPT);\
GEN_CASE(TRC_VMEXIT_INTERRUPT_WINDOW); \
GEN_CASE(TRC_VMEXIT_CPUID); \
GEN_CASE(TRC_VMEXIT_RDTSC); \
GEN_CASE(TRC_VMEXIT_VMCALL); \
GEN_CASE(TRC_VMEXIT_CR_ACCESS); \
GEN_CASE(TRC_VMEXIT_IO_INSTRUCTION); \
GEN_CASE(TRC_VMEXIT_RDMSR); \
GEN_CASE(TRC_VMEXIT_WRMSR); \
GEN_CASE(TRC_VMEXIT_EPT_VIOLATION); \
GEN_CASE(TRC_VMEXIT_EPT_MISCONFIGURATION);\
GEN_CASE(TRC_VMEXIT_RDTSCP); \
GEN_CASE(TRC_VMEXIT_APICV_WRITE); \
GEN_CASE(TRC_VMEXIT_APICV_ACCESS); \
GEN_CASE(TRC_VMEXIT_APICV_VIRT_EOI); \
GEN_CASE(TRC_VMEXIT_UNHANDLED); \
#endif /* TRACE_EVENT_H */