|  | // Copyright lowRISC contributors. | 
|  | // Licensed under the Apache License, Version 2.0, see LICENSE for details. | 
|  | // SPDX-License-Identifier: Apache-2.0 | 
|  |  | 
|  | ${autogen_banner} | 
|  |  | 
|  | #include "sw/device/lib/testing/autogen/isr_testutils.h" | 
|  |  | 
|  | #include "sw/device/lib/dif/dif_rv_plic.h" | 
|  | % for ip in ips_with_difs: | 
|  | % if ip.irqs: | 
|  | #include "sw/device/lib/dif/dif_${ip.name_snake}.h" | 
|  | % endif | 
|  | % endfor | 
|  | #include "sw/device/lib/testing/test_framework/check.h" | 
|  |  | 
|  | #include "hw/top_earlgrey/sw/autogen/top_earlgrey.h" // Generated. | 
|  |  | 
|  | % for ip in ips_with_difs: | 
|  | % if ip.irqs: | 
|  | void isr_testutils_${ip.name_snake}_isr( | 
|  | plic_isr_ctx_t plic_ctx, | 
|  | ${ip.name_snake}_isr_ctx_t ${ip.name_snake}_ctx, | 
|  | top_earlgrey_plic_peripheral_t *peripheral_serviced, | 
|  | dif_${ip.name_snake}_irq_t *irq_serviced) { | 
|  |  | 
|  | // Claim the IRQ at the PLIC. | 
|  | dif_rv_plic_irq_id_t plic_irq_id; | 
|  | CHECK_DIF_OK(dif_rv_plic_irq_claim( | 
|  | plic_ctx.rv_plic, | 
|  | plic_ctx.hart_id, | 
|  | &plic_irq_id)); | 
|  |  | 
|  | // Get the peripheral the IRQ belongs to. | 
|  | *peripheral_serviced = (top_earlgrey_plic_peripheral_t) | 
|  | top_earlgrey_plic_interrupt_for_peripheral[plic_irq_id]; | 
|  |  | 
|  | // Get the IRQ that was fired from the PLIC IRQ ID. | 
|  | dif_${ip.name_snake}_irq_t irq = (dif_${ip.name_snake}_irq_t)(plic_irq_id - | 
|  | ${ip.name_snake}_ctx.plic_${ip.name_snake}_start_irq_id); | 
|  | *irq_serviced = irq; | 
|  |  | 
|  | // Check if it is supposed to be the only IRQ fired. | 
|  | if (${ip.name_snake}_ctx.is_only_irq) { | 
|  | dif_${ip.name_snake}_irq_state_snapshot_t snapshot; | 
|  | CHECK_DIF_OK(dif_${ip.name_snake}_irq_get_state( | 
|  | ${ip.name_snake}_ctx.${ip.name_snake}, | 
|  | % if ip.name_snake == "rv_timer": | 
|  | plic_ctx.hart_id, | 
|  | % endif | 
|  | &snapshot)); | 
|  | CHECK(snapshot == (dif_${ip.name_snake}_irq_state_snapshot_t)(1 << irq), | 
|  | "Only ${ip.name_snake} IRQ %d expected to fire. Actual IRQ state = %x", | 
|  | irq, snapshot); | 
|  | } | 
|  |  | 
|  | % if ip.name_snake == "adc_ctrl": | 
|  | // TODO(lowRISC/opentitan:#11354): future releases of the ADC Controller HW should hide | 
|  | // the need to also clear the cause CSRs. At which point, this can be removed. | 
|  | CHECK_DIF_OK(dif_${ip.name_snake}_irq_clear_causes( | 
|  | ${ip.name_snake}_ctx.${ip.name_snake}, | 
|  | kDifAdcCtrlIrqCauseAll)); | 
|  | % endif | 
|  |  | 
|  | // Acknowledge the IRQ at the peripheral. | 
|  | CHECK_DIF_OK(dif_${ip.name_snake}_irq_acknowledge( | 
|  | ${ip.name_snake}_ctx.${ip.name_snake}, | 
|  | irq)); | 
|  |  | 
|  | // Complete the IRQ at the PLIC. | 
|  | CHECK_DIF_OK(dif_rv_plic_irq_complete( | 
|  | plic_ctx.rv_plic, | 
|  | plic_ctx.hart_id, | 
|  | plic_irq_id)); | 
|  | } | 
|  |  | 
|  | % endif | 
|  | % endfor |