From 6ae90033829705eea8aa3cfbcd2afdc8fb992082 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 11:25:43 +0800 Subject: [PATCH 01/10] drivers: intc_gicv3: enable dma-noncoherent support GIC redistributor on Some platform are connected to a non-coherent downstream interconnect, it need to use Non-cahable and Non-shareable access atttributes to access external memory. And also flush the data cache after CPU update related memory. Signed-off-by: Jiafei Pan --- drivers/interrupt_controller/Kconfig.gic | 9 +++++ drivers/interrupt_controller/intc_gicv3.c | 40 ++++++++++++++++++++--- 2 files changed, 45 insertions(+), 4 deletions(-) diff --git a/drivers/interrupt_controller/Kconfig.gic b/drivers/interrupt_controller/Kconfig.gic index b482bf3336b1..c3175c74ff2f 100644 --- a/drivers/interrupt_controller/Kconfig.gic +++ b/drivers/interrupt_controller/Kconfig.gic @@ -73,4 +73,13 @@ config GIC_SAFE_CONFIG crash the OS has already been started. With this enabled, it will bypass GIC distributor configuration if it has been configured by other OS. +config GIC_V3_RDIST_DMA_NONCOHERENT + bool "GIC redistributor is DMA noncoherent" + depends on GIC_V3 + default n + help + GIC redistributor on Some platform are connected to a non-coherent + downstream interconnect, it need to use Non-cahable and Non-shareable + access atttributes to access external memory. + endif # CPU_CORTEX diff --git a/drivers/interrupt_controller/intc_gicv3.c b/drivers/interrupt_controller/intc_gicv3.c index cc22eaedb17f..afc5c6d4377b 100644 --- a/drivers/interrupt_controller/intc_gicv3.c +++ b/drivers/interrupt_controller/intc_gicv3.c @@ -1,11 +1,12 @@ /* * Copyright 2020 Broadcom - * Copyright 2024 NXP + * Copyright 2024-2025 NXP * Copyright 2025 Arm Limited and/or its affiliates * * SPDX-License-Identifier: Apache-2.0 */ +#include #include #include #include @@ -111,7 +112,11 @@ static void arm_gic_lpi_setup(unsigned int intid, bool enable) *cfg &= ~BIT(0); } +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(cfg, sizeof(*cfg)); +#else barrier_dsync_fence_full(); +#endif its_rdist_invall(); } @@ -123,7 +128,11 @@ static void arm_gic_lpi_set_priority(unsigned int intid, unsigned int prio) *cfg &= 0xfc; *cfg |= prio & 0xfc; +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(cfg, sizeof(*cfg)); +#else barrier_dsync_fence_full(); +#endif its_rdist_invall(); } @@ -406,7 +415,7 @@ static void gicv3_rdist_setup_lpis(mem_addr_t rdist) unsigned int lpi_id_bits = MIN(GICD_TYPER_IDBITS(sys_read32(GICD_TYPER)), ITS_MAX_LPI_NRBITS); uintptr_t lpi_pend_table; - uint64_t reg; + uint64_t reg, tmp; uint32_t ctlr; /* If not, alloc a common prop table for all redistributors */ @@ -418,6 +427,11 @@ static void gicv3_rdist_setup_lpis(mem_addr_t rdist) lpi_pend_table = (uintptr_t)k_aligned_alloc(64 * 1024, LPI_PENDBASE_SZ(lpi_id_bits)); memset((void *)lpi_pend_table, 0, LPI_PENDBASE_SZ(lpi_id_bits)); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range((void *)lpi_prop_table, LPI_PROPBASE_SZ(lpi_id_bits)); + arch_dcache_flush_and_invd_range((void *)lpi_pend_table, LPI_PENDBASE_SZ(lpi_id_bits)); +#endif + ctlr = sys_read32(rdist + GICR_CTLR); ctlr &= ~GICR_CTLR_ENABLE_LPIS; sys_write32(ctlr, rdist + GICR_CTLR); @@ -429,7 +443,16 @@ static void gicv3_rdist_setup_lpis(mem_addr_t rdist) (GIC_BASER_CACHE_INNERLIKE << GITR_PROPBASER_OUTER_CACHE_SHIFT) | ((lpi_id_bits - 1) & GITR_PROPBASER_ID_BITS_MASK); sys_write64(reg, rdist + GICR_PROPBASER); - /* TOFIX: check SHAREABILITY validity */ + /* Check SHAREABILITY validity */ + tmp = sys_read64(rdist + GICR_PROPBASER); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + tmp &= ~MASK(GITR_PROPBASER_SHAREABILITY); +#endif + if (!(tmp & MASK(GITR_PROPBASER_SHAREABILITY))) { + reg &= ~(MASK(GITR_PROPBASER_SHAREABILITY) | MASK(GITR_PROPBASER_INNER_CACHE)); + reg |= GIC_BASER_CACHE_NCACHEABLE << GITR_PROPBASER_INNER_CACHE_SHIFT; + sys_write64(reg, rdist + GICR_PROPBASER); + } /* PENDBASE */ reg = (GIC_BASER_SHARE_INNER << GITR_PENDBASER_SHAREABILITY_SHIFT) | @@ -437,7 +460,16 @@ static void gicv3_rdist_setup_lpis(mem_addr_t rdist) (lpi_pend_table & (GITR_PENDBASER_ADDR_MASK << GITR_PENDBASER_ADDR_SHIFT)) | (GIC_BASER_CACHE_INNERLIKE << GITR_PENDBASER_OUTER_CACHE_SHIFT) | GITR_PENDBASER_PTZ; sys_write64(reg, rdist + GICR_PENDBASER); - /* TOFIX: check SHAREABILITY validity */ + /* Check SHAREABILITY validity */ + tmp = sys_read64(rdist + GICR_PENDBASER); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + tmp &= ~MASK(GITR_PENDBASER_SHAREABILITY); +#endif + if (!(tmp & MASK(GITR_PENDBASER_SHAREABILITY))) { + reg &= ~(MASK(GITR_PENDBASER_SHAREABILITY) | MASK(GITR_PENDBASER_INNER_CACHE)); + reg |= GIC_BASER_CACHE_NCACHEABLE << GITR_PENDBASER_INNER_CACHE_SHIFT; + sys_write64(reg, rdist + GICR_PENDBASER); + } ctlr = sys_read32(rdist + GICR_CTLR); ctlr |= GICR_CTLR_ENABLE_LPIS; From a7979a788b30779a21a2c7702b131d73fdf38f31 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Thu, 12 Jun 2025 18:44:21 +0800 Subject: [PATCH 02/10] drivers: gicv3_its: enable dma noncoherent support Add DMA noncoherent support on GICv3 ITS driver. Signed-off-by: Jiafei Pan --- drivers/interrupt_controller/intc_gicv3_its.c | 50 +++++++++++++++++-- 1 file changed, 45 insertions(+), 5 deletions(-) diff --git a/drivers/interrupt_controller/intc_gicv3_its.c b/drivers/interrupt_controller/intc_gicv3_its.c index 6316e686c755..d3864bbab32a 100644 --- a/drivers/interrupt_controller/intc_gicv3_its.c +++ b/drivers/interrupt_controller/intc_gicv3_its.c @@ -1,5 +1,6 @@ /* * Copyright 2021 BayLibre, SAS + * Copyright 2025 NXP * * SPDX-License-Identifier: Apache-2.0 */ @@ -7,6 +8,7 @@ #include LOG_MODULE_REGISTER(intc_gicv3_its, LOG_LEVEL_ERR); +#include #include #include #include @@ -39,6 +41,9 @@ struct its_cmd_block { #define ITS_CMD_QUEUE_SIZE SIZE_64K #define ITS_CMD_QUEUE_NR_ENTRIES (ITS_CMD_QUEUE_SIZE / sizeof(struct its_cmd_block)) +/* The level 1 entry size is a 64bit pointer */ +#define GITS_LVL1_ENTRY_SIZE (8UL) + struct gicv3_its_data { mm_reg_t base; struct its_cmd_block *cmd_base; @@ -190,8 +195,7 @@ static int its_alloc_tables(struct gicv3_its_data *data) lvl2_width = fls_z(page_size / entry_size) - 1; device_ids -= lvl2_width + 1; - /* The level 1 entry size is a 64bit pointer */ - entry_size = sizeof(uint64_t); + entry_size = GITS_LVL1_ENTRY_SIZE; indirect = true; } @@ -229,13 +233,22 @@ static int its_alloc_tables(struct gicv3_its_data *data) } reg |= MASK_SET(page_cnt - 1, GITS_BASER_SIZE); - reg |= MASK_SET(GIC_BASER_SHARE_INNER, GITS_BASER_SHAREABILITY); reg |= MASK_SET((uintptr_t)alloc_addr >> GITS_BASER_ADDR_SHIFT, GITS_BASER_ADDR); reg |= MASK_SET(GIC_BASER_CACHE_INNERLIKE, GITS_BASER_OUTER_CACHE); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + reg |= MASK_SET(GIC_BASER_SHARE_NO, GITS_BASER_SHAREABILITY); + reg |= MASK_SET(GIC_BASER_CACHE_NCACHEABLE, GITS_BASER_INNER_CACHE); +#else + reg |= MASK_SET(GIC_BASER_SHARE_INNER, GITS_BASER_SHAREABILITY); reg |= MASK_SET(GIC_BASER_CACHE_RAWAWB, GITS_BASER_INNER_CACHE); +#endif reg |= MASK_SET(indirect ? 1 : 0, GITS_BASER_INDIRECT); reg |= MASK_SET(1, GITS_BASER_VALID); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(alloc_addr, page_size * page_cnt); +#endif + sys_write64(reg, data->base + GITS_BASER(i)); /* TOFIX: check page size & SHAREABILITY validity after write */ @@ -300,6 +313,10 @@ static int its_post_command(struct gicv3_its_data *data, struct its_cmd_block *c uint64_t wr_idx, rd_idx, idx; unsigned int count = 1000000; /* 1s! */ +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(cmd, sizeof(*cmd)); +#endif + wr_idx = (data->cmd_write - data->cmd_base) * sizeof(*cmd); rd_idx = sys_read32(data->base + GITS_CREADR); @@ -426,7 +443,6 @@ static int its_send_invall_cmd(struct gicv3_its_data *data, uint32_t icid) static int gicv3_its_send_int(const struct device *dev, uint32_t device_id, uint32_t event_id) { struct gicv3_its_data *data = dev->data; - /* TOFIX check device_id & event_id bounds */ return its_send_int_cmd(data, device_id, event_id); @@ -436,7 +452,7 @@ static void its_setup_cmd_queue(const struct device *dev) { const struct gicv3_its_config *cfg = dev->config; struct gicv3_its_data *data = dev->data; - uint64_t reg = 0; + uint64_t reg = 0, tmp; /* Zero out cmd table */ memset(cfg->cmd_queue, 0, cfg->cmd_queue_size); @@ -450,6 +466,17 @@ static void its_setup_cmd_queue(const struct device *dev) sys_write64(reg, data->base + GITS_CBASER); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + reg &= ~(MASK(GITS_BASER_SHAREABILITY)); +#endif + /* Check whether hardware supports sharable */ + tmp = sys_read64(data->base + GITS_CBASER); + if (!(tmp & MASK(GITS_BASER_SHAREABILITY))) { + reg &= ~(MASK(GITS_BASER_SHAREABILITY) | MASK(GITS_BASER_INNER_CACHE)); + reg |= MASK_SET(GIC_BASER_CACHE_NCACHEABLE, GITS_CBASER_INNER_CACHE); + sys_write64(reg, data->base + GITS_CBASER); + } + data->cmd_base = (struct its_cmd_block *)cfg->cmd_queue; data->cmd_write = data->cmd_base; @@ -529,9 +556,18 @@ static int gicv3_its_init_device_id(const struct device *dev, uint32_t device_id memset(alloc_addr, 0, data->indirect_dev_page_size); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(alloc_addr, data->indirect_dev_page_size); +#endif + data->indirect_dev_lvl1_table[offset] = (uintptr_t)alloc_addr | MASK_SET(1, GITS_BASER_VALID); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(data->indirect_dev_lvl1_table + offset, + GITS_LVL1_ENTRY_SIZE); +#endif + barrier_dsync_fence_full(); } } @@ -547,6 +583,10 @@ static int gicv3_its_init_device_id(const struct device *dev, uint32_t device_id if (!itt) { return -ENOMEM; } + memset(itt, 0, alloc_size); +#ifdef CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT + arch_dcache_flush_and_invd_range(itt, alloc_size); +#endif /* size is log2(ites) - 1, equivalent to (fls(ites) - 1) - 1 */ ret = its_send_mapd_cmd(data, device_id, fls_z(nr_ites) - 2, (uintptr_t)itt, true); From 54423749b49ff173d651f9ed91f41350957f0325 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 21:22:27 +0800 Subject: [PATCH 03/10] drivers: intc_gicv3_its: fix incorrect RDbase when PE number is used For RDbase used by its command, When GITS_TYPER.PTA = 1, physicall address is used, the RDbase field consist of bits[51:16] of the address, so need to left shift the address by 16 bits. But when GITS_TYPER.PTA = 0, PE number is used, no need to shit anymore. Signed-off-by: Jiafei Pan --- drivers/interrupt_controller/intc_gicv3_its.c | 15 ++++++++++----- 1 file changed, 10 insertions(+), 5 deletions(-) diff --git a/drivers/interrupt_controller/intc_gicv3_its.c b/drivers/interrupt_controller/intc_gicv3_its.c index d3864bbab32a..a9a6018cdd89 100644 --- a/drivers/interrupt_controller/intc_gicv3_its.c +++ b/drivers/interrupt_controller/intc_gicv3_its.c @@ -352,7 +352,7 @@ static int its_send_sync_cmd(struct gicv3_its_data *data, uintptr_t rd_addr) } cmd->raw_cmd[0] = MASK_SET(GITS_CMD_ID_SYNC, GITS_CMD_ID); - cmd->raw_cmd[2] = MASK_SET(rd_addr >> GITS_CMD_RDBASE_ALIGN, GITS_CMD_RDBASE); + cmd->raw_cmd[2] = MASK_SET(rd_addr, GITS_CMD_RDBASE); return its_post_command(data, cmd); } @@ -367,8 +367,7 @@ static int its_send_mapc_cmd(struct gicv3_its_data *data, uint32_t icid, } cmd->raw_cmd[0] = MASK_SET(GITS_CMD_ID_MAPC, GITS_CMD_ID); - cmd->raw_cmd[2] = MASK_SET(icid, GITS_CMD_ICID) | - MASK_SET(rd_addr >> GITS_CMD_RDBASE_ALIGN, GITS_CMD_RDBASE) | + cmd->raw_cmd[2] = MASK_SET(icid, GITS_CMD_ICID) | MASK_SET(rd_addr, GITS_CMD_RDBASE) | MASK_SET(valid ? 1 : 0, GITS_CMD_VALID); return its_post_command(data, cmd); @@ -489,12 +488,18 @@ static uintptr_t gicv3_rdist_get_rdbase(const struct device *dev, unsigned int c { struct gicv3_its_data *data = dev->data; uint64_t typer = sys_read64(data->base + GITS_TYPER); + uintptr_t rdbase; if (GITS_TYPER_PTA_GET(typer)) { - return gic_rdists[cpuid]; + rdbase = gic_rdists[cpuid]; + /* RDbase must be 64KB aligned, only return bits[51:16] of the address */ + rdbase = rdbase >> GITS_CMD_RDBASE_ALIGN; } else { - return GICR_TYPER_PROCESSOR_NUMBER_GET(sys_read64(gic_rdists[cpuid] + GICR_TYPER)); + rdbase = + GICR_TYPER_PROCESSOR_NUMBER_GET(sys_read64(gic_rdists[cpuid] + GICR_TYPER)); } + + return rdbase; } static int gicv3_its_map_intid(const struct device *dev, uint32_t device_id, uint32_t event_id, From 9e35e53263e85aee4972f2d3f06516f2bcca4ebb Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 17:31:59 +0800 Subject: [PATCH 04/10] drivers: intc_gicv3_its: fix sleep issue in pre-kernel GIC v3 ITS is initialized in pre-kernel stage in which sleep function can't work yet, so use busy delay in pre-kernel stage and use sleep delay in post-kernel stage. Signed-off-by: Jiafei Pan --- drivers/interrupt_controller/intc_gicv3_its.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-) diff --git a/drivers/interrupt_controller/intc_gicv3_its.c b/drivers/interrupt_controller/intc_gicv3_its.c index a9a6018cdd89..544158685e1d 100644 --- a/drivers/interrupt_controller/intc_gicv3_its.c +++ b/drivers/interrupt_controller/intc_gicv3_its.c @@ -337,7 +337,11 @@ static int its_post_command(struct gicv3_its_data *data, struct its_cmd_block *c rd_idx, idx, wr_idx); return -ETIMEDOUT; } - k_usleep(1); + if (k_is_pre_kernel()) { + k_busy_wait(1); + } else { + k_usleep(1); + } } return 0; From f7511bfd31057f9c21f47d52526155b959e9f5e5 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 30 May 2025 18:12:25 +0800 Subject: [PATCH 05/10] boards: imx95_evk: a55: enlarge memory size Enlarge the memory size to 10M bytes as it is not enough if run some networking application. Signed-off-by: Jiafei Pan --- boards/nxp/imx95_evk/imx95_evk_mimx9596_a55.dts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55.dts b/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55.dts index d4aff0f100de..4d4866c1a858 100644 --- a/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55.dts +++ b/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55.dts @@ -43,7 +43,7 @@ }; dram: memory@d0000000 { - reg = <0xd0000000 DT_SIZE_M(1)>; + reg = <0xd0000000 DT_SIZE_M(10)>; }; }; From fbbec6c144db4641223efb792394a94e04559056 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 12:21:11 +0800 Subject: [PATCH 06/10] dts: arm64: imx95_a55: add gic v3 its dts node Added dts node for GIC v3 ITS. Signed-off-by: Jiafei Pan --- dts/arm64/nxp/nxp_mimx95_a55.dtsi | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/dts/arm64/nxp/nxp_mimx95_a55.dtsi b/dts/arm64/nxp/nxp_mimx95_a55.dtsi index 37df069d3dd0..cc52bd1d2b23 100644 --- a/dts/arm64/nxp/nxp_mimx95_a55.dtsi +++ b/dts/arm64/nxp/nxp_mimx95_a55.dtsi @@ -76,7 +76,15 @@ <0x48060000 0xc0000>; /* GICR (RD_base + SGI_base) */ interrupt-controller; #interrupt-cells = <4>; + #address-cells = <1>; + #size-cells = <1>; status = "okay"; + + its: msi-controller@48040000 { + compatible = "arm,gic-v3-its"; + reg = <0x48040000 0x20000>; + status = "okay"; + }; }; reserved-memory { From b663daaa0486ecce4faa3593e39cf46247946ec9 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 13 Jun 2025 12:12:18 +0800 Subject: [PATCH 07/10] soc: imx95: a55: include LPI in irq number In case of ITS is enabled, need to include LPI in the total number of irq. Signed-off-by: Jiafei Pan --- soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 b/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 index 0fc9f23d6888..9047517a1001 100644 --- a/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 +++ b/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 @@ -22,8 +22,10 @@ config ARM64_DCACHE_ALL_OPS config ARM64_BOOT_DISABLE_DCACHE default y +# Reserve 8192 LPI interrupt ID starts from 8192 when ITS is enabled config NUM_IRQS - default 320 + default 16384 if GIC_V3_ITS + default 407 if !GIC_V3_ITS config SYS_CLOCK_HW_CYCLES_PER_SEC default 24000000 From 4534af011b74578cea456908902ece4e66d749b8 Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 11:27:04 +0800 Subject: [PATCH 08/10] soc: imx95: a55: enable GIC redistribute noncoherent GIC redistribute on i.MX 95 is DMA noncoherent, so enable CONFIG_GIC_V3_RDIST_DMA_NONCOHERENT. Signed-off-by: Jiafei Pan --- soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 | 3 +++ 1 file changed, 3 insertions(+) diff --git a/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 b/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 index 9047517a1001..0d7fef5ac1fd 100644 --- a/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 +++ b/soc/nxp/imx/imx9/imx95/Kconfig.defconfig.mimx95.a55 @@ -16,6 +16,9 @@ config FLASH_BASE_ADDRESS config GIC_SAFE_CONFIG default y +config GIC_V3_RDIST_DMA_NONCOHERENT + default y + # Disable data cache until MMU is enabled when booting from EL2 config ARM64_DCACHE_ALL_OPS default y From 654003c15714f55f3cf8c5ac07a25edaab54258c Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 16:35:36 +0800 Subject: [PATCH 09/10] boards: imx95_evk: refine GIC and SCMI objects init priority GIC ITS depends on kernel heap, so move GIC initialize to be behind of heap which initialization priority is CONFIG_KERNEL_INIT_PRIORITY_OBJECTS (it is 30 by default). MU mailbox and SCMI objects depend on GIC, so set their init priority to be same with GIC, the initialization sequence decided by the dts dependency although they use the same init priority. Signed-off-by: Jiafei Pan --- boards/nxp/imx95_evk/Kconfig.defconfig | 24 +++++++++++++++++++ .../imx95_evk_mimx9596_a55_defconfig | 2 -- 2 files changed, 24 insertions(+), 2 deletions(-) create mode 100644 boards/nxp/imx95_evk/Kconfig.defconfig diff --git a/boards/nxp/imx95_evk/Kconfig.defconfig b/boards/nxp/imx95_evk/Kconfig.defconfig new file mode 100644 index 000000000000..a32ec5b99bbd --- /dev/null +++ b/boards/nxp/imx95_evk/Kconfig.defconfig @@ -0,0 +1,24 @@ +# Copyright 2024-2025 NXP +# SPDX-License-Identifier: Apache-2.0 + +if SOC_MIMX9596_A55 + +# GIC ITS depends on kernel heap which init priority is 30, so set +# GIC to be 31, mailbox and SCMI will be initialized by the order +# according to dts dependency although they use the same init priority. +config INTC_INIT_PRIORITY + default 31 + +config MBOX_INIT_PRIORITY + default 31 + +config ARM_SCMI_SHMEM_INIT_PRIORITY + default 31 + +config ARM_SCMI_TRANSPORT_INIT_PRIORITY + default 31 + +config CLOCK_CONTROL_INIT_PRIORITY + default 31 + +endif diff --git a/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55_defconfig b/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55_defconfig index 23e5dd52c5a4..88a5148a54ed 100644 --- a/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55_defconfig +++ b/boards/nxp/imx95_evk/imx95_evk_mimx9596_a55_defconfig @@ -31,5 +31,3 @@ CONFIG_CLOCK_CONTROL=y CONFIG_MBOX=y CONFIG_ARM_SCMI=y -CONFIG_INTC_INIT_PRIORITY=2 -CONFIG_MBOX_INIT_PRIORITY=3 From eb1aab7a7079b4a6f6bad709667017978160963d Mon Sep 17 00:00:00 2001 From: Jiafei Pan Date: Fri, 27 Jun 2025 11:27:48 +0800 Subject: [PATCH 10/10] tests: arm64_gicv3_its: add imx95_evk support Add imx95_evk support, as hardware limication, it only has 832 LPIs. Signed-off-by: Jiafei Pan --- .../boards/imx95_evk_mimx9596_a55.conf | 15 +++++++++++++++ tests/arch/arm64/arm64_gicv3_its/src/main.c | 9 ++++++++- 2 files changed, 23 insertions(+), 1 deletion(-) create mode 100644 tests/arch/arm64/arm64_gicv3_its/boards/imx95_evk_mimx9596_a55.conf diff --git a/tests/arch/arm64/arm64_gicv3_its/boards/imx95_evk_mimx9596_a55.conf b/tests/arch/arm64/arm64_gicv3_its/boards/imx95_evk_mimx9596_a55.conf new file mode 100644 index 000000000000..70a699068df6 --- /dev/null +++ b/tests/arch/arm64/arm64_gicv3_its/boards/imx95_evk_mimx9596_a55.conf @@ -0,0 +1,15 @@ +# The GICv3 & ITS drivers allocation needs are: +# - LPI prop table: global 1x64K aligned on 64K +# - LPI pend table: for each redistributor/cpu 1x64K aligned on 64K +# - Devices table: 128x4K aligned on 4K +# - Interrupt Collections table: 1x4K aligned on 4K +# +# This makes 11x64K to permit all allocations to success. +# +# Note, will need 64K HEAP_MEM per CPUs added. +# +# This doesn't necessarily include the Interrupt Translation Table, which are +# 256bytes aligned tables, for reference a 32 ITEs table needs 256bytes. +# +# To permit allocating 256 ITT tables of 32 ITEs, 13x64K HEAP_MEM is needed +CONFIG_HEAP_MEM_POOL_SIZE=851968 diff --git a/tests/arch/arm64/arm64_gicv3_its/src/main.c b/tests/arch/arm64/arm64_gicv3_its/src/main.c index 42f18067b33f..940e4f504f0d 100644 --- a/tests/arch/arm64/arm64_gicv3_its/src/main.c +++ b/tests/arch/arm64/arm64_gicv3_its/src/main.c @@ -19,12 +19,19 @@ static void lpi_irq_handle(const void *parameter) last_lpi_irq_num = i; } +#ifdef CONFIG_SOC_MIMX9596_A55 +/* DeviceID is 8bits */ +#define ITS_TEST_DEV(id) (id & 0xff) +/* Cover up to 832 LPIs over 26 DevicesIDs and 32 EventIDs per DeviceID */ +#define ITS_TEST_NUM_DEVS 26 +#define ITS_TEST_NUM_ITES 32 +#else /* Generate a DeviceID over the whole 16bits */ #define ITS_TEST_DEV(id) ((((id + 256) % 16) << 12) | (((id + 256) % 24) << 8) | (id & 0xff)) - /* Cover up to 8192 LPIs over 256 DevicesIDs and 32 EventIDs per DeviceID */ #define ITS_TEST_NUM_DEVS 256 #define ITS_TEST_NUM_ITES 32 +#endif /* Do not test all 8192 irqs, iterate with a prime offset to cover most of the possible event_ids */ #define ITS_TEST_NEXT 13