From: Chinmay Rath <rathc@linux.ibm.com>
To: Glenn Miles <milesg@linux.ibm.com>, qemu-devel@nongnu.org
Cc: qemu-ppc@nongnu.org, clg@redhat.com, npiggin@gmail.com,
harshpb@linux.ibm.com, thuth@redhat.com,
richard.henderson@linaro.org
Subject: Re: [PATCH v5 4/9] target/ppc: Add IBM PPE42 exception model
Date: Thu, 25 Sep 2025 22:19:40 +0530 [thread overview]
Message-ID: <18f62b28-d4ea-4b7c-8e61-375520b6ecb9@linux.ibm.com> (raw)
In-Reply-To: <20250918182731.528944-5-milesg@linux.ibm.com>
On 9/18/25 23:57, Glenn Miles wrote:
> Add support for the IBM PPE42 exception model including
> new exception vectors, exception priorities and setting
> of PPE42 SPRs for determining the cause of an exception.
>
> Signed-off-by: Glenn Miles <milesg@linux.ibm.com>
Reviewed-by: Chinmay Rath <rathc@linux.ibm.com>
> ---
> target/ppc/cpu_init.c | 39 ++++++++-
> target/ppc/excp_helper.c | 163 +++++++++++++++++++++++++++++++++++
> target/ppc/tcg-excp_helper.c | 12 +++
> 3 files changed, 213 insertions(+), 1 deletion(-)
>
> diff --git a/target/ppc/cpu_init.c b/target/ppc/cpu_init.c
> index b42673c6b5..097e3b3818 100644
> --- a/target/ppc/cpu_init.c
> +++ b/target/ppc/cpu_init.c
> @@ -1720,6 +1720,30 @@ static void init_excp_4xx(CPUPPCState *env)
> #endif
> }
>
> +static void init_excp_ppe42(CPUPPCState *env)
> +{
> +#if !defined(CONFIG_USER_ONLY)
> + /* Machine Check vector changed after version 0 */
> + if (((env->spr[SPR_PVR] & 0xf00000ul) >> 20) == 0) {
> + env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000000;
> + } else {
> + env->excp_vectors[POWERPC_EXCP_MCHECK] = 0x00000020;
> + }
> + env->excp_vectors[POWERPC_EXCP_RESET] = 0x00000040;
> + env->excp_vectors[POWERPC_EXCP_DSI] = 0x00000060;
> + env->excp_vectors[POWERPC_EXCP_ISI] = 0x00000080;
> + env->excp_vectors[POWERPC_EXCP_EXTERNAL] = 0x000000A0;
> + env->excp_vectors[POWERPC_EXCP_ALIGN] = 0x000000C0;
> + env->excp_vectors[POWERPC_EXCP_PROGRAM] = 0x000000E0;
> + env->excp_vectors[POWERPC_EXCP_DECR] = 0x00000100;
> + env->excp_vectors[POWERPC_EXCP_FIT] = 0x00000120;
> + env->excp_vectors[POWERPC_EXCP_WDT] = 0x00000140;
> + env->ivpr_mask = 0xFFFFFE00UL;
> + /* Hardware reset vector */
> + env->hreset_vector = 0x00000040UL;
> +#endif
> +}
> +
> static void init_excp_MPC5xx(CPUPPCState *env)
> {
> #if !defined(CONFIG_USER_ONLY)
> @@ -2245,6 +2269,7 @@ static void init_proc_ppe42(CPUPPCState *env)
> {
> register_ppe42_sprs(env);
>
> + init_excp_ppe42(env);
> env->dcache_line_size = 32;
> env->icache_line_size = 32;
> /* Allocate hardware IRQ controller */
> @@ -2278,7 +2303,7 @@ static void ppe42_class_common_init(PowerPCCPUClass *pcc)
> (1ull << MSR_IPE) |
> R_MSR_SIBRCA_MASK;
> pcc->mmu_model = POWERPC_MMU_REAL;
> - pcc->excp_model = POWERPC_EXCP_40x;
> + pcc->excp_model = POWERPC_EXCP_PPE42;
> pcc->bus_model = PPC_FLAGS_INPUT_PPE42;
> pcc->bfd_mach = bfd_mach_ppc_403;
> pcc->flags = POWERPC_FLAG_PPE42 | POWERPC_FLAG_BUS_CLK;
> @@ -7855,6 +7880,18 @@ void ppc_cpu_dump_state(CPUState *cs, FILE *f, int flags)
> * they can be read with "p $ivor0", "p $ivor1", etc.
> */
> break;
> + case POWERPC_EXCP_PPE42:
> + qemu_fprintf(f, "SRR0 " TARGET_FMT_lx " SRR1 " TARGET_FMT_lx "\n",
> + env->spr[SPR_SRR0], env->spr[SPR_SRR1]);
> +
> + qemu_fprintf(f, " TCR " TARGET_FMT_lx " TSR " TARGET_FMT_lx
> + " ISR " TARGET_FMT_lx " EDR " TARGET_FMT_lx "\n",
> + env->spr[SPR_PPE42_TCR], env->spr[SPR_PPE42_TSR],
> + env->spr[SPR_PPE42_ISR], env->spr[SPR_PPE42_EDR]);
> +
> + qemu_fprintf(f, " PIR " TARGET_FMT_lx " IVPR " TARGET_FMT_lx "\n",
> + env->spr[SPR_PPE42_PIR], env->spr[SPR_PPE42_IVPR]);
> + break;
> case POWERPC_EXCP_40x:
> qemu_fprintf(f, " TCR " TARGET_FMT_lx " TSR " TARGET_FMT_lx
> " ESR " TARGET_FMT_lx " DEAR " TARGET_FMT_lx "\n",
> diff --git a/target/ppc/excp_helper.c b/target/ppc/excp_helper.c
> index 1efdc4066e..d8bca19fff 100644
> --- a/target/ppc/excp_helper.c
> +++ b/target/ppc/excp_helper.c
> @@ -949,6 +949,125 @@ static void powerpc_excp_74xx(PowerPCCPU *cpu, int excp)
> powerpc_set_excp_state(cpu, vector, new_msr);
> }
>
> +static void powerpc_excp_ppe42(PowerPCCPU *cpu, int excp)
> +{
> + CPUPPCState *env = &cpu->env;
> + target_ulong msr, new_msr, vector;
> + target_ulong mcs = PPE42_ISR_MCS_INSTRUCTION;
> + bool promote_unmaskable;
> +
> + msr = env->msr;
> +
> + /*
> + * New interrupt handler msr preserves SIBRC and ME unless explicitly
> + * overridden by the exception. All other MSR bits are zeroed out.
> + */
> + new_msr = env->msr & (((target_ulong)1 << MSR_ME) | R_MSR_SIBRC_MASK);
> +
> + /* HV emu assistance interrupt only exists on server arch 2.05 or later */
> + if (excp == POWERPC_EXCP_HV_EMU) {
> + excp = POWERPC_EXCP_PROGRAM;
> + }
> +
> + /*
> + * Unmaskable interrupts (Program, ISI, Alignment and DSI) are promoted to
> + * machine check if MSR_UIE is 0.
> + */
> + promote_unmaskable = !(msr & ((target_ulong)1 << MSR_UIE));
> +
> +
> + switch (excp) {
> + case POWERPC_EXCP_MCHECK: /* Machine check exception */
> + break;
> + case POWERPC_EXCP_DSI: /* Data storage exception */
> + trace_ppc_excp_dsi(env->spr[SPR_PPE42_ISR], env->spr[SPR_PPE42_EDR]);
> + if (promote_unmaskable) {
> + excp = POWERPC_EXCP_MCHECK;
> + mcs = PPE42_ISR_MCS_DSI;
> + }
> + break;
> + case POWERPC_EXCP_ISI: /* Instruction storage exception */
> + trace_ppc_excp_isi(msr, env->nip);
> + if (promote_unmaskable) {
> + excp = POWERPC_EXCP_MCHECK;
> + mcs = PPE42_ISR_MCS_ISI;
> + }
> + break;
> + case POWERPC_EXCP_EXTERNAL: /* External input */
> + break;
> + case POWERPC_EXCP_ALIGN: /* Alignment exception */
> + if (promote_unmaskable) {
> + excp = POWERPC_EXCP_MCHECK;
> + mcs = PPE42_ISR_MCS_ALIGNMENT;
> + }
> + break;
> + case POWERPC_EXCP_PROGRAM: /* Program exception */
> + if (promote_unmaskable) {
> + excp = POWERPC_EXCP_MCHECK;
> + mcs = PPE42_ISR_MCS_PROGRAM;
> + }
> + switch (env->error_code & ~0xF) {
> + case POWERPC_EXCP_INVAL:
> + trace_ppc_excp_inval(env->nip);
> + env->spr[SPR_PPE42_ISR] &= ~((target_ulong)1 << PPE42_ISR_PTR);
> + break;
> + case POWERPC_EXCP_TRAP:
> + env->spr[SPR_PPE42_ISR] |= ((target_ulong)1 << PPE42_ISR_PTR);
> + break;
> + default:
> + /* Should never occur */
> + cpu_abort(env_cpu(env), "Invalid program exception %d. Aborting\n",
> + env->error_code);
> + break;
> + }
> +#ifdef CONFIG_TCG
> + env->spr[SPR_PPE42_EDR] = ppc_ldl_code(env, env->nip);
> +#endif
> + break;
> + case POWERPC_EXCP_DECR: /* Decrementer exception */
> + break;
> + case POWERPC_EXCP_FIT: /* Fixed-interval timer interrupt */
> + trace_ppc_excp_print("FIT");
> + break;
> + case POWERPC_EXCP_WDT: /* Watchdog timer interrupt */
> + trace_ppc_excp_print("WDT");
> + break;
> + case POWERPC_EXCP_RESET: /* System reset exception */
> + /* reset exceptions don't have ME set */
> + new_msr &= ~((target_ulong)1 << MSR_ME);
> + break;
> + default:
> + cpu_abort(env_cpu(env), "Invalid PPE42 exception %d. Aborting\n",
> + excp);
> + break;
> + }
> +
> + env->spr[SPR_SRR0] = env->nip;
> + env->spr[SPR_SRR1] = msr;
> +
> + vector = env->excp_vectors[excp];
> + if (vector == (target_ulong)-1ULL) {
> + cpu_abort(env_cpu(env),
> + "Raised an exception without defined vector %d\n", excp);
> + }
> + vector |= env->spr[SPR_PPE42_IVPR];
> +
> + if (excp == POWERPC_EXCP_MCHECK) {
> + /* Also set the Machine Check Status (MCS) */
> + env->spr[SPR_PPE42_ISR] &= ~R_PPE42_ISR_MCS_MASK;
> + env->spr[SPR_PPE42_ISR] |= (mcs & R_PPE42_ISR_MCS_MASK);
> + env->spr[SPR_PPE42_ISR] &= ~((target_ulong)1 << PPE42_ISR_MFE);
> +
> + /* Machine checks halt execution if MSR_ME is 0 */
> + powerpc_mcheck_checkstop(env);
> +
> + /* machine check exceptions don't have ME set */
> + new_msr &= ~((target_ulong)1 << MSR_ME);
> + }
> +
> + powerpc_set_excp_state(cpu, vector, new_msr);
> +}
> +
> static void powerpc_excp_booke(PowerPCCPU *cpu, int excp)
> {
> CPUPPCState *env = &cpu->env;
> @@ -1589,6 +1708,9 @@ void powerpc_excp(PowerPCCPU *cpu, int excp)
> case POWERPC_EXCP_POWER11:
> powerpc_excp_books(cpu, excp);
> break;
> + case POWERPC_EXCP_PPE42:
> + powerpc_excp_ppe42(cpu, excp);
> + break;
> default:
> g_assert_not_reached();
> }
> @@ -1945,6 +2067,43 @@ static int p9_next_unmasked_interrupt(CPUPPCState *env,
> }
> #endif /* TARGET_PPC64 */
>
> +static int ppe42_next_unmasked_interrupt(CPUPPCState *env)
> +{
> + bool async_deliver;
> +
> + /* External reset */
> + if (env->pending_interrupts & PPC_INTERRUPT_RESET) {
> + return PPC_INTERRUPT_RESET;
> + }
> + /* Machine check exception */
> + if (env->pending_interrupts & PPC_INTERRUPT_MCK) {
> + return PPC_INTERRUPT_MCK;
> + }
> +
> + async_deliver = FIELD_EX64(env->msr, MSR, EE);
> +
> + if (async_deliver != 0) {
> + /* Watchdog timer */
> + if (env->pending_interrupts & PPC_INTERRUPT_WDT) {
> + return PPC_INTERRUPT_WDT;
> + }
> + /* External Interrupt */
> + if (env->pending_interrupts & PPC_INTERRUPT_EXT) {
> + return PPC_INTERRUPT_EXT;
> + }
> + /* Fixed interval timer */
> + if (env->pending_interrupts & PPC_INTERRUPT_FIT) {
> + return PPC_INTERRUPT_FIT;
> + }
> + /* Decrementer exception */
> + if (env->pending_interrupts & PPC_INTERRUPT_DECR) {
> + return PPC_INTERRUPT_DECR;
> + }
> + }
> +
> + return 0;
> +}
> +
> static int ppc_next_unmasked_interrupt(CPUPPCState *env)
> {
> uint32_t pending_interrupts = env->pending_interrupts;
> @@ -1970,6 +2129,10 @@ static int ppc_next_unmasked_interrupt(CPUPPCState *env)
> }
> #endif
>
> + if (env->excp_model == POWERPC_EXCP_PPE42) {
> + return ppe42_next_unmasked_interrupt(env);
> + }
> +
> /* External reset */
> if (pending_interrupts & PPC_INTERRUPT_RESET) {
> return PPC_INTERRUPT_RESET;
> diff --git a/target/ppc/tcg-excp_helper.c b/target/ppc/tcg-excp_helper.c
> index f835be5156..edecfb8572 100644
> --- a/target/ppc/tcg-excp_helper.c
> +++ b/target/ppc/tcg-excp_helper.c
> @@ -229,6 +229,18 @@ void ppc_cpu_do_unaligned_access(CPUState *cs, vaddr vaddr,
> case POWERPC_MMU_BOOKE206:
> env->spr[SPR_BOOKE_DEAR] = vaddr;
> break;
> + case POWERPC_MMU_REAL:
> + if (env->flags & POWERPC_FLAG_PPE42) {
> + env->spr[SPR_PPE42_EDR] = vaddr;
> + if (access_type == MMU_DATA_STORE) {
> + env->spr[SPR_PPE42_ISR] |= PPE42_ISR_ST;
> + } else {
> + env->spr[SPR_PPE42_ISR] &= ~PPE42_ISR_ST;
> + }
> + } else {
> + env->spr[SPR_DAR] = vaddr;
> + }
> + break;
> default:
> env->spr[SPR_DAR] = vaddr;
> break;
next prev parent reply other threads:[~2025-09-25 16:51 UTC|newest]
Thread overview: 22+ messages / expand[flat|nested] mbox.gz Atom feed top
2025-09-18 18:27 [PATCH v5 0/9] Add IBM PPE42 CPU support Glenn Miles
2025-09-18 18:27 ` [PATCH v5 1/9] target/ppc: IBM PPE42 general regs and flags Glenn Miles
2025-09-24 12:28 ` Chinmay Rath
2025-09-18 18:27 ` [PATCH v5 2/9] target/ppc: Add IBM PPE42 family of processors Glenn Miles
2025-09-24 12:32 ` Chinmay Rath
2025-09-24 14:52 ` Miles Glenn
2025-09-24 15:06 ` Miles Glenn
2025-09-25 4:57 ` Harsh Prateek Bora
2025-09-25 15:29 ` Miles Glenn
2025-09-25 15:54 ` Harsh Prateek Bora
2025-09-18 18:27 ` [PATCH v5 3/9] target/ppc: IBM PPE42 exception flags and regs Glenn Miles
2025-09-25 16:25 ` Chinmay Rath
2025-09-18 18:27 ` [PATCH v5 4/9] target/ppc: Add IBM PPE42 exception model Glenn Miles
2025-09-25 16:49 ` Chinmay Rath [this message]
2025-09-18 18:27 ` [PATCH v5 5/9] target/ppc: Support for IBM PPE42 MMU Glenn Miles
2025-09-25 18:57 ` Chinmay Rath
2025-09-18 18:27 ` [PATCH v5 6/9] target/ppc: Add IBM PPE42 special instructions Glenn Miles
2025-09-22 10:18 ` Chinmay Rath
2025-09-18 18:27 ` [PATCH v5 7/9] hw/ppc: Support for an IBM PPE42 CPU decrementer Glenn Miles
2025-09-18 18:27 ` [PATCH v5 8/9] hw/ppc: Add a test machine for the IBM PPE42 CPU Glenn Miles
2025-09-18 18:27 ` [PATCH v5 9/9] tests/functional: Add test for IBM PPE42 instructions Glenn Miles
2025-09-19 8:29 ` Cédric Le Goater
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=18f62b28-d4ea-4b7c-8e61-375520b6ecb9@linux.ibm.com \
--to=rathc@linux.ibm.com \
--cc=clg@redhat.com \
--cc=harshpb@linux.ibm.com \
--cc=milesg@linux.ibm.com \
--cc=npiggin@gmail.com \
--cc=qemu-devel@nongnu.org \
--cc=qemu-ppc@nongnu.org \
--cc=richard.henderson@linaro.org \
--cc=thuth@redhat.com \
/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).