From nobody Wed May  7 19:23:04 2025
Delivered-To: importer@patchew.org
Received-SPF: pass (zoho.com: domain of gnu.org designates 209.51.188.17 as
 permitted sender) client-ip=209.51.188.17;
 envelope-from=qemu-devel-bounces+importer=patchew.org@nongnu.org;
 helo=lists.gnu.org;
Authentication-Results: mx.zohomail.com;
	dkim=fail;
	spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted
 sender)  smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org;
	dmarc=fail(p=none dis=none)  header.from=linaro.org
ARC-Seal: i=1; a=rsa-sha256; t=1556558711; cv=none;
	d=zoho.com; s=zohoarc;
	b=Ib4+XjoVEYG9NL0VvWOsIeH2HKL8UmgwIizC7krCKCjFLVUvKdn3UvR91/KcrN49bIUtdJJqEXFgQyKzMnzOkFBi89Z6nRep/hR8sw0U5WSNMTfLTcdmOVbITOfrxdiP+7LZYpsaqFmqObNKgGfzrZ4KpZRXqB6sl9GNaxdxpyU=
ARC-Message-Signature: i=1; a=rsa-sha256; c=relaxed/relaxed; d=zoho.com;
 s=zohoarc;
	t=1556558711;
 h=Content-Transfer-Encoding:Date:From:In-Reply-To:List-Subscribe:List-Post:List-Id:List-Archive:List-Help:List-Unsubscribe:MIME-Version:Message-ID:References:Sender:Subject:To:ARC-Authentication-Results;
	bh=GBDO/4e++xgCc/SivTvk9ncGYDexkFJwWQi8bM72ET4=;
	b=CqbtOxoTFnkgjzojCH6q2ZDnGp/JARckQUdCsDFQGhivbcIbSLshK0WpLD+gsdGWi5PxVxPbbKirqoTnnWA9LbpKPcGy5J9E/ST2ZvT/s8pmLF6ZvUBYnXlbb+ZrxUFdFitJTY9NbgLjd2YNfzfW8DVEazg26WoxfIhZ5Cr1Uik=
ARC-Authentication-Results: i=1; mx.zoho.com;
	dkim=fail;
	spf=pass (zoho.com: domain of gnu.org designates 209.51.188.17 as permitted
 sender)  smtp.mailfrom=qemu-devel-bounces+importer=patchew.org@nongnu.org;
	dmarc=fail header.from=<peter.maydell@linaro.org> (p=none dis=none)
 header.from=<peter.maydell@linaro.org>
Return-Path: <qemu-devel-bounces+importer=patchew.org@nongnu.org>
Received: from lists.gnu.org (lists.gnu.org [209.51.188.17]) by
 mx.zohomail.com
	with SMTPS id 1556558711955675.1562193753663;
 Mon, 29 Apr 2019 10:25:11 -0700 (PDT)
Received: from localhost ([127.0.0.1]:60926 helo=lists.gnu.org)
	by lists.gnu.org with esmtp (Exim 4.71)
	(envelope-from <qemu-devel-bounces+importer=patchew.org@nongnu.org>)
	id 1hLA1X-0007iZ-LE
	for importer@patchew.org; Mon, 29 Apr 2019 13:25:03 -0400
Received: from eggs.gnu.org ([209.51.188.92]:34515)
	by lists.gnu.org with esmtp (Exim 4.71)
	(envelope-from <peter.maydell@linaro.org>) id 1hL9ew-0004yK-9K
	for qemu-devel@nongnu.org; Mon, 29 Apr 2019 13:01:43 -0400
Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71)
	(envelope-from <peter.maydell@linaro.org>) id 1hL9et-0006o0-Ac
	for qemu-devel@nongnu.org; Mon, 29 Apr 2019 13:01:41 -0400
Received: from mail-wr1-x42b.google.com ([2a00:1450:4864:20::42b]:45471)
	by eggs.gnu.org with esmtps (TLS1.0:RSA_AES_128_CBC_SHA1:16)
	(Exim 4.71) (envelope-from <peter.maydell@linaro.org>)
	id 1hL9er-0006Y3-O8
	for qemu-devel@nongnu.org; Mon, 29 Apr 2019 13:01:39 -0400
Received: by mail-wr1-x42b.google.com with SMTP id s15so17081739wra.12
	for <qemu-devel@nongnu.org>; Mon, 29 Apr 2019 10:01:08 -0700 (PDT)
Received: from orth.archaic.org.uk (orth.archaic.org.uk. [81.2.115.148])
	by smtp.gmail.com with ESMTPSA id a13sm36896wmj.39.2019.04.29.10.01.05
	for <qemu-devel@nongnu.org>
	(version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128);
	Mon, 29 Apr 2019 10:01:06 -0700 (PDT)
DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=linaro.org; s=google;
	h=from:to:subject:date:message-id:in-reply-to:references:mime-version
	:content-transfer-encoding;
	bh=GBDO/4e++xgCc/SivTvk9ncGYDexkFJwWQi8bM72ET4=;
	b=pkhs7dw2mqrIPbt68ipaCRJY3OmAp/AU0h+n8XhyeAGWSH0nKGETaTEO6WXPej6lJC
	hwodlcDOYfq3/XoIgz8CcMQ7Pgc9TGNzp7dDFo98/PVzFFxS+jMN1zwX+qbA1DiazZHZ
	BC9jCmeaZ8RekEs9zstsnhK5rx8xlWYry0A+GtjhT5rg1S2wpA3fHsdoBnB7pcMAuhwG
	7t58lNxUJqonVhS2GnXFYDxpGwz58J8Ptk7uYnDrPctMj/cq+JjsCDw02SgwpLN/HfYF
	DT2IhUC5n9swi0BI5D+A44z6yOaOTkqCD7QBk3nvxJmRV3CkZMpa4MrgCaRRWklyxp5R
	AYfQ==
X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed;
	d=1e100.net; s=20161025;
	h=x-gm-message-state:from:to:subject:date:message-id:in-reply-to
	:references:mime-version:content-transfer-encoding;
	bh=GBDO/4e++xgCc/SivTvk9ncGYDexkFJwWQi8bM72ET4=;
	b=CFzYvr5eqHrOl/JOgGLXKfwziyoCT4Q+ZEzSad5whkel3DJcH7DN5nFqItvDmYev+1
	QXHE5pbvx3P8ngu5EFzh9PCnG0j5ZO2e0gZEA6MaUzCUU2sQfFKhIR7r1McPm0HG+HFd
	WBxHSY6EDhARA6qks4FroRfPCZ83PPvVNV/gkIhHNNwy+mXEwB3dK/UqZgqZJVZZ/cZQ
	X9FSFI/Bldxb51ghKOjH9LWQKAOy166aIQTQEqrBQymWH6kfE887ESG7UjF8o4ANMvUQ
	2TVdyEGgJkPVE43eZlorEsNT7WFEec+jD739hmJax3kIBBQudozHBeG2HxG1app0Tez5
	4bRw==
X-Gm-Message-State: APjAAAVt6sagHv1XM6MLxsQDgR54q+kGvAiIIzBWldb6sPQ8scbk+cd0
	JwCqI71i4A74wAtRDoyY74mPn4I3ZuA=
X-Google-Smtp-Source: 
 APXvYqwItw1G2xidHiCAgKbVYVAgmS8SLBXZAe4aYKAH72zkli1vL99EbRYNA9o1qGl2r+ao0U7iFA==
X-Received: by 2002:adf:dd46:: with SMTP id u6mr3733211wrm.228.1556557267596;
	Mon, 29 Apr 2019 10:01:07 -0700 (PDT)
From: Peter Maydell <peter.maydell@linaro.org>
To: qemu-devel@nongnu.org
Date: Mon, 29 Apr 2019 18:00:15 +0100
Message-Id: <20190429170030.11323-28-peter.maydell@linaro.org>
X-Mailer: git-send-email 2.20.1
In-Reply-To: <20190429170030.11323-1-peter.maydell@linaro.org>
References: <20190429170030.11323-1-peter.maydell@linaro.org>
MIME-Version: 1.0
Content-Transfer-Encoding: quoted-printable
X-detected-operating-system: by eggs.gnu.org: Genre and OS details not
	recognized.
X-Received-From: 2a00:1450:4864:20::42b
Subject: [Qemu-devel] [PULL 27/42] target/arm: Implement VLSTM for v7M CPUs
 with an FPU
X-BeenThere: qemu-devel@nongnu.org
X-Mailman-Version: 2.1.21
Precedence: list
List-Id: <qemu-devel.nongnu.org>
List-Unsubscribe: <https://lists.nongnu.org/mailman/options/qemu-devel>,
	<mailto:qemu-devel-request@nongnu.org?subject=unsubscribe>
List-Archive: <http://lists.nongnu.org/archive/html/qemu-devel/>
List-Post: <mailto:qemu-devel@nongnu.org>
List-Help: <mailto:qemu-devel-request@nongnu.org?subject=help>
List-Subscribe: <https://lists.nongnu.org/mailman/listinfo/qemu-devel>,
	<mailto:qemu-devel-request@nongnu.org?subject=subscribe>
Errors-To: qemu-devel-bounces+importer=patchew.org@nongnu.org
Sender: "Qemu-devel" <qemu-devel-bounces+importer=patchew.org@nongnu.org>
X-ZohoMail-DKIM: fail (Header signature does not verify)
Content-Type: text/plain; charset="utf-8"

Implement the VLSTM instruction for v7M for the FPU present case.

Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
Reviewed-by: Richard Henderson <richard.henderson@linaro.org>
Message-id: 20190416125744.27770-25-peter.maydell@linaro.org
---
 target/arm/cpu.h       |  2 +
 target/arm/helper.h    |  2 +
 target/arm/helper.c    | 84 ++++++++++++++++++++++++++++++++++++++++++
 target/arm/translate.c | 15 +++++++-
 4 files changed, 102 insertions(+), 1 deletion(-)

diff --git a/target/arm/cpu.h b/target/arm/cpu.h
index 0b10aefb93d..22bc6e00ab9 100644
--- a/target/arm/cpu.h
+++ b/target/arm/cpu.h
@@ -58,6 +58,8 @@
 #define EXCP_INVSTATE       18   /* v7M INVSTATE UsageFault */
 #define EXCP_STKOF          19   /* v8M STKOF UsageFault */
 #define EXCP_LAZYFP         20   /* v7M fault during lazy FP stacking */
+#define EXCP_LSERR          21   /* v8M LSERR SecureFault */
+#define EXCP_UNALIGNED      22   /* v7M UNALIGNED UsageFault */
 /* NB: add new EXCP_ defines to the array in arm_log_exception() too */
=20
 #define ARMV7M_EXCP_RESET   1
diff --git a/target/arm/helper.h b/target/arm/helper.h
index 0a3a80528c7..62051ae6d51 100644
--- a/target/arm/helper.h
+++ b/target/arm/helper.h
@@ -71,6 +71,8 @@ DEF_HELPER_3(v7m_tt, i32, env, i32, i32)
=20
 DEF_HELPER_1(v7m_preserve_fp_state, void, env)
=20
+DEF_HELPER_2(v7m_vlstm, void, env, i32)
+
 DEF_HELPER_2(v8m_stackcheck, void, env, i32)
=20
 DEF_HELPER_4(access_check_cp_reg, void, env, ptr, i32, i32)
diff --git a/target/arm/helper.c b/target/arm/helper.c
index b11f8aa14df..b821037c3b6 100644
--- a/target/arm/helper.c
+++ b/target/arm/helper.c
@@ -7384,6 +7384,12 @@ void HELPER(v7m_preserve_fp_state)(CPUARMState *env)
     g_assert_not_reached();
 }
=20
+void HELPER(v7m_vlstm)(CPUARMState *env, uint32_t fptr)
+{
+    /* translate.c should never generate calls here in user-only mode */
+    g_assert_not_reached();
+}
+
 uint32_t HELPER(v7m_tt)(CPUARMState *env, uint32_t addr, uint32_t op)
 {
     /* The TT instructions can be used by unprivileged code, but in
@@ -8400,6 +8406,74 @@ static void v7m_update_fpccr(CPUARMState *env, uint3=
2_t frameptr,
     }
 }
=20
+void HELPER(v7m_vlstm)(CPUARMState *env, uint32_t fptr)
+{
+    /* fptr is the value of Rn, the frame pointer we store the FP regs to =
*/
+    bool s =3D env->v7m.fpccr[M_REG_S] & R_V7M_FPCCR_S_MASK;
+    bool lspact =3D env->v7m.fpccr[s] & R_V7M_FPCCR_LSPACT_MASK;
+
+    assert(env->v7m.secure);
+
+    if (!(env->v7m.control[M_REG_S] & R_V7M_CONTROL_SFPA_MASK)) {
+        return;
+    }
+
+    /* Check access to the coprocessor is permitted */
+    if (!v7m_cpacr_pass(env, true, arm_current_el(env) !=3D 0)) {
+        raise_exception_ra(env, EXCP_NOCP, 0, 1, GETPC());
+    }
+
+    if (lspact) {
+        /* LSPACT should not be active when there is active FP state */
+        raise_exception_ra(env, EXCP_LSERR, 0, 1, GETPC());
+    }
+
+    if (fptr & 7) {
+        raise_exception_ra(env, EXCP_UNALIGNED, 0, 1, GETPC());
+    }
+
+    /*
+     * Note that we do not use v7m_stack_write() here, because the
+     * accesses should not set the FSR bits for stacking errors if they
+     * fail. (In pseudocode terms, they are AccType_NORMAL, not AccType_ST=
ACK
+     * or AccType_LAZYFP). Faults in cpu_stl_data() will throw exceptions
+     * and longjmp out.
+     */
+    if (!(env->v7m.fpccr[M_REG_S] & R_V7M_FPCCR_LSPEN_MASK)) {
+        bool ts =3D env->v7m.fpccr[M_REG_S] & R_V7M_FPCCR_TS_MASK;
+        int i;
+
+        for (i =3D 0; i < (ts ? 32 : 16); i +=3D 2) {
+            uint64_t dn =3D *aa32_vfp_dreg(env, i / 2);
+            uint32_t faddr =3D fptr + 4 * i;
+            uint32_t slo =3D extract64(dn, 0, 32);
+            uint32_t shi =3D extract64(dn, 32, 32);
+
+            if (i >=3D 16) {
+                faddr +=3D 8; /* skip the slot for the FPSCR */
+            }
+            cpu_stl_data(env, faddr, slo);
+            cpu_stl_data(env, faddr + 4, shi);
+        }
+        cpu_stl_data(env, fptr + 0x40, vfp_get_fpscr(env));
+
+        /*
+         * If TS is 0 then s0 to s15 and FPSCR are UNKNOWN; we choose to
+         * leave them unchanged, matching our choice in v7m_preserve_fp_st=
ate.
+         */
+        if (ts) {
+            for (i =3D 0; i < 32; i +=3D 2) {
+                *aa32_vfp_dreg(env, i / 2) =3D 0;
+            }
+            vfp_set_fpscr(env, 0);
+        }
+    } else {
+        v7m_update_fpccr(env, fptr, false);
+    }
+
+    env->v7m.control[M_REG_S] &=3D ~R_V7M_CONTROL_FPCA_MASK;
+}
+
 static bool v7m_push_stack(ARMCPU *cpu)
 {
     /* Do the "set up stack frame" part of exception entry,
@@ -9160,6 +9234,8 @@ static void arm_log_exception(int idx)
             [EXCP_INVSTATE] =3D "v7M INVSTATE UsageFault",
             [EXCP_STKOF] =3D "v8M STKOF UsageFault",
             [EXCP_LAZYFP] =3D "v7M exception during lazy FP stacking",
+            [EXCP_LSERR] =3D "v8M LSERR UsageFault",
+            [EXCP_UNALIGNED] =3D "v7M UNALIGNED UsageFault",
         };
=20
         if (idx >=3D 0 && idx < ARRAY_SIZE(excnames)) {
@@ -9334,6 +9410,14 @@ void arm_v7m_cpu_do_interrupt(CPUState *cs)
         armv7m_nvic_set_pending(env->nvic, ARMV7M_EXCP_USAGE, env->v7m.sec=
ure);
         env->v7m.cfsr[env->v7m.secure] |=3D R_V7M_CFSR_STKOF_MASK;
         break;
+    case EXCP_LSERR:
+        armv7m_nvic_set_pending(env->nvic, ARMV7M_EXCP_SECURE, false);
+        env->v7m.sfsr |=3D R_V7M_SFSR_LSERR_MASK;
+        break;
+    case EXCP_UNALIGNED:
+        armv7m_nvic_set_pending(env->nvic, ARMV7M_EXCP_USAGE, env->v7m.sec=
ure);
+        env->v7m.cfsr[env->v7m.secure] |=3D R_V7M_CFSR_UNALIGNED_MASK;
+        break;
     case EXCP_SWI:
         /* The PC already points to the next instruction.  */
         armv7m_nvic_set_pending(env->nvic, ARMV7M_EXCP_SVC, env->v7m.secur=
e);
diff --git a/target/arm/translate.c b/target/arm/translate.c
index 4f29d09a28a..99b38dd5f2b 100644
--- a/target/arm/translate.c
+++ b/target/arm/translate.c
@@ -11818,7 +11818,20 @@ static void disas_thumb2_insn(DisasContext *s, uin=
t32_t insn)
                 if (!s->v8m_secure || (insn & 0x0040f0ff)) {
                     goto illegal_op;
                 }
-                /* Just NOP since FP support is not implemented */
+
+                if (arm_dc_feature(s, ARM_FEATURE_VFP)) {
+                    TCGv_i32 fptr =3D load_reg(s, rn);
+
+                    if (extract32(insn, 20, 1)) {
+                        /* VLLDM */
+                    } else {
+                        gen_helper_v7m_vlstm(cpu_env, fptr);
+                    }
+                    tcg_temp_free_i32(fptr);
+
+                    /* End the TB, because we have updated FP control bits=
 */
+                    s->base.is_jmp =3D DISAS_UPDATE;
+                }
                 break;
             }
             if (arm_dc_feature(s, ARM_FEATURE_VFP) &&
--=20
2.20.1