From patchwork Tue Jan 31 10:07:19 2017 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: "Denis V. Lunev" X-Patchwork-Id: 9546829 Return-Path: Received: from mail.wl.linuxfoundation.org (pdx-wl-mail.web.codeaurora.org [172.30.200.125]) by pdx-korg-patchwork.web.codeaurora.org (Postfix) with ESMTP id 2A79B60236 for ; Tue, 31 Jan 2017 10:08:06 +0000 (UTC) Received: from mail.wl.linuxfoundation.org (localhost [127.0.0.1]) by mail.wl.linuxfoundation.org (Postfix) with ESMTP id 1BBAB281A7 for ; Tue, 31 Jan 2017 10:08:06 +0000 (UTC) Received: by mail.wl.linuxfoundation.org (Postfix, from userid 486) id 107DA28285; Tue, 31 Jan 2017 10:08:06 +0000 (UTC) X-Spam-Checker-Version: SpamAssassin 3.3.1 (2010-03-16) on pdx-wl-mail.web.codeaurora.org X-Spam-Level: X-Spam-Status: No, score=-6.9 required=2.0 tests=BAYES_00,RCVD_IN_DNSWL_HI autolearn=ham version=3.3.1 Received: from lists.gnu.org (lists.gnu.org [208.118.235.17]) (using TLSv1 with cipher AES256-SHA (256/256 bits)) (No client certificate requested) by mail.wl.linuxfoundation.org (Postfix) with ESMTPS id 5B5F0281A7 for ; Tue, 31 Jan 2017 10:08:05 +0000 (UTC) Received: from localhost ([::1]:36996 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1cYVM4-00048Q-ED for patchwork-qemu-devel@patchwork.kernel.org; Tue, 31 Jan 2017 05:08:04 -0500 Received: from eggs.gnu.org ([2001:4830:134:3::10]:53575) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1cYVLg-000463-Sr for qemu-devel@nongnu.org; Tue, 31 Jan 2017 05:07:42 -0500 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1cYVLc-0005ig-O1 for qemu-devel@nongnu.org; Tue, 31 Jan 2017 05:07:40 -0500 Received: from mailhub.sw.ru ([195.214.232.25]:44933 helo=relay.sw.ru) by eggs.gnu.org with esmtps (TLS1.0:DHE_RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1cYVLc-0005eA-BV for qemu-devel@nongnu.org; Tue, 31 Jan 2017 05:07:36 -0500 Received: from iris.sw.ru (msk-vpn.virtuozzo.com [195.214.232.6]) by relay.sw.ru (8.13.4/8.13.4) with ESMTP id v0VA7JQd018513; Tue, 31 Jan 2017 13:07:20 +0300 (MSK) From: "Denis V. Lunev" To: qemu-devel@nongnu.org Date: Tue, 31 Jan 2017 13:07:19 +0300 Message-Id: <1485857239-14296-1-git-send-email-den@openvz.org> X-Mailer: git-send-email 2.7.4 X-detected-operating-system: by eggs.gnu.org: OpenBSD 3.x [fuzzy] X-Received-From: 195.214.232.25 Subject: [Qemu-devel] [PATCH 1/1] kvm: log available guest crash parameters X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.21 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Cc: Anton Nefedov , Eduardo Habkost , Marcelo Tosatti , Paolo Bonzini , "Denis V . Lunev" , Richard Henderson Errors-To: qemu-devel-bounces+patchwork-qemu-devel=patchwork.kernel.org@nongnu.org Sender: "Qemu-devel" X-Virus-Scanned: ClamAV using ClamSMTP From: Anton Nefedov Windows reports BSOD parameters through Hyper-V crash MSRs. This information is very useful for initial crash analysis and thus it would be nice to see it in the QEMU log file. There is suitable log mask for the purpose. Linux guest does not provide this information, but still it would be nice to log that we have crashed. Signed-off-by: Anton Nefedov Signed-off-by: Denis V. Lunev CC: Paolo Bonzini CC: Marcelo Tosatti CC: Richard Henderson CC: Eduardo Habkost --- hw/misc/pvpanic.c | 1 + include/sysemu/kvm.h | 2 ++ kvm-all.c | 1 + stubs/Makefile.objs | 1 + stubs/kvm-crash.c | 8 ++++++++ target/i386/kvm.c | 51 +++++++++++++++++++++++++++++++++++++++++++++++++++ 6 files changed, 64 insertions(+) create mode 100644 stubs/kvm-crash.c diff --git a/hw/misc/pvpanic.c b/hw/misc/pvpanic.c index 0ac1e6a..221aa4e 100644 --- a/hw/misc/pvpanic.c +++ b/hw/misc/pvpanic.c @@ -42,6 +42,7 @@ static void handle_event(int event) } if (event & PVPANIC_PANICKED) { + qemu_log_mask(LOG_GUEST_ERROR, "Guest panicked\n"); qemu_system_guest_panicked(); return; } diff --git a/include/sysemu/kvm.h b/include/sysemu/kvm.h index 3045ee7..70cab9d 100644 --- a/include/sysemu/kvm.h +++ b/include/sysemu/kvm.h @@ -527,4 +527,6 @@ int kvm_set_one_reg(CPUState *cs, uint64_t id, void *source); */ int kvm_get_one_reg(CPUState *cs, uint64_t id, void *target); int kvm_get_max_memslots(void); + +void kvm_arch_log_crash(CPUState *cpu); #endif diff --git a/kvm-all.c b/kvm-all.c index 330219e..5f83389 100644 --- a/kvm-all.c +++ b/kvm-all.c @@ -2000,6 +2000,7 @@ int kvm_cpu_exec(CPUState *cpu) ret = EXCP_INTERRUPT; break; case KVM_SYSTEM_EVENT_CRASH: + kvm_arch_log_crash(cpu); qemu_mutex_lock_iothread(); qemu_system_guest_panicked(); qemu_mutex_unlock_iothread(); diff --git a/stubs/Makefile.objs b/stubs/Makefile.objs index a187295..3b1632a 100644 --- a/stubs/Makefile.objs +++ b/stubs/Makefile.objs @@ -35,3 +35,4 @@ stub-obj-y += qmp_pc_dimm_device_list.o stub-obj-y += target-monitor-defs.o stub-obj-y += target-get-monitor-def.o stub-obj-y += pc_madt_cpu_entry.o +stub-obj-y += kvm-crash.o diff --git a/stubs/kvm-crash.c b/stubs/kvm-crash.c new file mode 100644 index 0000000..36ab7f0 --- /dev/null +++ b/stubs/kvm-crash.c @@ -0,0 +1,8 @@ +#include "qemu/osdep.h" +#include "qemu-common.h" +#include "sysemu/kvm.h" + +void kvm_arch_log_crash(CPUState *cs) +{ + return; +} diff --git a/target/i386/kvm.c b/target/i386/kvm.c index 3b52821..899a83c 100644 --- a/target/i386/kvm.c +++ b/target/i386/kvm.c @@ -2020,6 +2020,36 @@ static int kvm_get_sregs(X86CPU *cpu) return 0; } +static int kvm_read_msr_hv_crash(X86CPU *cpu, uint64_t *buf) +{ + int i, ret; + struct { + struct kvm_msrs info; + struct kvm_msr_entry entries[HV_X64_MSR_CRASH_PARAMS]; + } msr_data; + + if (!has_msr_hv_crash) { + return -ENOSYS; + } + + for (i = 0; i < HV_X64_MSR_CRASH_PARAMS; i++) { + msr_data.entries[i].index = HV_X64_MSR_CRASH_P0 + i; + } + msr_data.info.nmsrs = HV_X64_MSR_CRASH_PARAMS; + + ret = kvm_vcpu_ioctl(CPU(cpu), KVM_GET_MSRS, &msr_data); + if (ret < 0) { + return ret; + } + + for (i = 0; i < ret; i++) { + const struct kvm_msr_entry *msr = msr_data.entries + i; + buf[msr->index - HV_X64_MSR_CRASH_P0] = msr->data; + } + + return 0; +} + static int kvm_get_msrs(X86CPU *cpu) { CPUX86State *env = &cpu->env; @@ -2767,6 +2797,27 @@ int kvm_arch_get_registers(CPUState *cs) return ret; } +void kvm_arch_log_crash(CPUState *cs) +{ + uint64_t msrs[HV_X64_MSR_CRASH_PARAMS]; + int ret; + X86CPU *cpu = X86_CPU(cs); + + qemu_log_mask(LOG_GUEST_ERROR, "Guest crashed\n"); + if (!has_msr_hv_crash) { + return; + } + + ret = kvm_read_msr_hv_crash(cpu, msrs); + if (ret < 0) { + qemu_log_mask(LOG_GUEST_ERROR, "Failed to get HV crash parameters\n"); + return; + } + qemu_log_mask(LOG_GUEST_ERROR, "HV crash parameters: (%#"PRIx64 + " %#"PRIx64" %#"PRIx64" %#"PRIx64" %#"PRIx64")\n", + msrs[0], msrs[1], msrs[2], msrs[3], msrs[4]); +} + void kvm_arch_pre_run(CPUState *cpu, struct kvm_run *run) { X86CPU *x86_cpu = X86_CPU(cpu);