Commit 8c8efa86 authored by Manish Pandey's avatar Manish Pandey Committed by TrustedFirmware Code Review
Browse files

Merge changes I76eee5c5,Ie45ab1d8,Iddcb83d3,I4425777d,I5be2837c, ... into integration

* changes:
  drivers/gicv3: also shift eSPI register offset in GICD_OFFSET_64()
  drivers/gicv3: add debug log for maximum INTID of SPI and eSPI
  drivers/gicv3: limit SPI ID to avoid misjudgement in GICD_OFFSET()
  drivers/gicv3: fix logical issue for num_eints
  drivers/gicv3: fix potential GICD context override with ESPI enabled
  drivers/gicv3: use mpidr to probe GICR for current CPU
parents 42de214f 612b4a3f
/* /*
* Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
* *
* SPDX-License-Identifier: BSD-3-Clause * SPDX-License-Identifier: BSD-3-Clause
*/ */
...@@ -105,6 +105,16 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base) ...@@ -105,6 +105,16 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base)
/* Maximum SPI INTID is 32 * (GICD_TYPER.ITLinesNumber + 1) - 1 */ /* Maximum SPI INTID is 32 * (GICD_TYPER.ITLinesNumber + 1) - 1 */
num_ints = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5; num_ints = ((typer_reg & TYPER_IT_LINES_NO_MASK) + 1U) << 5;
/*
* The GICv3 architecture allows GICD_TYPER.ITLinesNumber to be 31, so
* the maximum possible value for num_ints is 1024. Limit the value to
* MAX_SPI_ID + 1 to avoid getting wrong address in GICD_OFFSET() macro.
*/
if (num_ints > MAX_SPI_ID + 1U) {
num_ints = MAX_SPI_ID + 1U;
}
INFO("Maximum SPI INTID supported: %u\n", num_ints - 1);
/* Treat all (E)SPIs as G1NS by default. We do 32 at a time. */ /* Treat all (E)SPIs as G1NS by default. We do 32 at a time. */
for (i = MIN_SPI_ID; i < num_ints; i += (1U << IGROUPR_SHIFT)) { for (i = MIN_SPI_ID; i < num_ints; i += (1U << IGROUPR_SHIFT)) {
gicd_write_igroupr(gicd_base, i, ~0U); gicd_write_igroupr(gicd_base, i, ~0U);
...@@ -117,7 +127,8 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base) ...@@ -117,7 +127,8 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base)
* Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
*/ */
num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) & num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1; TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID;
INFO("Maximum ESPI INTID supported: %u\n", num_eints - 1);
for (i = MIN_ESPI_ID; i < num_eints; for (i = MIN_ESPI_ID; i < num_eints;
i += (1U << IGROUPR_SHIFT)) { i += (1U << IGROUPR_SHIFT)) {
...@@ -125,6 +136,7 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base) ...@@ -125,6 +136,7 @@ void gicv3_spis_config_defaults(uintptr_t gicd_base)
} }
} else { } else {
num_eints = 0U; num_eints = 0U;
INFO("ESPI range is not implemented.\n");
} }
#endif #endif
......
/* /*
* Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
* *
* SPDX-License-Identifier: BSD-3-Clause * SPDX-License-Identifier: BSD-3-Clause
*/ */
...@@ -70,7 +70,8 @@ static bool is_sgi_ppi(unsigned int id); ...@@ -70,7 +70,8 @@ static bool is_sgi_ppi(unsigned int id);
for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\ for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\
int_id += (1U << REG##R_SHIFT)) { \ int_id += (1U << REG##R_SHIFT)) { \
gicd_write_##reg((base), int_id, \ gicd_write_##reg((base), int_id, \
(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - MIN_SPI_ID))\ (ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - \
round_up(TOTAL_SPI_INTR_NUM, 1U << REG##R_SHIFT)))\
>> REG##R_SHIFT]); \ >> REG##R_SHIFT]); \
} \ } \
} while (false) } while (false)
...@@ -79,7 +80,8 @@ static bool is_sgi_ppi(unsigned int id); ...@@ -79,7 +80,8 @@ static bool is_sgi_ppi(unsigned int id);
do { \ do { \
for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\ for (unsigned int int_id = MIN_ESPI_ID; int_id < (intr_num);\
int_id += (1U << REG##R_SHIFT)) { \ int_id += (1U << REG##R_SHIFT)) { \
(ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - MIN_SPI_ID))\ (ctx)->gicd_##reg[(int_id - (MIN_ESPI_ID - \
round_up(TOTAL_SPI_INTR_NUM, 1U << REG##R_SHIFT)))\
>> REG##R_SHIFT] = gicd_read_##reg((base), int_id);\ >> REG##R_SHIFT] = gicd_read_##reg((base), int_id);\
} \ } \
} while (false) } while (false)
...@@ -755,7 +757,7 @@ void gicv3_distif_save(gicv3_dist_ctx_t * const dist_ctx) ...@@ -755,7 +757,7 @@ void gicv3_distif_save(gicv3_dist_ctx_t * const dist_ctx)
* Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
*/ */
num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) & num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1; TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID;
} else { } else {
num_eints = 0U; num_eints = 0U;
} }
...@@ -879,7 +881,7 @@ void gicv3_distif_init_restore(const gicv3_dist_ctx_t * const dist_ctx) ...@@ -879,7 +881,7 @@ void gicv3_distif_init_restore(const gicv3_dist_ctx_t * const dist_ctx)
* Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095 * Maximum ESPI INTID is 32 * (GICD_TYPER.ESPI_range + 1) + 4095
*/ */
num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) & num_eints = ((((typer_reg >> TYPER_ESPI_RANGE_SHIFT) &
TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID - 1; TYPER_ESPI_RANGE_MASK) + 1U) << 5) + MIN_ESPI_ID;
} else { } else {
num_eints = 0U; num_eints = 0U;
} }
...@@ -1299,8 +1301,8 @@ unsigned int gicv3_set_pmr(unsigned int mask) ...@@ -1299,8 +1301,8 @@ unsigned int gicv3_set_pmr(unsigned int mask)
******************************************************************************/ ******************************************************************************/
int gicv3_rdistif_probe(const uintptr_t gicr_frame) int gicv3_rdistif_probe(const uintptr_t gicr_frame)
{ {
u_register_t mpidr; u_register_t mpidr, mpidr_self;
unsigned int proc_num, proc_self; unsigned int proc_num;
uint64_t typer_val; uint64_t typer_val;
uintptr_t rdistif_base; uintptr_t rdistif_base;
bool gicr_frame_found = false; bool gicr_frame_found = false;
...@@ -1314,18 +1316,18 @@ int gicv3_rdistif_probe(const uintptr_t gicr_frame) ...@@ -1314,18 +1316,18 @@ int gicv3_rdistif_probe(const uintptr_t gicr_frame)
assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U); assert((read_sctlr_el3() & SCTLR_C_BIT) != 0U);
#endif /* !__aarch64__ */ #endif /* !__aarch64__ */
proc_self = gicv3_driver_data->mpidr_to_core_pos(read_mpidr_el1()); mpidr_self = read_mpidr_el1() & MPIDR_AFFINITY_MASK;
rdistif_base = gicr_frame; rdistif_base = gicr_frame;
do { do {
typer_val = gicr_read_typer(rdistif_base); typer_val = gicr_read_typer(rdistif_base);
if (gicv3_driver_data->mpidr_to_core_pos != NULL) {
mpidr = mpidr_from_gicr_typer(typer_val); mpidr = mpidr_from_gicr_typer(typer_val);
if (gicv3_driver_data->mpidr_to_core_pos != NULL) {
proc_num = gicv3_driver_data->mpidr_to_core_pos(mpidr); proc_num = gicv3_driver_data->mpidr_to_core_pos(mpidr);
} else { } else {
proc_num = (unsigned int)(typer_val >> proc_num = (unsigned int)(typer_val >>
TYPER_PROC_NUM_SHIFT) & TYPER_PROC_NUM_MASK; TYPER_PROC_NUM_SHIFT) & TYPER_PROC_NUM_MASK;
} }
if (proc_num == proc_self) { if (mpidr == mpidr_self) {
/* The base address doesn't need to be initialized on /* The base address doesn't need to be initialized on
* every warm boot. * every warm boot.
*/ */
......
/* /*
* Copyright (c) 2015-2020, ARM Limited and Contributors. All rights reserved. * Copyright (c) 2015-2021, ARM Limited and Contributors. All rights reserved.
* *
* SPDX-License-Identifier: BSD-3-Clause * SPDX-License-Identifier: BSD-3-Clause
*/ */
...@@ -48,7 +48,8 @@ ...@@ -48,7 +48,8 @@
#define GICD_OFFSET_64(REG, id) \ #define GICD_OFFSET_64(REG, id) \
(((id) <= MAX_SPI_ID) ? \ (((id) <= MAX_SPI_ID) ? \
GICD_##REG##R + (((uintptr_t)(id) >> REG##R_SHIFT) << 3) : \ GICD_##REG##R + (((uintptr_t)(id) >> REG##R_SHIFT) << 3) : \
GICD_##REG##RE + (((uintptr_t)(id) - MIN_ESPI_ID) << 3)) GICD_##REG##RE + ((((uintptr_t)(id) - MIN_ESPI_ID) >> \
REG##R_SHIFT) << 3))
#else /* GICv3 */ #else /* GICv3 */
#define GICD_OFFSET_8(REG, id) \ #define GICD_OFFSET_8(REG, id) \
......
Markdown is supported
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment