The branch main has been updated by andrew:

URL: 
https://cgit.FreeBSD.org/src/commit/?id=b47a6c93e262f4245492c947af8a600a4b1fe308

commit b47a6c93e262f4245492c947af8a600a4b1fe308
Author:     Andrew Turner <and...@freebsd.org>
AuthorDate: 2025-06-23 10:16:03 +0000
Commit:     Andrew Turner <and...@freebsd.org>
CommitDate: 2025-06-23 10:18:19 +0000

    arm64: Reduce where we decode msr/mrs instructions
    
    We only use the mrs_Op* and mrs_CR* functions and MRS_* macros when
    handling userspace executing a msr/msr instruction.
    
    Move the macros to where they are used and expand the functions to
    just use the macros directly.
    
    While here update MRS_Op0_MASK to include bit 20 as this will cause
    the correct op0 value to be calculated for all instructions we decode.
    
    Reviewed by:    Harry Moulton <harry.moul...@arm.com>
    Sponsored by:   Arm Ltd
    Differential Revision:  https://reviews.freebsd.org/D50214
---
 sys/arm64/arm64/undefined.c   | 49 ++++++++++++++++++++++++++++++++++++-------
 sys/arm64/include/armreg.h    | 19 -----------------
 sys/arm64/include/undefined.h | 20 ------------------
 3 files changed, 42 insertions(+), 46 deletions(-)

diff --git a/sys/arm64/arm64/undefined.c b/sys/arm64/arm64/undefined.c
index a88d47c182cf..19f34fa91702 100644
--- a/sys/arm64/arm64/undefined.c
+++ b/sys/arm64/arm64/undefined.c
@@ -327,16 +327,30 @@ static bool
 undef_sys_insn(struct trapframe *frame, uint32_t insn)
 {
        uint64_t esr;
-       int op0;
        bool read;
 
+#define        MRS_MASK                        0xfff00000
+#define        MRS_VALUE                       0xd5300000
+#define        MSR_REG_VALUE                   0xd5100000
+#define        MSR_IMM_VALUE                   0xd5000000
+#define        MRS_REGISTER(insn)              ((insn) & 0x0000001f)
+#define         MRS_Op0_SHIFT                  19
+#define         MRS_Op0_MASK                   0x00180000
+#define         MRS_Op1_SHIFT                  16
+#define         MRS_Op1_MASK                   0x00070000
+#define         MRS_CRn_SHIFT                  12
+#define         MRS_CRn_MASK                   0x0000f000
+#define         MRS_CRm_SHIFT                  8
+#define         MRS_CRm_MASK                   0x00000f00
+#define         MRS_Op2_SHIFT                  5
+#define         MRS_Op2_MASK                   0x000000e0
+
        read = false;
        switch (insn & MRS_MASK) {
        case MRS_VALUE:
                read = true;
-               /* FALLTHROUGH */
+               break;
        case MSR_REG_VALUE:
-               op0 = mrs_Op0(insn);
                break;
        case MSR_IMM_VALUE:
                /*
@@ -346,9 +360,10 @@ undef_sys_insn(struct trapframe *frame, uint32_t insn)
                 */
                if (MRS_REGISTER(insn) != 31)
                        return (false);
-               if (mrs_CRn(insn) != 4)
+               if ((insn & MRS_CRn_MASK) >> MRS_CRn_SHIFT != 4)
+                       return (false);
+               if ((insn & MRS_Op0_MASK) >> MRS_Op0_SHIFT != 0)
                        return (false);
-               op0 = 0;
                break;
        default:
                return (false);
@@ -357,12 +372,32 @@ undef_sys_insn(struct trapframe *frame, uint32_t insn)
        /* Create a fake EXCP_MSR esr value */
        esr = EXCP_MSR << ESR_ELx_EC_SHIFT;
        esr |= ESR_ELx_IL;
-       esr |= __ISS_MSR_REG(op0, mrs_Op1(insn), mrs_CRn(insn), mrs_CRm(insn),
-           mrs_Op2(insn));
+       esr |= __ISS_MSR_REG(
+           (insn & MRS_Op0_MASK) >> MRS_Op0_SHIFT,
+           (insn & MRS_Op1_MASK) >> MRS_Op1_SHIFT,
+           (insn & MRS_CRn_MASK) >> MRS_CRn_SHIFT,
+           (insn & MRS_CRm_MASK) >> MRS_CRm_SHIFT,
+           (insn & MRS_Op2_MASK) >> MRS_Op2_SHIFT);
        esr |= MRS_REGISTER(insn) << ISS_MSR_Rt_SHIFT;
        if (read)
                esr |= ISS_MSR_DIR;
 
+#undef MRS_MASK
+#undef MRS_VALUE
+#undef MSR_REG_VALUE
+#undef MSR_IMM_VALUE
+#undef MRS_REGISTER
+#undef MRS_Op0_SHIFT
+#undef MRS_Op0_MASK
+#undef MRS_Op1_SHIFT
+#undef MRS_Op1_MASK
+#undef MRS_CRn_SHIFT
+#undef MRS_CRn_MASK
+#undef MRS_CRm_SHIFT
+#undef MRS_CRm_MASK
+#undef MRS_Op2_SHIFT
+#undef MRS_Op2_MASK
+
        return (undef_sys(esr, frame));
 }
 
diff --git a/sys/arm64/include/armreg.h b/sys/arm64/include/armreg.h
index a44cc4343dee..cd770386f852 100644
--- a/sys/arm64/include/armreg.h
+++ b/sys/arm64/include/armreg.h
@@ -36,25 +36,6 @@
 
 #define        INSN_SIZE               4
 
-#define        MRS_MASK                        0xfff00000
-#define        MRS_VALUE                       0xd5300000
-#define        MSR_REG_VALUE                   0xd5100000
-#define        MSR_IMM_VALUE                   0xd5000000
-#define        MRS_SPECIAL(insn)               ((insn) & 0x000fffe0)
-#define        MRS_REGISTER(insn)              ((insn) & 0x0000001f)
-#define         MRS_Op0_SHIFT                  19
-#define         MRS_Op0_MASK                   0x00080000
-#define         MRS_Op1_SHIFT                  16
-#define         MRS_Op1_MASK                   0x00070000
-#define         MRS_CRn_SHIFT                  12
-#define         MRS_CRn_MASK                   0x0000f000
-#define         MRS_CRm_SHIFT                  8
-#define         MRS_CRm_MASK                   0x00000f00
-#define         MRS_Op2_SHIFT                  5
-#define         MRS_Op2_MASK                   0x000000e0
-#define         MRS_Rt_SHIFT                   0
-#define         MRS_Rt_MASK                    0x0000001f
-
 #define        __MRS_REG_ALT_NAME(op0, op1, crn, crm, op2)                     
\
     S##op0##_##op1##_C##crn##_C##crm##_##op2
 #define        _MRS_REG_ALT_NAME(op0, op1, crn, crm, op2)                      
\
diff --git a/sys/arm64/include/undefined.h b/sys/arm64/include/undefined.h
index c23b020e960f..71b2eed22a84 100644
--- a/sys/arm64/include/undefined.h
+++ b/sys/arm64/include/undefined.h
@@ -37,26 +37,6 @@ typedef int (*undef_handler_t)(vm_offset_t, uint32_t, struct 
trapframe *,
     uint32_t);
 typedef bool (*undef_sys_handler_t)(uint64_t, struct trapframe *);
 
-static inline int
-mrs_Op0(uint32_t insn)
-{
-
-       /* op0 is encoded without the top bit in a mrs instruction */
-       return (2 | ((insn & MRS_Op0_MASK) >> MRS_Op0_SHIFT));
-}
-
-#define        MRS_GET(op)                                             \
-static inline int                                              \
-mrs_##op(uint32_t insn)                                                \
-{                                                              \
-                                                               \
-       return ((insn & MRS_##op##_MASK) >> MRS_##op##_SHIFT);  \
-}
-MRS_GET(Op1)
-MRS_GET(CRn)
-MRS_GET(CRm)
-MRS_GET(Op2)
-
 void undef_init(void);
 void install_sys_handler(undef_sys_handler_t);
 void *install_undef_handler(undef_handler_t);

Reply via email to