From patchwork Wed May 22 09:13:10 2019 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Hesham Almatary X-Patchwork-Id: 1103261 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Authentication-Results: ozlabs.org; spf=pass (mailfrom) smtp.mailfrom=nongnu.org (client-ip=209.51.188.17; helo=lists.gnu.org; envelope-from=qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org; receiver=) Authentication-Results: ozlabs.org; dmarc=none (p=none dis=none) header.from=cl.cam.ac.uk Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) (using TLSv1 with cipher DHE-RSA-AES256-SHA (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id 4586QK3gvBz9s5c for ; Wed, 22 May 2019 19:14:17 +1000 (AEST) Received: from localhost ([127.0.0.1]:38938 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1hTNKB-0002P8-Fo for incoming@patchwork.ozlabs.org; Wed, 22 May 2019 05:14:15 -0400 Received: from eggs.gnu.org ([209.51.188.92]:41251) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1hTNJN-0002NS-J9 for qemu-devel@nongnu.org; Wed, 22 May 2019 05:13:26 -0400 Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1hTNJJ-0005qE-Rk for qemu-devel@nongnu.org; Wed, 22 May 2019 05:13:23 -0400 Received: from mta1.cl.cam.ac.uk ([2a05:b400:110::25:1]:41341) by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.71) (envelope-from ) id 1hTNJD-0005gk-Rc; Wed, 22 May 2019 05:13:15 -0400 Received: from cassia.cl.cam.ac.uk ([2001:630:212:238:b26e:bfff:fe2f:c7d9]) by mta1.cl.cam.ac.uk with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1hTNJC-0007CP-Ba; Wed, 22 May 2019 09:13:14 +0000 Received: from hmka2 by cassia.cl.cam.ac.uk with local (Exim 4.90_1) (envelope-from ) id 1hTNJC-00083r-93; Wed, 22 May 2019 10:13:14 +0100 From: Hesham Almatary To: qemu-riscv@nongnu.org Date: Wed, 22 May 2019 10:13:10 +0100 Message-Id: <20190522091310.30941-1-Hesham.Almatary@cl.cam.ac.uk> X-Mailer: git-send-email 2.17.1 X-detected-operating-system: by eggs.gnu.org: Genre and OS details not recognized. X-Received-From: 2a05:b400:110::25:1 Subject: [Qemu-devel] [PATCHv3 4/5] RISC-V: Fix a PMP bug where it succeeds even if PMP entry is off 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: Sagar Karandikar , Bastian Koppelmann , Palmer Dabbelt , qemu-devel@nongnu.org, Alistair Francis , Hesham Almatary Errors-To: qemu-devel-bounces+incoming=patchwork.ozlabs.org@nongnu.org Sender: "Qemu-devel" The current implementation returns 1 (PMP check success) if the address is in range even if the PMP entry is off. This is a bug. For example, if there is a PMP check in S-Mode which is in range, but its PMP entry is off, this will succeed, which it should not. The patch fixes this bug by only checking the PMP permissions if the address is in range and its corresponding PMP entry it not off. Otherwise, it will keep the ret = -1 which will be checked and handled correctly at the end of the function. Signed-off-by: Hesham Almatary Reviewed-by: Alistair Francis --- target/riscv/pmp.c | 9 +++++---- 1 file changed, 5 insertions(+), 4 deletions(-) -- 2.17.1 diff --git a/target/riscv/pmp.c b/target/riscv/pmp.c index b11c4ae22f..8668f0dd7c 100644 --- a/target/riscv/pmp.c +++ b/target/riscv/pmp.c @@ -259,11 +259,12 @@ bool pmp_hart_has_privs(CPURISCVState *env, target_ulong addr, /* fully inside */ const uint8_t a_field = pmp_get_a_field(env->pmp_state.pmp[i].cfg_reg); - if ((s + e) == 2) { - if (PMP_AMATCH_OFF == a_field) { - return 1; - } + /* + * If the PMP entry is not off and the address is in range, do the priv + * check + */ + if (((s + e) == 2) && (PMP_AMATCH_OFF != a_field)) { allowed_privs = PMP_READ | PMP_WRITE | PMP_EXEC; if ((env->priv != PRV_M) || pmp_is_locked(env, i)) { allowed_privs &= env->pmp_state.pmp[i].cfg_reg;