struct ARMSSEInfo {
     const char *name;
+    int sram_banks;
 };
 
 static const ARMSSEInfo armsse_variants[] = {
     {
         .name = TYPE_IOTKIT,
+        .sram_banks = 1,
     },
 };
 
 static void armsse_init(Object *obj)
 {
     ARMSSE *s = ARMSSE(obj);
+    ARMSSEClass *asc = ARMSSE_GET_CLASS(obj);
+    const ARMSSEInfo *info = asc->info;
     int i;
 
+    assert(info->sram_banks <= MAX_SRAM_BANKS);
+
     memory_region_init(&s->container, obj, "armsse-container", UINT64_MAX);
 
     sysbus_init_child_obj(obj, "armv7m", &s->armv7m, sizeof(s->armv7m),
                           TYPE_TZ_PPC);
     sysbus_init_child_obj(obj, "apb-ppc1", &s->apb_ppc1, sizeof(s->apb_ppc1),
                           TYPE_TZ_PPC);
-    sysbus_init_child_obj(obj, "mpc", &s->mpc, sizeof(s->mpc), TYPE_TZ_MPC);
+    for (i = 0; i < info->sram_banks; i++) {
+        char *name = g_strdup_printf("mpc%d", i);
+        sysbus_init_child_obj(obj, name, &s->mpc[i],
+                              sizeof(s->mpc[i]), TYPE_TZ_MPC);
+        g_free(name);
+    }
     object_initialize_child(obj, "mpc-irq-orgate", &s->mpc_irq_orgate,
                             sizeof(s->mpc_irq_orgate), TYPE_OR_IRQ,
                             &error_abort, NULL);
 
-    for (i = 0; i < IOTS_NUM_EXP_MPC + 1; i++) {
+    for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
         char *name = g_strdup_printf("mpc-irq-splitter-%d", i);
         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
 
 static void armsse_realize(DeviceState *dev, Error **errp)
 {
     ARMSSE *s = ARMSSE(dev);
+    ARMSSEClass *asc = ARMSSE_GET_CLASS(dev);
+    const ARMSSEInfo *info = asc->info;
     int i;
     MemoryRegion *mr;
     Error *err = NULL;
     qdev_connect_gpio_out_named(dev_secctl, "sec_resp_cfg", 0,
                                 qdev_get_gpio_in(dev_splitter, 0));
 
-    /* This RAM lives behind the Memory Protection Controller */
-    memory_region_init_ram(&s->sram0, NULL, "armsse.sram0", 0x00008000, &err);
-    if (err) {
-        error_propagate(errp, err);
-        return;
-    }
-    object_property_set_link(OBJECT(&s->mpc), OBJECT(&s->sram0),
-                             "downstream", &err);
-    if (err) {
-        error_propagate(errp, err);
-        return;
-    }
-    object_property_set_bool(OBJECT(&s->mpc), true, "realized", &err);
-    if (err) {
-        error_propagate(errp, err);
-        return;
+    /* Each SRAM bank lives behind its own Memory Protection Controller */
+    for (i = 0; i < info->sram_banks; i++) {
+        char *ramname = g_strdup_printf("armsse.sram%d", i);
+        SysBusDevice *sbd_mpc;
+
+        memory_region_init_ram(&s->sram[i], NULL, ramname, 0x00008000, &err);
+        g_free(ramname);
+        if (err) {
+            error_propagate(errp, err);
+            return;
+        }
+        object_property_set_link(OBJECT(&s->mpc[i]), OBJECT(&s->sram[i]),
+                                 "downstream", &err);
+        if (err) {
+            error_propagate(errp, err);
+            return;
+        }
+        object_property_set_bool(OBJECT(&s->mpc[i]), true, "realized", &err);
+        if (err) {
+            error_propagate(errp, err);
+            return;
+        }
+        /* Map the upstream end of the MPC into the right place... */
+        sbd_mpc = SYS_BUS_DEVICE(&s->mpc[i]);
+        memory_region_add_subregion(&s->container, 0x20000000 + i * 0x8000,
+                                    sysbus_mmio_get_region(sbd_mpc, 1));
+        /* ...and its register interface */
+        memory_region_add_subregion(&s->container, 0x50083000 + i * 0x1000,
+                                    sysbus_mmio_get_region(sbd_mpc, 0));
     }
-    /* Map the upstream end of the MPC into the right place... */
-    memory_region_add_subregion(&s->container, 0x20000000,
-                                sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->mpc),
-                                                       1));
-    /* ...and its register interface */
-    memory_region_add_subregion(&s->container, 0x50083000,
-                                sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->mpc),
-                                                       0));
 
     /* We must OR together lines from the MPC splitters to go to the NVIC */
     object_property_set_int(OBJECT(&s->mpc_irq_orgate),
-                            IOTS_NUM_EXP_MPC + 1, "num-lines", &err);
+                            IOTS_NUM_EXP_MPC + info->sram_banks,
+                            "num-lines", &err);
     if (err) {
         error_propagate(errp, err);
         return;
     }
 
     /* Wire up the splitters for the MPC IRQs */
-    for (i = 0; i < IOTS_NUM_EXP_MPC + 1; i++) {
+    for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
         DeviceState *dev_splitter = DEVICE(splitter);
 
                                                          "mpcexp_status", i));
         } else {
             /* Splitter input is from our own MPC */
-            qdev_connect_gpio_out_named(DEVICE(&s->mpc), "irq", 0,
+            qdev_connect_gpio_out_named(DEVICE(&s->mpc[i - IOTS_NUM_EXP_MPC]),
+                                        "irq", 0,
                                         qdev_get_gpio_in(dev_splitter, 0));
             qdev_connect_gpio_out(dev_splitter, 0,
                                   qdev_get_gpio_in_named(dev_secctl,