From: Fabiano Rosas <farosas@linux.ibm.com>
To: qemu-devel@nongnu.org
Cc: danielhb413@gmail.com, mark.cave-ayland@ilande.co.uk,
qemu-ppc@nongnu.org, clg@kaod.org, openbios@openbios.org,
david@gibson.dropbear.id.au
Subject: [RFC PATCH 1/2] ppc: Add support for MPC7450 software TLB miss interrupts
Date: Fri, 19 Nov 2021 10:44:30 -0300 [thread overview]
Message-ID: <20211119134431.406753-2-farosas@linux.ibm.com> (raw)
In-Reply-To: <20211119134431.406753-1-farosas@linux.ibm.com>
The MPC7450 Family has a software TLB search feature that defines
three interrupts at 0x1000, 0x1100 and 0x1200. These are not currently
implemented in openbios.
Due to an outstanding bug in QEMU[1], the feature is always enabled
when emulating the 7450, requiring any software that runs in those
cpus to implement the interrupt handlers.
Fortunately, the 7450 User Manual provides sample code[2] for the TLB
miss handlers so adding support for the feature in openbios is
somewhat easy.
This patch implements the software TLB search so that we can get the
MPC7450 working again on the emulator.
1- https://gitlab.com/qemu-project/qemu/-/issues/86
2- https://www.nxp.com/docs/en/reference-manual/MPC7450UM.pdf
(5.5.5.2.2 - Code for Example Exception Handlers)
Signed-off-by: Fabiano Rosas <farosas@linux.ibm.com>
---
arch/ppc/qemu/start.S | 236 +++++++++++++++++++++++++++++++++++++++++-
1 file changed, 233 insertions(+), 3 deletions(-)
diff --git a/arch/ppc/qemu/start.S b/arch/ppc/qemu/start.S
index c679230..a09a210 100644
--- a/arch/ppc/qemu/start.S
+++ b/arch/ppc/qemu/start.S
@@ -25,6 +25,10 @@
#define ILLEGAL_VECTOR( v ) .org __vectors + v ; vector__##v: bl trap_error ;
#define VECTOR( v, dummystr ) .org __vectors + v ; vector__##v
+#define SPR_TLBMISS 980
+#define SPR_PTEHI 981
+#define SPR_PTELO 982
+
#ifdef CONFIG_PPC_64BITSUPPORT
/* We're trying to use the same code for the ppc32 and ppc64 handlers here.
@@ -164,6 +168,76 @@
EXCEPTION_EPILOGUE_TEMPLATE
.endm
+.macro ITLB_SEARCH
+ TLB_SEARCH
+.endm
+
+.macro DTLB_SEARCH
+ TLB_SEARCH 1
+.endm
+
+.macro TLB_SEARCH data
+ mfspr r0,SPR_TLBMISS /* EA of access that missed */
+ rlwinm r0,r0,20,16,31 /* mask out lower 16 bits of EA */
+ mfspr r1,SPR_PTEHI /* PTEHI[1:24] has the VSID */
+ rlwinm r1,r1,25,8,31 /* mask out upper 23 bits of VSID */
+
+ xor r1,r0,r1 /* primary hash */
+ mfsdr1 r3
+ rlwinm r0,r3,10,13,31 /* align HTMEXT and HTABMASK fields */
+ ori r0,r0,0x3ff /* mask out HTMEXT and HTABMASK */
+ and r1,r0,r1
+ rlwinm r0,r3,26,13,21
+ or r1,r0,r1
+
+/* 32-bit PTEG address generation into r2 */
+ andis. r2,r3,0xfe00
+ rlwimi r2,r1,6,7,25
+
+ xor r1,r1,r1
+ addi r1,r1,8
+ mfspr r3,SPR_PTEHI
+ addi r2,r2,-8
+
+1:
+ mtctr r1
+2:
+ lwzu r1,8(r2) /* get next pte */
+ cmp 0,r1,r3
+ bdnzf eq,2b
+ beq 1f /* found */
+
+ andi. r1,r3,0x0040 /* see if we have done second hash */
+.ifnb data
+ bne do_dsi
+.else
+ bne do_isi
+.endif
+ mfspr r0,SPR_TLBMISS /* EA of access that missed */
+ rlwinm r0,r0,20,16,3 /* mask out lower 16 bits of EA */
+ mfspr r1,SPR_PTEHI /* PTEHI[1:24] has the VSID */
+ rlwinm r1,r1,25,8,31 /* mask out uppder 23 bits of VSID */
+
+ xor r1,r0,r1 /* primary hash */
+ mfsdr1 r3
+ rlwinm r0,r3,10,13,31 /* align HTMEXT and HTABMASK fields */
+ ori r0,r0,0x3ff /* mask out HTMEXT and HTABMASK */
+ and r1,r0,r1
+ rlwinm r0,r3,26,13,21
+ or r1,r0,r1
+
+/* 32-bit PTEG address generation into r2 */
+ andis. r2,r3,0xfe00
+ rlwimi r2,r1,6,7,25
+
+ ori r3,r3,0x0040
+ addi r1,r0,8
+ addi r2,r2,-8
+ b 1b
+
+1:
+.endm
+
#undef ULONG_SIZE
#undef stl
#undef ll
@@ -329,9 +403,16 @@ ILLEGAL_VECTOR( 0xd00 )
ILLEGAL_VECTOR( 0xe00 )
ILLEGAL_VECTOR( 0xf00 )
ILLEGAL_VECTOR( 0xf20 )
-ILLEGAL_VECTOR( 0x1000 )
-ILLEGAL_VECTOR( 0x1100 )
-ILLEGAL_VECTOR( 0x1200 )
+
+VECTOR( 0x1000, "IFTLB" ):
+ b insn_tlb_miss
+
+VECTOR( 0x1100, "DLTLB" ):
+ b data_load_tlb_miss
+
+VECTOR( 0x1200, "DSTLB" ):
+ b data_store_tlb_miss
+
ILLEGAL_VECTOR( 0x1300 )
ILLEGAL_VECTOR( 0x1400 )
ILLEGAL_VECTOR( 0x1500 )
@@ -373,6 +454,155 @@ real_isi:
exception_return:
EXCEPTION_EPILOGUE
+/*
+ * Instruction TLB miss
+ * Entry:
+ * srr0 -> address of instruction that missed
+ * srr1 -> 16:31 = saved MSR
+ * TLBMISS -> ea that missed
+ * PTEHI -> upper 32-bits of pte value
+ * PTELO -> lower 32-bits of pte value
+ */
+insn_tlb_miss:
+ EXCEPTION_PREAMBLE
+ mtsprg3 r1 /* save ABI frame, we might call into C later */
+
+ ITLB_SEARCH
+
+/* pte found*/
+ lwz r1,4(r2) /* load tlb entry lower-word */
+ andi. r3,r1,8 /* check G-bit */
+ bne isi_prot /* if guarded, take an ISI */
+
+ ori r1,r1,0x100 /* set reference bit */
+ mtspr SPR_PTELO,r1 /* put rpn into PTELO */
+ mfspr r0,SPR_TLBMISS
+ tlbli r0 /* load the itlb */
+ srwi r1,r1,8 /* get byte 7 of pte */
+ stb r1,6(r2) /* update page table */
+
+ mfsprg3 r1 /* restore C ABI stack */
+ b exception_return
+
+/* Guarded memory protection violation: synthesize an ISI exception */
+isi_prot:
+ mfsrr1 r3
+ andi. r2,r3,0xffff /* clean upper SRR1 */
+ addis r2,r2,0x0800 /* protection violation flag */
+ b 1f
+
+do_isi:
+ mfsrr1 r3
+ andi. r2,r3,0xffff
+ addis r2,r2,0x4000 /* pte not found flag */
+ mtsrr1 r2
+ mtcrf 0x80,r3
+1:
+ mfsprg3 r1 /* restore C ABI stack */
+ LOAD_REG_FUNC(r3, isi_exception)
+ mtctr r3
+ bctrl
+ b exception_return
+
+/*
+ * Data Load TLB miss
+ * Entry:
+ * srr0 -> address of instruction that caused data tlb miss
+ * srr1 -> 16:31 = saved MSR
+ * TLBMISS -> ea that missed
+ * PTEHI -> upper 32-bits of pte value
+ * PTELO -> lower 32-bits of pte value
+ */
+data_load_tlb_miss:
+ EXCEPTION_PREAMBLE
+ mtsprg3 r1 /* save ABI frame, we might call into C later */
+
+ DTLB_SEARCH
+
+/* pte found */
+ lwz r1,4(r2) /* load tlb entry lower-word */
+ ori r1,r1,0x100 /* set reference bit */
+ mtspr SPR_PTELO,r1 /* put RPN into PTELO */
+ mfspr r0,SPR_TLBMISS
+ tlbld r0 /* load the dtlb */
+ srwi r1,r1,8 /* get byte 7 of pte */
+ stb r1,6(r2) /* update page table */
+
+ mfsprg3 r1 /* restore C ABI stack */
+ b exception_return
+
+/*
+ * Data Store TLB miss
+ * Entry:
+ * srr0 -> address of instruction that caused data tlb miss
+ * srr1 -> 16:31 = saved MSR
+ * TLBMISS -> ea that missed
+ * PTEHI -> upper 32-bits of pte value
+ * PTELO -> lower 32-bits of pte value
+ */
+data_store_tlb_miss:
+ EXCEPTION_PREAMBLE
+ mtsprg3 r1 /* save ABI frame, we might call into C later */
+
+ DTLB_SEARCH
+
+/* pte found */
+ lwz r1,4(r2) /* load tlb entry lower-word */
+ andi. r3,r1,0x80 /* check the C-bit */
+ beq data_store_prot_check /* if (C==0) go check protection modes */
+3:
+ ori r1,r1,0x180 /* set reference and change bit */
+ mtspr SPR_PTELO,r1 /* put RPN into PTELO */
+ mfspr r0,SPR_TLBMISS
+ xori r0,r0,0x01 /* toggle LRU bit */
+ tlbld r0 /* load the dtlb */
+ sth r1,6(r2) /* update page table */
+
+ mfsprg3 r1 /* restore C ABI stack */
+ b exception_return
+
+data_store_prot_check:
+ rlwinm. r3,r1,30,0,1 /* test PP */
+ bge- 1f /* if (PP==00 or PP==01) go check KEY bit */
+ andi. r3,r1,1 /* test PP[0] */
+ beq+ 3b /* return if PP[0]==0 */
+ b dsi_prot
+1:
+ mfsrr1 r3
+ andis. r3,r3,0x0008 /* test the KEY bit (SRR1-bit 12) */
+ ble 3b
+
+dsi_prot:
+ mfsrr1 r3
+ rlwinm r1,r3,9,6,6 /* copy load/store bit over */
+ addis r1,r1,0x0800 /* protection violation flag */
+ b 2f
+
+do_dsi:
+ mfsrr1 r3
+ rlwinm r1,r3,9,6,6 /* copy load/store bit over */
+ addis r1,r1,0x4000 /* pte not found */
+
+2:
+ andis. r2,r3,0x0200 /* save the Altivec Avail. bit in r2 */
+ andi. r3,r3,0xffff /* clear upper SRR1 */
+ or r2,r2,r3
+ mtsrr1 r2
+ mtdsisr r1
+ mfspr r1,SPR_TLBMISS
+ rlwinm r1,r1,0,0,30 /* Clear the LRU bit */
+ rlwinm. r2,r2,0,31,31 /* test LE bit */
+ beq 3f
+ xori r1,r1,0x07
+3:
+ mtdar r1
+ mtcrf 0x80,r3
+ mfsprg3 r1 /* restore C ABI stack */
+ LOAD_REG_FUNC(r3, dsi_exception)
+ mtctr r3
+ bctrl
+ b exception_return
+
GLOBL(__vectors_end):
/************************************************************************/
--
2.29.2
next prev parent reply other threads:[~2021-11-19 13:50 UTC|newest]
Thread overview: 27+ messages / expand[flat|nested] mbox.gz Atom feed top
2021-11-19 13:44 [RFC PATCH 0/2] QEMU/openbios: PPC Software TLB support in the G4 family Fabiano Rosas
2021-11-19 13:44 ` Fabiano Rosas [this message]
2021-11-19 13:44 ` [RFC PATCH 2/2] ppc: Add PVRs for the MPC7450 family Fabiano Rosas
2021-11-24 22:00 ` [RFC PATCH 0/2] QEMU/openbios: PPC Software TLB support in the G4 family Fabiano Rosas
2021-11-25 0:45 ` BALATON Zoltan
2021-11-25 8:11 ` Cédric Le Goater
2021-11-25 14:03 ` BALATON Zoltan
2021-11-25 14:28 ` Cédric Le Goater
2021-11-25 9:38 ` [OpenBIOS] " Segher Boessenkool
2021-11-26 8:34 ` Cédric Le Goater
2021-11-26 10:37 ` Segher Boessenkool
2021-11-26 12:13 ` Fabiano Rosas
2021-11-26 12:45 ` Cédric Le Goater
2021-11-26 13:02 ` Fabiano Rosas
2021-11-26 12:43 ` Fabiano Rosas
2021-11-26 14:46 ` BALATON Zoltan
2021-11-26 8:01 ` Mark Cave-Ayland
2021-11-26 8:40 ` Cédric Le Goater
2021-11-26 8:56 ` Mark Cave-Ayland
2021-11-26 12:31 ` Fabiano Rosas
2021-11-26 13:53 ` Cédric Le Goater
2021-11-26 15:02 ` BALATON Zoltan
2021-11-29 15:28 ` Fabiano Rosas
2022-01-07 8:19 ` Cédric Le Goater
2022-01-07 13:19 ` Fabiano Rosas
2022-01-07 13:51 ` Cédric Le Goater
2022-01-07 23:19 ` [OpenBIOS] " Mark Cave-Ayland
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20211119134431.406753-2-farosas@linux.ibm.com \
--to=farosas@linux.ibm.com \
--cc=clg@kaod.org \
--cc=danielhb413@gmail.com \
--cc=david@gibson.dropbear.id.au \
--cc=mark.cave-ayland@ilande.co.uk \
--cc=openbios@openbios.org \
--cc=qemu-devel@nongnu.org \
--cc=qemu-ppc@nongnu.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).