Skip to content

Commit

Permalink
KVM: PPC: Book3S HV: Tracepoints for KVM HV guest interactions
Browse files Browse the repository at this point in the history
This patch adds trace points in the guest entry and exit code and also
for exceptions handled by the host in kernel mode - hypercalls and page
faults. The new events are added to /sys/kernel/debug/tracing/events
under a new subsystem called kvm_hv.

Acked-by: Paul Mackerras <[email protected]>
Signed-off-by: Suresh Warrier <[email protected]>
Signed-off-by: Alexander Graf <[email protected]>
  • Loading branch information
Suresh E. Warrier authored and agraf committed Dec 17, 2014
1 parent 2711e24 commit 3c78f78
Show file tree
Hide file tree
Showing 5 changed files with 539 additions and 27 deletions.
13 changes: 10 additions & 3 deletions arch/powerpc/kvm/book3s_64_mmu_hv.c
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,8 @@
#include <asm/ppc-opcode.h>
#include <asm/cputable.h>

#include "trace_hv.h"

/* POWER7 has 10-bit LPIDs, PPC970 has 6-bit LPIDs */
#define MAX_LPID_970 63

Expand Down Expand Up @@ -622,6 +624,8 @@ int kvmppc_book3s_hv_page_fault(struct kvm_run *run, struct kvm_vcpu *vcpu,
gfn = gpa >> PAGE_SHIFT;
memslot = gfn_to_memslot(kvm, gfn);

trace_kvm_page_fault_enter(vcpu, hpte, memslot, ea, dsisr);

/* No memslot means it's an emulated MMIO region */
if (!memslot || (memslot->flags & KVM_MEMSLOT_INVALID))
return kvmppc_hv_emulate_mmio(run, vcpu, gpa, ea,
Expand All @@ -641,6 +645,7 @@ int kvmppc_book3s_hv_page_fault(struct kvm_run *run, struct kvm_vcpu *vcpu,
mmu_seq = kvm->mmu_notifier_seq;
smp_rmb();

ret = -EFAULT;
is_io = 0;
pfn = 0;
page = NULL;
Expand All @@ -664,7 +669,7 @@ int kvmppc_book3s_hv_page_fault(struct kvm_run *run, struct kvm_vcpu *vcpu,
}
up_read(&current->mm->mmap_sem);
if (!pfn)
return -EFAULT;
goto out_put;
} else {
page = pages[0];
pfn = page_to_pfn(page);
Expand Down Expand Up @@ -694,14 +699,14 @@ int kvmppc_book3s_hv_page_fault(struct kvm_run *run, struct kvm_vcpu *vcpu,
}
}

ret = -EFAULT;
if (psize > pte_size)
goto out_put;

/* Check WIMG vs. the actual page we're accessing */
if (!hpte_cache_flags_ok(r, is_io)) {
if (is_io)
return -EFAULT;
goto out_put;

/*
* Allow guest to map emulated device memory as
* uncacheable, but actually make it cacheable.
Expand Down Expand Up @@ -765,6 +770,8 @@ int kvmppc_book3s_hv_page_fault(struct kvm_run *run, struct kvm_vcpu *vcpu,
SetPageDirty(page);

out_put:
trace_kvm_page_fault_exit(vcpu, hpte, ret);

if (page) {
/*
* We drop pages[0] here, not page because page might
Expand Down
19 changes: 19 additions & 0 deletions arch/powerpc/kvm/book3s_hv.c
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,9 @@

#include "book3s.h"

#define CREATE_TRACE_POINTS
#include "trace_hv.h"

/* #define EXIT_DEBUG */
/* #define EXIT_DEBUG_SIMPLE */
/* #define EXIT_DEBUG_INT */
Expand Down Expand Up @@ -1730,6 +1733,7 @@ static void kvmppc_run_core(struct kvmppc_vcore *vc)
list_for_each_entry(vcpu, &vc->runnable_threads, arch.run_list) {
kvmppc_start_thread(vcpu);
kvmppc_create_dtl_entry(vcpu, vc);
trace_kvm_guest_enter(vcpu);
}

/* Set this explicitly in case thread 0 doesn't have a vcpu */
Expand All @@ -1738,6 +1742,9 @@ static void kvmppc_run_core(struct kvmppc_vcore *vc)

vc->vcore_state = VCORE_RUNNING;
preempt_disable();

trace_kvmppc_run_core(vc, 0);

spin_unlock(&vc->lock);

kvm_guest_enter();
Expand Down Expand Up @@ -1783,6 +1790,8 @@ static void kvmppc_run_core(struct kvmppc_vcore *vc)
kvmppc_core_pending_dec(vcpu))
kvmppc_core_dequeue_dec(vcpu);

trace_kvm_guest_exit(vcpu);

ret = RESUME_GUEST;
if (vcpu->arch.trap)
ret = kvmppc_handle_exit_hv(vcpu->arch.kvm_run, vcpu,
Expand All @@ -1808,6 +1817,8 @@ static void kvmppc_run_core(struct kvmppc_vcore *vc)
wake_up(&vcpu->arch.cpu_run);
}
}

trace_kvmppc_run_core(vc, 1);
}

/*
Expand Down Expand Up @@ -1854,11 +1865,13 @@ static void kvmppc_vcore_blocked(struct kvmppc_vcore *vc)
}

vc->vcore_state = VCORE_SLEEPING;
trace_kvmppc_vcore_blocked(vc, 0);
spin_unlock(&vc->lock);
schedule();
finish_wait(&vc->wq, &wait);
spin_lock(&vc->lock);
vc->vcore_state = VCORE_INACTIVE;
trace_kvmppc_vcore_blocked(vc, 1);
}

static int kvmppc_run_vcpu(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu)
Expand All @@ -1867,6 +1880,8 @@ static int kvmppc_run_vcpu(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu)
struct kvmppc_vcore *vc;
struct kvm_vcpu *v, *vn;

trace_kvmppc_run_vcpu_enter(vcpu);

kvm_run->exit_reason = 0;
vcpu->arch.ret = RESUME_GUEST;
vcpu->arch.trap = 0;
Expand Down Expand Up @@ -1896,6 +1911,7 @@ static int kvmppc_run_vcpu(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu)
VCORE_EXIT_COUNT(vc) == 0) {
kvmppc_create_dtl_entry(vcpu, vc);
kvmppc_start_thread(vcpu);
trace_kvm_guest_enter(vcpu);
} else if (vc->vcore_state == VCORE_SLEEPING) {
wake_up(&vc->wq);
}
Expand Down Expand Up @@ -1960,6 +1976,7 @@ static int kvmppc_run_vcpu(struct kvm_run *kvm_run, struct kvm_vcpu *vcpu)
wake_up(&v->arch.cpu_run);
}

trace_kvmppc_run_vcpu_exit(vcpu, kvm_run);
spin_unlock(&vc->lock);
return vcpu->arch.ret;
}
Expand Down Expand Up @@ -2005,7 +2022,9 @@ static int kvmppc_vcpu_run_hv(struct kvm_run *run, struct kvm_vcpu *vcpu)

if (run->exit_reason == KVM_EXIT_PAPR_HCALL &&
!(vcpu->arch.shregs.msr & MSR_PR)) {
trace_kvm_hcall_enter(vcpu);
r = kvmppc_pseries_do_hcall(vcpu);
trace_kvm_hcall_exit(vcpu, r);
kvmppc_core_prepare_to_enter(vcpu);
} else if (r == RESUME_PAGE_FAULT) {
srcu_idx = srcu_read_lock(&vcpu->kvm->srcu);
Expand Down
32 changes: 32 additions & 0 deletions arch/powerpc/kvm/trace_book3s.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
#if !defined(_TRACE_KVM_BOOK3S_H)
#define _TRACE_KVM_BOOK3S_H

/*
* Common defines used by the trace macros in trace_pr.h and trace_hv.h
*/

#define kvm_trace_symbol_exit \
{0x100, "SYSTEM_RESET"}, \
{0x200, "MACHINE_CHECK"}, \
{0x300, "DATA_STORAGE"}, \
{0x380, "DATA_SEGMENT"}, \
{0x400, "INST_STORAGE"}, \
{0x480, "INST_SEGMENT"}, \
{0x500, "EXTERNAL"}, \
{0x501, "EXTERNAL_LEVEL"}, \
{0x502, "EXTERNAL_HV"}, \
{0x600, "ALIGNMENT"}, \
{0x700, "PROGRAM"}, \
{0x800, "FP_UNAVAIL"}, \
{0x900, "DECREMENTER"}, \
{0x980, "HV_DECREMENTER"}, \
{0xc00, "SYSCALL"}, \
{0xd00, "TRACE"}, \
{0xe00, "H_DATA_STORAGE"}, \
{0xe20, "H_INST_STORAGE"}, \
{0xe40, "H_EMUL_ASSIST"}, \
{0xf00, "PERFMON"}, \
{0xf20, "ALTIVEC"}, \
{0xf40, "VSX"}

#endif
Loading

0 comments on commit 3c78f78

Please sign in to comment.