From patchwork Fri May 29 15:19:24 2015 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 8bit X-Patchwork-Submitter: =?utf-8?q?Alex_Benn=C3=A9e?= X-Patchwork-Id: 49231 Return-Path: X-Original-To: linaro@patches.linaro.org Delivered-To: linaro@patches.linaro.org Received: from mail-lb0-f199.google.com (mail-lb0-f199.google.com [209.85.217.199]) by ip-10-151-82-157.ec2.internal (Postfix) with ESMTPS id A0820218EC for ; Fri, 29 May 2015 15:21:56 +0000 (UTC) Received: by lbbqq2 with SMTP id qq2sf19916788lbb.0 for ; Fri, 29 May 2015 08:21:55 -0700 (PDT) X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20130820; h=x-gm-message-state:delivered-to:from:to:date:message-id:in-reply-to :references:mime-version:content-type:content-transfer-encoding:cc :subject:precedence:list-id:list-unsubscribe:list-archive:list-post :list-help:list-subscribe:errors-to:sender:x-original-sender :x-original-authentication-results:mailing-list; bh=SWMW6ySVKAQJNO3f8wLZPae13c2lgbJp0vdbhPplG+o=; b=QU1S88Ubqs/W3Zgfc+n+7yZwA/V3+Q+9s/oPaeQix0SpS087o8w6Z6U+sWceHu1vJ0 YjDw9lmsvlLMwr64/aMyuIifSx23P6D9FuiVT7VsF5xHHjgXW4CRcGWX1gQ1JNooZMF1 l8RkmowX3Y1MHn889/dHjfJhmFGTT8NDF4KGxiIEm0lPcAnUhBZ9JwtpfHS7CNMkGj9J XHnvNlDlXBZV6os0m1arqGEyM3bcCVyW/IAFDonQ9l9UHo5oqQyyGMVPauGsnBlYuYj8 ykDgWYMfrD7WAMH0dpNDysSZd/O1FWp8M/wQJ19jevxBB7gUxJvtg7zdsFATqPU1pK4+ 6KMA== X-Gm-Message-State: ALoCoQmQdJELNxvjEKFvd4awngNidWT7E0i8TeACjWPvcYLzecG+71HlHdFYzrh3Zi7rKKZnq7rk X-Received: by 10.194.175.36 with SMTP id bx4mr7673459wjc.1.1432912915016; Fri, 29 May 2015 08:21:55 -0700 (PDT) X-BeenThere: patchwork-forward@linaro.org Received: by 10.152.88.3 with SMTP id bc3ls365062lab.22.gmail; Fri, 29 May 2015 08:21:54 -0700 (PDT) X-Received: by 10.152.203.162 with SMTP id kr2mr8597136lac.68.1432912914720; Fri, 29 May 2015 08:21:54 -0700 (PDT) Received: from mail-lb0-f173.google.com (mail-lb0-f173.google.com. [209.85.217.173]) by mx.google.com with ESMTPS id mh3si4941812lbb.59.2015.05.29.08.21.54 for (version=TLSv1.2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Fri, 29 May 2015 08:21:54 -0700 (PDT) Received-SPF: pass (google.com: domain of patch+caf_=patchwork-forward=linaro.org@linaro.org designates 209.85.217.173 as permitted sender) client-ip=209.85.217.173; Received: by lbcue7 with SMTP id ue7so50679709lbc.0 for ; Fri, 29 May 2015 08:21:54 -0700 (PDT) X-Received: by 10.152.2.133 with SMTP id 5mr7165550lau.36.1432912914622; Fri, 29 May 2015 08:21:54 -0700 (PDT) X-Forwarded-To: patchwork-forward@linaro.org X-Forwarded-For: patch@linaro.org patchwork-forward@linaro.org Delivered-To: patch@linaro.org Received: by 10.112.108.230 with SMTP id hn6csp419689lbb; Fri, 29 May 2015 08:21:53 -0700 (PDT) X-Received: by 10.55.33.155 with SMTP id f27mr17042649qki.106.1432912912608; Fri, 29 May 2015 08:21:52 -0700 (PDT) Received: from lists.gnu.org (lists.gnu.org. [2001:4830:134:3::11]) by mx.google.com with ESMTPS id e30si5839906qkh.102.2015.05.29.08.21.52 for (version=TLSv1 cipher=RC4-SHA bits=128/128); Fri, 29 May 2015 08:21:52 -0700 (PDT) Received-SPF: pass (google.com: domain of qemu-devel-bounces+patch=linaro.org@nongnu.org designates 2001:4830:134:3::11 as permitted sender) client-ip=2001:4830:134:3::11; Received: from localhost ([::1]:36646 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1YyM6Z-0003NV-JA for patch@linaro.org; Fri, 29 May 2015 11:21:51 -0400 Received: from eggs.gnu.org ([2001:4830:134:3::10]:59658) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1YyM49-0008EE-EM for qemu-devel@nongnu.org; Fri, 29 May 2015 11:19:22 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1YyM47-0000ol-9T for qemu-devel@nongnu.org; Fri, 29 May 2015 11:19:21 -0400 Received: from static.88-198-71-155.clients.your-server.de ([88.198.71.155]:35690 helo=socrates.bennee.com) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1YyM47-0000oc-0c for qemu-devel@nongnu.org; Fri, 29 May 2015 11:19:19 -0400 Received: from localhost ([127.0.0.1] helo=zen.linaroharston) by socrates.bennee.com with esmtp (Exim 4.80) (envelope-from ) id 1YyNOS-0005fR-0q; Fri, 29 May 2015 18:44:24 +0200 From: =?UTF-8?q?Alex=20Benn=C3=A9e?= To: qemu-devel@nongnu.org, peter.maydell@linaro.org, christoffer.dall@linaro.org, zhichao.huang@linaro.org Date: Fri, 29 May 2015 16:19:24 +0100 Message-Id: <1432912764-7073-7-git-send-email-alex.bennee@linaro.org> X-Mailer: git-send-email 2.4.1 In-Reply-To: <1432912764-7073-1-git-send-email-alex.bennee@linaro.org> References: <1432912764-7073-1-git-send-email-alex.bennee@linaro.org> MIME-Version: 1.0 X-SA-Exim-Connect-IP: 127.0.0.1 X-SA-Exim-Mail-From: alex.bennee@linaro.org X-SA-Exim-Scanned: No (on socrates.bennee.com); SAEximRunCond expanded to false X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x X-Received-From: 88.198.71.155 Cc: =?UTF-8?q?Alex=20Benn=C3=A9e?= , kvm@vger.kernel.org, marc.zyngier@arm.com, Paolo Bonzini , =?UTF-8?q?Alex=20Benn=C3=A9e?= , kvmarm@lists.cs.columbia.edu, linux-arm-kernel@lists.infradead.org Subject: [Qemu-devel] [PATCH v5 6/6] target-arm: kvm - re-inject guest debug exceptions X-BeenThere: qemu-devel@nongnu.org X-Mailman-Version: 2.1.14 Precedence: list List-Id: List-Unsubscribe: , List-Archive: List-Post: , List-Help: , List-Subscribe: , Errors-To: qemu-devel-bounces+patch=linaro.org@nongnu.org Sender: qemu-devel-bounces+patch=linaro.org@nongnu.org X-Removed-Original-Auth: Dkim didn't pass. X-Original-Sender: alex.bennee@linaro.org X-Original-Authentication-Results: mx.google.com; spf=pass (google.com: domain of patch+caf_=patchwork-forward=linaro.org@linaro.org designates 209.85.217.173 as permitted sender) smtp.mail=patch+caf_=patchwork-forward=linaro.org@linaro.org Mailing-list: list patchwork-forward@linaro.org; contact patchwork-forward+owners@linaro.org X-Google-Group-Id: 836684582541 From: Alex Bennée If we can't find details for the debug exception in our debug state then we can assume the exception is due to debugging inside the guest. To inject the exception into the guest state we re-use the TCG exception code (do_interupt). However while guest debugging is in effect we currently can't handle the guest using single step which is heavily used by GDB. Signed-off-by: Alex Bennée --- v5: - new for v5 --- target-arm/cpu.h | 1 + target-arm/helper-a64.c | 17 ++++++++++++++--- target-arm/internals.h | 1 + target-arm/kvm.c | 30 ++++++++++++++++++++++-------- 4 files changed, 38 insertions(+), 11 deletions(-) diff --git a/target-arm/cpu.h b/target-arm/cpu.h index 083211c..95ae3a8 100644 --- a/target-arm/cpu.h +++ b/target-arm/cpu.h @@ -56,6 +56,7 @@ #define EXCP_SMC 13 /* Secure Monitor Call */ #define EXCP_VIRQ 14 #define EXCP_VFIQ 15 +#define EXCP_WAPT 16 #define ARMV7M_EXCP_RESET 1 #define ARMV7M_EXCP_NMI 2 diff --git a/target-arm/helper-a64.c b/target-arm/helper-a64.c index 861f6fa..32bd27d 100644 --- a/target-arm/helper-a64.c +++ b/target-arm/helper-a64.c @@ -25,6 +25,7 @@ #include "qemu/bitops.h" #include "internals.h" #include "qemu/crc32c.h" +#include "sysemu/kvm.h" #include /* For crc32 */ /* C2.4.7 Multiply and divide */ @@ -478,10 +479,13 @@ void aarch64_cpu_do_interrupt(CPUState *cs) } arm_log_exception(cs->exception_index); - qemu_log_mask(CPU_LOG_INT, "...from EL%d\n", arm_current_el(env)); + qemu_log_mask(CPU_LOG_INT, "...from EL%d PC 0x%" PRIx64 "\n", + arm_current_el(env), env->pc); + if (qemu_loglevel_mask(CPU_LOG_INT) && !excp_is_internal(cs->exception_index)) { - qemu_log_mask(CPU_LOG_INT, "...with ESR 0x%" PRIx32 "\n", + qemu_log_mask(CPU_LOG_INT, "...with ESR %x/0x%" PRIx32 "\n", + env->exception.syndrome >> ARM_EL_EC_SHIFT, env->exception.syndrome); } @@ -494,6 +498,7 @@ void aarch64_cpu_do_interrupt(CPUState *cs) switch (cs->exception_index) { case EXCP_PREFETCH_ABORT: case EXCP_DATA_ABORT: + case EXCP_WAPT: env->cp15.far_el[new_el] = env->exception.vaddress; qemu_log_mask(CPU_LOG_INT, "...with FAR 0x%" PRIx64 "\n", env->cp15.far_el[new_el]); @@ -539,6 +544,12 @@ void aarch64_cpu_do_interrupt(CPUState *cs) aarch64_restore_sp(env, new_el); env->pc = addr; - cs->interrupt_request |= CPU_INTERRUPT_EXITTB; + + qemu_log_mask(CPU_LOG_INT, "...to EL%d PC 0x%" PRIx64 " PSTATE 0x%x\n", + new_el, env->pc, pstate_read(env)); + + if (!kvm_enabled()) { + cs->interrupt_request |= CPU_INTERRUPT_EXITTB; + } } #endif diff --git a/target-arm/internals.h b/target-arm/internals.h index 2cc3017..10e8999 100644 --- a/target-arm/internals.h +++ b/target-arm/internals.h @@ -58,6 +58,7 @@ static const char * const excnames[] = { [EXCP_SMC] = "Secure Monitor Call", [EXCP_VIRQ] = "Virtual IRQ", [EXCP_VFIQ] = "Virtual FIQ", + [EXCP_WAPT] = "Watchpoint", }; static inline void arm_log_exception(int idx) diff --git a/target-arm/kvm.c b/target-arm/kvm.c index e1fccdd..6f608d8 100644 --- a/target-arm/kvm.c +++ b/target-arm/kvm.c @@ -523,9 +523,11 @@ static int kvm_handle_debug(CPUState *cs, struct kvm_run *run) struct kvm_debug_exit_arch *arch_info = &run->debug.arch; int hsr_ec = arch_info->hsr >> ARM_EL_EC_SHIFT; ARMCPU *cpu = ARM_CPU(cs); + CPUClass *cc = CPU_GET_CLASS(cs); CPUARMState *env = &cpu->env; + int forward_excp = EXCP_BKPT; - /* Ensure PC is synchronised */ + /* Ensure all state is synchronised */ kvm_cpu_synchronize_state(cs); switch (hsr_ec) { @@ -533,7 +535,14 @@ static int kvm_handle_debug(CPUState *cs, struct kvm_run *run) if (cs->singlestep_enabled) { return true; } else { - error_report("Came out of SINGLE STEP when not enabled"); + /* + * The kernel should have supressed the guests ability to + * single step at this point so something has gone wrong. + */ + error_report("%s: guest single-step while debugging unsupported" + " (%"PRIx64", %"PRIx32")\n", + __func__, env->pc, arch_info->hsr); + return false; } break; case EC_AA64_BKPT: @@ -549,19 +558,24 @@ static int kvm_handle_debug(CPUState *cs, struct kvm_run *run) case EC_WATCHPOINT: if (kvm_arm_find_hw_watchpoint(cs, arch_info->far)) { return true; + } else { + forward_excp = EXCP_WAPT; } break; default: error_report("%s: unhandled debug exit (%"PRIx32", %"PRIx64")\n", __func__, arch_info->hsr, env->pc); + return false; } - /* If we don't handle this it could be it really is for the - guest to handle */ - qemu_log_mask(LOG_UNIMP, - "%s: re-injecting exception not yet implemented" - " (0x%"PRIx32", %"PRIx64")\n", - __func__, hsr_ec, env->pc); + /* If we are not handling the debug exception it must belong to + * the guest. Let's re-use the existing TCG interrupt code to set + * everything up properly + */ + cs->exception_index = forward_excp; + env->exception.syndrome = arch_info->hsr; + env->exception.vaddress = arch_info->far; + cc->do_interrupt(cs); return false; }