Partially revert 21550029f709072aacf3b90edd574e7d3021b400
authorStefano Stabellini <sstabellini@kernel.org>
Tue, 8 Nov 2016 19:42:43 +0000 (11:42 -0800)
committerStefano Stabellini <sstabellini@kernel.org>
Wed, 9 Nov 2016 22:29:59 +0000 (14:29 -0800)
Commit 21550029f709072aacf3b90edd574e7d3021b400 removed the
PLATFORM_QUIRK_GIC_64K_STRIDE quirk and introduced a way to
automatically detect that the two GICC pages have a 64K stride.

However the heuristic requires that the device tree for the platform
reports a GICC size == 128K, which is not the case for some versions of
XGene.

Fix the issue by partially reverting
21550029f709072aacf3b90edd574e7d3021b400:

- reintroduce PLATFORM_QUIRK_GIC_64K_STRIDE for XGene
- force csize and vsize to SZ_128K if csize is initially 4K and if
  PLATFORM_QUIRK_GIC_64K_STRIDE

Also add a warning in case GICC is SZ_128K but not aliased.

Signed-off-by: Stefano Stabellini <sstabellini@kernel.org>
Release-acked-by: Wei Liu <wei.liu2@citrix.com>
Acked-by: Julien Grall <julien.grall@arm.com>
xen/arch/arm/gic-v2.c
xen/arch/arm/platforms/xgene-storm.c
xen/include/asm-arm/platform.h

index 9bd9d0b345d91b3b3d0bd2ee3e5ed7db1e8648e4..9245e7d47fab5b8a6814582e71b4371fea217dfe 100644 (file)
@@ -965,7 +965,12 @@ static void __init gicv2_dt_init(void)
         printk(XENLOG_WARNING "GICv2: WARNING: "
                "The GICC size is too small: %#"PRIx64" expected %#x\n",
                csize, SZ_8K);
-        csize = SZ_8K;
+        if ( platform_has_quirk(PLATFORM_QUIRK_GIC_64K_STRIDE) )
+        {
+            printk(XENLOG_WARNING "GICv2: enable platform quirk: 64K stride\n");
+            vsize = csize = SZ_128K;
+        } else
+            csize = SZ_8K;
     }
 
     /*
@@ -1189,7 +1194,10 @@ static int __init gicv2_init(void)
         printk(XENLOG_WARNING
                "GICv2: Adjusting CPU interface base to %#"PRIx64"\n",
                cbase + aliased_offset);
-    }
+    } else if ( csize == SZ_128K )
+        printk(XENLOG_WARNING
+               "GICv2: GICC size=%#"PRIx64" but not aliased\n",
+               csize);
 
     gicv2.map_hbase = ioremap_nocache(hbase, PAGE_SIZE);
     if ( !gicv2.map_hbase )
index 686b19b6f553a388b70e2c0d75806a6f6d2339b5..c795a95ee286046003311f2e13f19d4f78bc914d 100644 (file)
@@ -67,6 +67,11 @@ static void __init xgene_check_pirq_eoi(void)
               "Please upgrade your firmware to the latest version");
 }
 
+static uint32_t xgene_storm_quirks(void)
+{
+    return PLATFORM_QUIRK_GIC_64K_STRIDE;
+}
+
 static void xgene_storm_reset(void)
 {
     void __iomem *addr;
@@ -116,6 +121,7 @@ PLATFORM_START(xgene_storm, "APM X-GENE STORM")
     .compatible = xgene_storm_dt_compat,
     .init = xgene_storm_init,
     .reset = xgene_storm_reset,
+    .quirks = xgene_storm_quirks,
 PLATFORM_END
 
 /*
index c6e5010bc9844e4370f1e148d815cf80848b57a1..08010ba09b32bfa86436d56bed97da464b728185 100644 (file)
@@ -39,6 +39,13 @@ struct platform_desc {
     const struct dt_device_match *blacklist_dev;
 };
 
+/*
+ * Quirk for platforms where device tree incorrectly reports 4K GICC
+ * size, but actually the two GICC register ranges are placed at 64K
+ * stride.
+ */
+#define PLATFORM_QUIRK_GIC_64K_STRIDE (1 << 0)
+
 void __init platform_init(void);
 int __init platform_init_time(void);
 int __init platform_specific_mapping(struct domain *d);