On Thu, Feb 03, 2022 at 07:31:24PM +0000, Robin Murphy wrote: > The original version of the IORT PMCG definition had an oversight > wherein there was no way to describe the second register page for an > implementation using the recommended RELOC_CTRS feature. Although the > spec was fixed, and the final patches merged to ACPICA and Linux written > against the new version, it seems that some old firmware based on the > original revision has survived and turned up in the wild. > > Add a check for the original PMCG definition, and avoid filling in the > second memory resource with nonsense if so. Otherwise it is likely that > something horrible will happen when the PMCG driver attempts to probe. > > Reported-by: Michael Petlan <mpetlan@xxxxxxxxxx> > Fixes: 24e516049360 ("ACPI/IORT: Add support for PMCG") > Signed-off-by: Robin Murphy <robin.murphy@xxxxxxx> > --- > > v2: Simpler workaround, since I realised platform_get_resource() > should happily just skip over a zero-initialised hole in the > resource array. > > drivers/acpi/arm64/iort.c | 14 +++++++++++--- > 1 file changed, 11 insertions(+), 3 deletions(-) Acked-by: Lorenzo Pieralisi <lorenzo.pieralisi@xxxxxxx> Should we send it to stable kernels ? I'd kindly ask Catalin/Will to pick it up please. Thanks, Lorenzo > > diff --git a/drivers/acpi/arm64/iort.c b/drivers/acpi/arm64/iort.c > index 175397913be1..7092b94b2aae 100644 > --- a/drivers/acpi/arm64/iort.c > +++ b/drivers/acpi/arm64/iort.c > @@ -1371,9 +1371,17 @@ static void __init arm_smmu_v3_pmcg_init_resources(struct resource *res, > res[0].start = pmcg->page0_base_address; > res[0].end = pmcg->page0_base_address + SZ_4K - 1; > res[0].flags = IORESOURCE_MEM; > - res[1].start = pmcg->page1_base_address; > - res[1].end = pmcg->page1_base_address + SZ_4K - 1; > - res[1].flags = IORESOURCE_MEM; > + /* > + * The initial version in DEN0049C lacked a way to describe register > + * page 1, which makes it broken for most PMCG implementations; in > + * that case, just let the driver fail gracefully if it expects to > + * find a second memory resource. > + */ > + if (node->revision > 0) { > + res[1].start = pmcg->page1_base_address; > + res[1].end = pmcg->page1_base_address + SZ_4K - 1; > + res[1].flags = IORESOURCE_MEM; > + } > > if (pmcg->overflow_gsiv) > acpi_iort_register_irq(pmcg->overflow_gsiv, "overflow", > -- > 2.28.0.dirty >