From 8d449929e52b3c64266d5faf960ec97c01b2bba3 Mon Sep 17 00:00:00 2001 From: Sona Mathew Date: Mon, 1 Jan 2024 21:00:44 -0600 Subject: [PATCH] refactor(gicv3): introducing is_valid_interrupt, a new helper utility In gicv3_main.c the function is_sgi_ppi() returns true when its sgi/ppi or false when the interrupt number matches an spi interrupt. Introducing a new API is_valid_interrupt() which validates if an interrupt number matches SGI/PPI or SPI as a valid interrupt, any other interrupt number is considered invalid and panics. Change-Id: Idce8f5432a94c8d300b9408cf5b2502c60e13318 Signed-off-by: Sona Mathew --- drivers/arm/gic/v3/gicv3_main.c | 75 +++++++++++++++++++++------------ 1 file changed, 48 insertions(+), 27 deletions(-) diff --git a/drivers/arm/gic/v3/gicv3_main.c b/drivers/arm/gic/v3/gicv3_main.c index 3c995171f..3190f6615 100644 --- a/drivers/arm/gic/v3/gicv3_main.c +++ b/drivers/arm/gic/v3/gicv3_main.c @@ -1,5 +1,5 @@ /* - * Copyright (c) 2015-2023, Arm Limited and Contributors. All rights reserved. + * Copyright (c) 2015-2024, Arm Limited and Contributors. All rights reserved. * Copyright (c) 2023, NVIDIA Corporation. All rights reserved. * * SPDX-License-Identifier: BSD-3-Clause @@ -34,8 +34,8 @@ static spinlock_t gic_lock; #pragma weak gicv3_rdistif_off #pragma weak gicv3_rdistif_on -/* Check interrupt ID for SGI/(E)PPI and (E)SPIs */ -static bool is_sgi_ppi(unsigned int id); +/* Check for valid SGI/PPI or SPI interrupt ID */ +static bool is_valid_interrupt(unsigned int id); /* * Helper macros to save and restore GICR and GICD registers @@ -447,8 +447,12 @@ unsigned int gicv3_get_interrupt_group(unsigned int id, unsigned int proc_num) return INTR_GROUP1NS; } + if (!is_valid_interrupt(id)) { + panic(); + } + /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* SGIs: 0-15, PPIs: 16-31, EPPIs: 1056-1119 */ assert(gicv3_driver_data->rdistif_base_addrs != NULL); gicr_base = gicv3_driver_data->rdistif_base_addrs[proc_num]; @@ -942,8 +946,11 @@ unsigned int gicv3_get_interrupt_active(unsigned int id, unsigned int proc_num) assert(proc_num < gicv3_driver_data->rdistif_num); assert(gicv3_driver_data->rdistif_base_addrs != NULL); + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ return gicr_get_isactiver( gicv3_driver_data->rdistif_base_addrs[proc_num], id); @@ -973,9 +980,11 @@ void gicv3_enable_interrupt(unsigned int id, unsigned int proc_num) * interrupt trigger are observed before enabling interrupt. */ dsbishst(); - + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_set_isenabler( gicv3_driver_data->rdistif_base_addrs[proc_num], id); @@ -1004,9 +1013,11 @@ void gicv3_disable_interrupt(unsigned int id, unsigned int proc_num) * Disable interrupt, and ensure that any shared variable updates * depending on out of band interrupt trigger are observed afterwards. */ - + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_set_icenabler( gicv3_driver_data->rdistif_base_addrs[proc_num], id); @@ -1041,8 +1052,11 @@ void gicv3_set_interrupt_priority(unsigned int id, unsigned int proc_num, assert(proc_num < gicv3_driver_data->rdistif_num); assert(gicv3_driver_data->rdistif_base_addrs != NULL); + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_base = gicv3_driver_data->rdistif_base_addrs[proc_num]; gicr_set_ipriorityr(gicr_base, id, priority); @@ -1088,8 +1102,11 @@ void gicv3_set_interrupt_group(unsigned int id, unsigned int proc_num, break; } + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_base = gicv3_driver_data->rdistif_base_addrs[proc_num]; @@ -1228,12 +1245,14 @@ void gicv3_clear_interrupt_pending(unsigned int id, unsigned int proc_num) * Clear pending interrupt, and ensure that any shared variable updates * depending on out of band interrupt trigger are observed afterwards. */ - + if (!is_valid_interrupt(id)) { + panic(); + } /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_set_icpendr( - gicv3_driver_data->rdistif_base_addrs[proc_num], id); + gicv3_driver_data->rdistif_base_addrs[proc_num], id); } else { /* For SPIs: 32-1019 and ESPIs: 4096-5119 */ gicd_base = gicv3_get_multichip_base(id, gicv3_driver_data->gicd_base); @@ -1263,8 +1282,12 @@ void gicv3_set_interrupt_pending(unsigned int id, unsigned int proc_num) */ dsbishst(); + if (!is_valid_interrupt(id)) { + panic(); + } + /* Check interrupt ID */ - if (is_sgi_ppi(id)) { + if (IS_SGI_PPI(id)) { /* For SGIs: 0-15, PPIs: 16-31 and EPPIs: 1056-1119 */ gicr_set_ispendr( gicv3_driver_data->rdistif_base_addrs[proc_num], id); @@ -1371,21 +1394,19 @@ int gicv3_rdistif_probe(const uintptr_t gicr_frame) } /****************************************************************************** - * This function checks the interrupt ID and returns true for SGIs and (E)PPIs - * and false for (E)SPIs IDs. + * This function checks the interrupt ID and returns true for SGIs, (E)PPIs + * and (E)SPIs IDs. Any interrupt ID outside the range is invalid and returns + * false. *****************************************************************************/ -static bool is_sgi_ppi(unsigned int id) +static bool is_valid_interrupt(unsigned int id) { - /* SGIs: 0-15, PPIs: 16-31, EPPIs: 1056-1119 */ - if (IS_SGI_PPI(id)) { + /* Valid interrupts: + * SGIs: 0-15, PPIs: 16-31, EPPIs: 1056-1119 + * SPIs: 32-1019, ESPIs: 4096-5119 + */ + if ((IS_SGI_PPI(id)) || (IS_SPI(id))) { return true; } - /* SPIs: 32-1019, ESPIs: 4096-5119 */ - if (IS_SPI(id)) { - return false; - } - - assert(false); - panic(); + return false; }