xref: /qemu/hw/arm/armsse.c (revision f8574705f62b38a610d398573828b57da24b1adb)
1 /*
2  * Arm SSE (Subsystems for Embedded): IoTKit
3  *
4  * Copyright (c) 2018 Linaro Limited
5  * Written by Peter Maydell
6  *
7  * This program is free software; you can redistribute it and/or modify
8  * it under the terms of the GNU General Public License version 2 or
9  * (at your option) any later version.
10  */
11 
12 #include "qemu/osdep.h"
13 #include "qemu/log.h"
14 #include "qapi/error.h"
15 #include "trace.h"
16 #include "hw/sysbus.h"
17 #include "hw/registerfields.h"
18 #include "hw/arm/armsse.h"
19 #include "hw/arm/arm.h"
20 
21 /* Format of the System Information block SYS_CONFIG register */
22 typedef enum SysConfigFormat {
23     IoTKitFormat,
24     SSE200Format,
25 } SysConfigFormat;
26 
27 struct ARMSSEInfo {
28     const char *name;
29     int sram_banks;
30     int num_cpus;
31     uint32_t sys_version;
32     SysConfigFormat sys_config_format;
33     bool has_mhus;
34 };
35 
36 static const ARMSSEInfo armsse_variants[] = {
37     {
38         .name = TYPE_IOTKIT,
39         .sram_banks = 1,
40         .num_cpus = 1,
41         .sys_version = 0x41743,
42         .sys_config_format = IoTKitFormat,
43         .has_mhus = false,
44     },
45 };
46 
47 static uint32_t armsse_sys_config_value(ARMSSE *s, const ARMSSEInfo *info)
48 {
49     /* Return the SYS_CONFIG value for this SSE */
50     uint32_t sys_config;
51 
52     switch (info->sys_config_format) {
53     case IoTKitFormat:
54         sys_config = 0;
55         sys_config = deposit32(sys_config, 0, 4, info->sram_banks);
56         sys_config = deposit32(sys_config, 4, 4, s->sram_addr_width - 12);
57         break;
58     case SSE200Format:
59         sys_config = 0;
60         sys_config = deposit32(sys_config, 0, 4, info->sram_banks);
61         sys_config = deposit32(sys_config, 4, 5, s->sram_addr_width);
62         sys_config = deposit32(sys_config, 24, 4, 2);
63         if (info->num_cpus > 1) {
64             sys_config = deposit32(sys_config, 10, 1, 1);
65             sys_config = deposit32(sys_config, 20, 4, info->sram_banks - 1);
66             sys_config = deposit32(sys_config, 28, 4, 2);
67         }
68         break;
69     default:
70         g_assert_not_reached();
71     }
72     return sys_config;
73 }
74 
75 /* Clock frequency in HZ of the 32KHz "slow clock" */
76 #define S32KCLK (32 * 1000)
77 
78 /* Is internal IRQ n shared between CPUs in a multi-core SSE ? */
79 static bool irq_is_common[32] = {
80     [0 ... 5] = true,
81     /* 6, 7: per-CPU MHU interrupts */
82     [8 ... 12] = true,
83     /* 13: per-CPU icache interrupt */
84     /* 14: reserved */
85     [15 ... 20] = true,
86     /* 21: reserved */
87     [22 ... 26] = true,
88     /* 27: reserved */
89     /* 28, 29: per-CPU CTI interrupts */
90     /* 30, 31: reserved */
91 };
92 
93 /* Create an alias region of @size bytes starting at @base
94  * which mirrors the memory starting at @orig.
95  */
96 static void make_alias(ARMSSE *s, MemoryRegion *mr, const char *name,
97                        hwaddr base, hwaddr size, hwaddr orig)
98 {
99     memory_region_init_alias(mr, NULL, name, &s->container, orig, size);
100     /* The alias is even lower priority than unimplemented_device regions */
101     memory_region_add_subregion_overlap(&s->container, base, mr, -1500);
102 }
103 
104 static void irq_status_forwarder(void *opaque, int n, int level)
105 {
106     qemu_irq destirq = opaque;
107 
108     qemu_set_irq(destirq, level);
109 }
110 
111 static void nsccfg_handler(void *opaque, int n, int level)
112 {
113     ARMSSE *s = ARMSSE(opaque);
114 
115     s->nsccfg = level;
116 }
117 
118 static void armsse_forward_ppc(ARMSSE *s, const char *ppcname, int ppcnum)
119 {
120     /* Each of the 4 AHB and 4 APB PPCs that might be present in a
121      * system using the ARMSSE has a collection of control lines which
122      * are provided by the security controller and which we want to
123      * expose as control lines on the ARMSSE device itself, so the
124      * code using the ARMSSE can wire them up to the PPCs.
125      */
126     SplitIRQ *splitter = &s->ppc_irq_splitter[ppcnum];
127     DeviceState *armssedev = DEVICE(s);
128     DeviceState *dev_secctl = DEVICE(&s->secctl);
129     DeviceState *dev_splitter = DEVICE(splitter);
130     char *name;
131 
132     name = g_strdup_printf("%s_nonsec", ppcname);
133     qdev_pass_gpios(dev_secctl, armssedev, name);
134     g_free(name);
135     name = g_strdup_printf("%s_ap", ppcname);
136     qdev_pass_gpios(dev_secctl, armssedev, name);
137     g_free(name);
138     name = g_strdup_printf("%s_irq_enable", ppcname);
139     qdev_pass_gpios(dev_secctl, armssedev, name);
140     g_free(name);
141     name = g_strdup_printf("%s_irq_clear", ppcname);
142     qdev_pass_gpios(dev_secctl, armssedev, name);
143     g_free(name);
144 
145     /* irq_status is a little more tricky, because we need to
146      * split it so we can send it both to the security controller
147      * and to our OR gate for the NVIC interrupt line.
148      * Connect up the splitter's outputs, and create a GPIO input
149      * which will pass the line state to the input splitter.
150      */
151     name = g_strdup_printf("%s_irq_status", ppcname);
152     qdev_connect_gpio_out(dev_splitter, 0,
153                           qdev_get_gpio_in_named(dev_secctl,
154                                                  name, 0));
155     qdev_connect_gpio_out(dev_splitter, 1,
156                           qdev_get_gpio_in(DEVICE(&s->ppc_irq_orgate), ppcnum));
157     s->irq_status_in[ppcnum] = qdev_get_gpio_in(dev_splitter, 0);
158     qdev_init_gpio_in_named_with_opaque(armssedev, irq_status_forwarder,
159                                         s->irq_status_in[ppcnum], name, 1);
160     g_free(name);
161 }
162 
163 static void armsse_forward_sec_resp_cfg(ARMSSE *s)
164 {
165     /* Forward the 3rd output from the splitter device as a
166      * named GPIO output of the armsse object.
167      */
168     DeviceState *dev = DEVICE(s);
169     DeviceState *dev_splitter = DEVICE(&s->sec_resp_splitter);
170 
171     qdev_init_gpio_out_named(dev, &s->sec_resp_cfg, "sec_resp_cfg", 1);
172     s->sec_resp_cfg_in = qemu_allocate_irq(irq_status_forwarder,
173                                            s->sec_resp_cfg, 1);
174     qdev_connect_gpio_out(dev_splitter, 2, s->sec_resp_cfg_in);
175 }
176 
177 static void armsse_init(Object *obj)
178 {
179     ARMSSE *s = ARMSSE(obj);
180     ARMSSEClass *asc = ARMSSE_GET_CLASS(obj);
181     const ARMSSEInfo *info = asc->info;
182     int i;
183 
184     assert(info->sram_banks <= MAX_SRAM_BANKS);
185     assert(info->num_cpus <= SSE_MAX_CPUS);
186 
187     memory_region_init(&s->container, obj, "armsse-container", UINT64_MAX);
188 
189     for (i = 0; i < info->num_cpus; i++) {
190         /*
191          * We put each CPU in its own cluster as they are logically
192          * distinct and may be configured differently.
193          */
194         char *name;
195 
196         name = g_strdup_printf("cluster%d", i);
197         object_initialize_child(obj, name, &s->cluster[i],
198                                 sizeof(s->cluster[i]), TYPE_CPU_CLUSTER,
199                                 &error_abort, NULL);
200         qdev_prop_set_uint32(DEVICE(&s->cluster[i]), "cluster-id", i);
201         g_free(name);
202 
203         name = g_strdup_printf("armv7m%d", i);
204         sysbus_init_child_obj(OBJECT(&s->cluster[i]), name,
205                               &s->armv7m[i], sizeof(s->armv7m), TYPE_ARMV7M);
206         qdev_prop_set_string(DEVICE(&s->armv7m[i]), "cpu-type",
207                              ARM_CPU_TYPE_NAME("cortex-m33"));
208         g_free(name);
209         name = g_strdup_printf("arm-sse-cpu-container%d", i);
210         memory_region_init(&s->cpu_container[i], obj, name, UINT64_MAX);
211         g_free(name);
212         if (i > 0) {
213             name = g_strdup_printf("arm-sse-container-alias%d", i);
214             memory_region_init_alias(&s->container_alias[i - 1], obj,
215                                      name, &s->container, 0, UINT64_MAX);
216             g_free(name);
217         }
218     }
219 
220     sysbus_init_child_obj(obj, "secctl", &s->secctl, sizeof(s->secctl),
221                           TYPE_IOTKIT_SECCTL);
222     sysbus_init_child_obj(obj, "apb-ppc0", &s->apb_ppc0, sizeof(s->apb_ppc0),
223                           TYPE_TZ_PPC);
224     sysbus_init_child_obj(obj, "apb-ppc1", &s->apb_ppc1, sizeof(s->apb_ppc1),
225                           TYPE_TZ_PPC);
226     for (i = 0; i < info->sram_banks; i++) {
227         char *name = g_strdup_printf("mpc%d", i);
228         sysbus_init_child_obj(obj, name, &s->mpc[i],
229                               sizeof(s->mpc[i]), TYPE_TZ_MPC);
230         g_free(name);
231     }
232     object_initialize_child(obj, "mpc-irq-orgate", &s->mpc_irq_orgate,
233                             sizeof(s->mpc_irq_orgate), TYPE_OR_IRQ,
234                             &error_abort, NULL);
235 
236     for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
237         char *name = g_strdup_printf("mpc-irq-splitter-%d", i);
238         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
239 
240         object_initialize_child(obj, name, splitter, sizeof(*splitter),
241                                 TYPE_SPLIT_IRQ, &error_abort, NULL);
242         g_free(name);
243     }
244     sysbus_init_child_obj(obj, "timer0", &s->timer0, sizeof(s->timer0),
245                           TYPE_CMSDK_APB_TIMER);
246     sysbus_init_child_obj(obj, "timer1", &s->timer1, sizeof(s->timer1),
247                           TYPE_CMSDK_APB_TIMER);
248     sysbus_init_child_obj(obj, "s32ktimer", &s->s32ktimer, sizeof(s->s32ktimer),
249                           TYPE_CMSDK_APB_TIMER);
250     sysbus_init_child_obj(obj, "dualtimer", &s->dualtimer, sizeof(s->dualtimer),
251                           TYPE_CMSDK_APB_DUALTIMER);
252     sysbus_init_child_obj(obj, "s32kwatchdog", &s->s32kwatchdog,
253                           sizeof(s->s32kwatchdog), TYPE_CMSDK_APB_WATCHDOG);
254     sysbus_init_child_obj(obj, "nswatchdog", &s->nswatchdog,
255                           sizeof(s->nswatchdog), TYPE_CMSDK_APB_WATCHDOG);
256     sysbus_init_child_obj(obj, "swatchdog", &s->swatchdog,
257                           sizeof(s->swatchdog), TYPE_CMSDK_APB_WATCHDOG);
258     sysbus_init_child_obj(obj, "armsse-sysctl", &s->sysctl,
259                           sizeof(s->sysctl), TYPE_IOTKIT_SYSCTL);
260     sysbus_init_child_obj(obj, "armsse-sysinfo", &s->sysinfo,
261                           sizeof(s->sysinfo), TYPE_IOTKIT_SYSINFO);
262     if (info->has_mhus) {
263         sysbus_init_child_obj(obj, "mhu0", &s->mhu[0], sizeof(s->mhu[0]),
264                               TYPE_UNIMPLEMENTED_DEVICE);
265         sysbus_init_child_obj(obj, "mhu1", &s->mhu[1], sizeof(s->mhu[1]),
266                               TYPE_UNIMPLEMENTED_DEVICE);
267     }
268     object_initialize_child(obj, "nmi-orgate", &s->nmi_orgate,
269                             sizeof(s->nmi_orgate), TYPE_OR_IRQ,
270                             &error_abort, NULL);
271     object_initialize_child(obj, "ppc-irq-orgate", &s->ppc_irq_orgate,
272                             sizeof(s->ppc_irq_orgate), TYPE_OR_IRQ,
273                             &error_abort, NULL);
274     object_initialize_child(obj, "sec-resp-splitter", &s->sec_resp_splitter,
275                             sizeof(s->sec_resp_splitter), TYPE_SPLIT_IRQ,
276                             &error_abort, NULL);
277     for (i = 0; i < ARRAY_SIZE(s->ppc_irq_splitter); i++) {
278         char *name = g_strdup_printf("ppc-irq-splitter-%d", i);
279         SplitIRQ *splitter = &s->ppc_irq_splitter[i];
280 
281         object_initialize_child(obj, name, splitter, sizeof(*splitter),
282                                 TYPE_SPLIT_IRQ, &error_abort, NULL);
283         g_free(name);
284     }
285     if (info->num_cpus > 1) {
286         for (i = 0; i < ARRAY_SIZE(s->cpu_irq_splitter); i++) {
287             if (irq_is_common[i]) {
288                 char *name = g_strdup_printf("cpu-irq-splitter%d", i);
289                 SplitIRQ *splitter = &s->cpu_irq_splitter[i];
290 
291                 object_initialize_child(obj, name, splitter, sizeof(*splitter),
292                                         TYPE_SPLIT_IRQ, &error_abort, NULL);
293                 g_free(name);
294             }
295         }
296     }
297 }
298 
299 static void armsse_exp_irq(void *opaque, int n, int level)
300 {
301     qemu_irq *irqarray = opaque;
302 
303     qemu_set_irq(irqarray[n], level);
304 }
305 
306 static void armsse_mpcexp_status(void *opaque, int n, int level)
307 {
308     ARMSSE *s = ARMSSE(opaque);
309     qemu_set_irq(s->mpcexp_status_in[n], level);
310 }
311 
312 static qemu_irq armsse_get_common_irq_in(ARMSSE *s, int irqno)
313 {
314     /*
315      * Return a qemu_irq which can be used to signal IRQ n to
316      * all CPUs in the SSE.
317      */
318     ARMSSEClass *asc = ARMSSE_GET_CLASS(s);
319     const ARMSSEInfo *info = asc->info;
320 
321     assert(irq_is_common[irqno]);
322 
323     if (info->num_cpus == 1) {
324         /* Only one CPU -- just connect directly to it */
325         return qdev_get_gpio_in(DEVICE(&s->armv7m[0]), irqno);
326     } else {
327         /* Connect to the splitter which feeds all CPUs */
328         return qdev_get_gpio_in(DEVICE(&s->cpu_irq_splitter[irqno]), 0);
329     }
330 }
331 
332 static void armsse_realize(DeviceState *dev, Error **errp)
333 {
334     ARMSSE *s = ARMSSE(dev);
335     ARMSSEClass *asc = ARMSSE_GET_CLASS(dev);
336     const ARMSSEInfo *info = asc->info;
337     int i;
338     MemoryRegion *mr;
339     Error *err = NULL;
340     SysBusDevice *sbd_apb_ppc0;
341     SysBusDevice *sbd_secctl;
342     DeviceState *dev_apb_ppc0;
343     DeviceState *dev_apb_ppc1;
344     DeviceState *dev_secctl;
345     DeviceState *dev_splitter;
346     uint32_t addr_width_max;
347 
348     if (!s->board_memory) {
349         error_setg(errp, "memory property was not set");
350         return;
351     }
352 
353     if (!s->mainclk_frq) {
354         error_setg(errp, "MAINCLK property was not set");
355         return;
356     }
357 
358     /* max SRAM_ADDR_WIDTH: 24 - log2(SRAM_NUM_BANK) */
359     assert(is_power_of_2(info->sram_banks));
360     addr_width_max = 24 - ctz32(info->sram_banks);
361     if (s->sram_addr_width < 1 || s->sram_addr_width > addr_width_max) {
362         error_setg(errp, "SRAM_ADDR_WIDTH must be between 1 and %d",
363                    addr_width_max);
364         return;
365     }
366 
367     /* Handling of which devices should be available only to secure
368      * code is usually done differently for M profile than for A profile.
369      * Instead of putting some devices only into the secure address space,
370      * devices exist in both address spaces but with hard-wired security
371      * permissions that will cause the CPU to fault for non-secure accesses.
372      *
373      * The ARMSSE has an IDAU (Implementation Defined Access Unit),
374      * which specifies hard-wired security permissions for different
375      * areas of the physical address space. For the ARMSSE IDAU, the
376      * top 4 bits of the physical address are the IDAU region ID, and
377      * if bit 28 (ie the lowest bit of the ID) is 0 then this is an NS
378      * region, otherwise it is an S region.
379      *
380      * The various devices and RAMs are generally all mapped twice,
381      * once into a region that the IDAU defines as secure and once
382      * into a non-secure region. They sit behind either a Memory
383      * Protection Controller (for RAM) or a Peripheral Protection
384      * Controller (for devices), which allow a more fine grained
385      * configuration of whether non-secure accesses are permitted.
386      *
387      * (The other place that guest software can configure security
388      * permissions is in the architected SAU (Security Attribution
389      * Unit), which is entirely inside the CPU. The IDAU can upgrade
390      * the security attributes for a region to more restrictive than
391      * the SAU specifies, but cannot downgrade them.)
392      *
393      * 0x10000000..0x1fffffff  alias of 0x00000000..0x0fffffff
394      * 0x20000000..0x2007ffff  32KB FPGA block RAM
395      * 0x30000000..0x3fffffff  alias of 0x20000000..0x2fffffff
396      * 0x40000000..0x4000ffff  base peripheral region 1
397      * 0x40010000..0x4001ffff  CPU peripherals (none for ARMSSE)
398      * 0x40020000..0x4002ffff  system control element peripherals
399      * 0x40080000..0x400fffff  base peripheral region 2
400      * 0x50000000..0x5fffffff  alias of 0x40000000..0x4fffffff
401      */
402 
403     memory_region_add_subregion_overlap(&s->container, 0, s->board_memory, -2);
404 
405     for (i = 0; i < info->num_cpus; i++) {
406         DeviceState *cpudev = DEVICE(&s->armv7m[i]);
407         Object *cpuobj = OBJECT(&s->armv7m[i]);
408         int j;
409         char *gpioname;
410 
411         qdev_prop_set_uint32(cpudev, "num-irq", s->exp_numirq + 32);
412         /*
413          * In real hardware the initial Secure VTOR is set from the INITSVTOR0
414          * register in the IoT Kit System Control Register block, and the
415          * initial value of that is in turn specifiable by the FPGA that
416          * instantiates the IoT Kit. In QEMU we don't implement this wrinkle,
417          * and simply set the CPU's init-svtor to the IoT Kit default value.
418          * In SSE-200 the situation is similar, except that the default value
419          * is a reset-time signal input. Typically a board using the SSE-200
420          * will have a system control processor whose boot firmware initializes
421          * the INITSVTOR* registers before powering up the CPUs in any case,
422          * so the hardware's default value doesn't matter. QEMU doesn't emulate
423          * the control processor, so instead we behave in the way that the
424          * firmware does. All boards currently known about have firmware that
425          * sets the INITSVTOR0 and INITSVTOR1 registers to 0x10000000, like the
426          * IoTKit default. We can make this more configurable if necessary.
427          */
428         qdev_prop_set_uint32(cpudev, "init-svtor", 0x10000000);
429         /*
430          * Start all CPUs except CPU0 powered down. In real hardware it is
431          * a configurable property of the SSE-200 which CPUs start powered up
432          * (via the CPUWAIT0_RST and CPUWAIT1_RST parameters), but since all
433          * the boards we care about start CPU0 and leave CPU1 powered off,
434          * we hard-code that for now. We can add QOM properties for this
435          * later if necessary.
436          */
437         if (i > 0) {
438             object_property_set_bool(cpuobj, true, "start-powered-off", &err);
439             if (err) {
440                 error_propagate(errp, err);
441                 return;
442             }
443         }
444 
445         if (i > 0) {
446             memory_region_add_subregion_overlap(&s->cpu_container[i], 0,
447                                                 &s->container_alias[i - 1], -1);
448         } else {
449             memory_region_add_subregion_overlap(&s->cpu_container[i], 0,
450                                                 &s->container, -1);
451         }
452         object_property_set_link(cpuobj, OBJECT(&s->cpu_container[i]),
453                                  "memory", &err);
454         if (err) {
455             error_propagate(errp, err);
456             return;
457         }
458         object_property_set_link(cpuobj, OBJECT(s), "idau", &err);
459         if (err) {
460             error_propagate(errp, err);
461             return;
462         }
463         object_property_set_bool(cpuobj, true, "realized", &err);
464         if (err) {
465             error_propagate(errp, err);
466             return;
467         }
468         /*
469          * The cluster must be realized after the armv7m container, as
470          * the container's CPU object is only created on realize, and the
471          * CPU must exist and have been parented into the cluster before
472          * the cluster is realized.
473          */
474         object_property_set_bool(OBJECT(&s->cluster[i]),
475                                  true, "realized", &err);
476         if (err) {
477             error_propagate(errp, err);
478             return;
479         }
480 
481         /* Connect EXP_IRQ/EXP_CPUn_IRQ GPIOs to the NVIC's lines 32 and up */
482         s->exp_irqs[i] = g_new(qemu_irq, s->exp_numirq);
483         for (j = 0; j < s->exp_numirq; j++) {
484             s->exp_irqs[i][j] = qdev_get_gpio_in(cpudev, i + 32);
485         }
486         if (i == 0) {
487             gpioname = g_strdup("EXP_IRQ");
488         } else {
489             gpioname = g_strdup_printf("EXP_CPU%d_IRQ", i);
490         }
491         qdev_init_gpio_in_named_with_opaque(dev, armsse_exp_irq,
492                                             s->exp_irqs[i],
493                                             gpioname, s->exp_numirq);
494         g_free(gpioname);
495     }
496 
497     /* Wire up the splitters that connect common IRQs to all CPUs */
498     if (info->num_cpus > 1) {
499         for (i = 0; i < ARRAY_SIZE(s->cpu_irq_splitter); i++) {
500             if (irq_is_common[i]) {
501                 Object *splitter = OBJECT(&s->cpu_irq_splitter[i]);
502                 DeviceState *devs = DEVICE(splitter);
503                 int cpunum;
504 
505                 object_property_set_int(splitter, info->num_cpus,
506                                         "num-lines", &err);
507                 if (err) {
508                     error_propagate(errp, err);
509                     return;
510                 }
511                 object_property_set_bool(splitter, true, "realized", &err);
512                 if (err) {
513                     error_propagate(errp, err);
514                     return;
515                 }
516                 for (cpunum = 0; cpunum < info->num_cpus; cpunum++) {
517                     DeviceState *cpudev = DEVICE(&s->armv7m[cpunum]);
518 
519                     qdev_connect_gpio_out(devs, cpunum,
520                                           qdev_get_gpio_in(cpudev, i));
521                 }
522             }
523         }
524     }
525 
526     /* Set up the big aliases first */
527     make_alias(s, &s->alias1, "alias 1", 0x10000000, 0x10000000, 0x00000000);
528     make_alias(s, &s->alias2, "alias 2", 0x30000000, 0x10000000, 0x20000000);
529     /* The 0x50000000..0x5fffffff region is not a pure alias: it has
530      * a few extra devices that only appear there (generally the
531      * control interfaces for the protection controllers).
532      * We implement this by mapping those devices over the top of this
533      * alias MR at a higher priority.
534      */
535     make_alias(s, &s->alias3, "alias 3", 0x50000000, 0x10000000, 0x40000000);
536 
537 
538     /* Security controller */
539     object_property_set_bool(OBJECT(&s->secctl), true, "realized", &err);
540     if (err) {
541         error_propagate(errp, err);
542         return;
543     }
544     sbd_secctl = SYS_BUS_DEVICE(&s->secctl);
545     dev_secctl = DEVICE(&s->secctl);
546     sysbus_mmio_map(sbd_secctl, 0, 0x50080000);
547     sysbus_mmio_map(sbd_secctl, 1, 0x40080000);
548 
549     s->nsc_cfg_in = qemu_allocate_irq(nsccfg_handler, s, 1);
550     qdev_connect_gpio_out_named(dev_secctl, "nsc_cfg", 0, s->nsc_cfg_in);
551 
552     /* The sec_resp_cfg output from the security controller must be split into
553      * multiple lines, one for each of the PPCs within the ARMSSE and one
554      * that will be an output from the ARMSSE to the system.
555      */
556     object_property_set_int(OBJECT(&s->sec_resp_splitter), 3,
557                             "num-lines", &err);
558     if (err) {
559         error_propagate(errp, err);
560         return;
561     }
562     object_property_set_bool(OBJECT(&s->sec_resp_splitter), true,
563                              "realized", &err);
564     if (err) {
565         error_propagate(errp, err);
566         return;
567     }
568     dev_splitter = DEVICE(&s->sec_resp_splitter);
569     qdev_connect_gpio_out_named(dev_secctl, "sec_resp_cfg", 0,
570                                 qdev_get_gpio_in(dev_splitter, 0));
571 
572     /* Each SRAM bank lives behind its own Memory Protection Controller */
573     for (i = 0; i < info->sram_banks; i++) {
574         char *ramname = g_strdup_printf("armsse.sram%d", i);
575         SysBusDevice *sbd_mpc;
576         uint32_t sram_bank_size = 1 << s->sram_addr_width;
577 
578         memory_region_init_ram(&s->sram[i], NULL, ramname,
579                                sram_bank_size, &err);
580         g_free(ramname);
581         if (err) {
582             error_propagate(errp, err);
583             return;
584         }
585         object_property_set_link(OBJECT(&s->mpc[i]), OBJECT(&s->sram[i]),
586                                  "downstream", &err);
587         if (err) {
588             error_propagate(errp, err);
589             return;
590         }
591         object_property_set_bool(OBJECT(&s->mpc[i]), true, "realized", &err);
592         if (err) {
593             error_propagate(errp, err);
594             return;
595         }
596         /* Map the upstream end of the MPC into the right place... */
597         sbd_mpc = SYS_BUS_DEVICE(&s->mpc[i]);
598         memory_region_add_subregion(&s->container,
599                                     0x20000000 + i * sram_bank_size,
600                                     sysbus_mmio_get_region(sbd_mpc, 1));
601         /* ...and its register interface */
602         memory_region_add_subregion(&s->container, 0x50083000 + i * 0x1000,
603                                     sysbus_mmio_get_region(sbd_mpc, 0));
604     }
605 
606     /* We must OR together lines from the MPC splitters to go to the NVIC */
607     object_property_set_int(OBJECT(&s->mpc_irq_orgate),
608                             IOTS_NUM_EXP_MPC + info->sram_banks,
609                             "num-lines", &err);
610     if (err) {
611         error_propagate(errp, err);
612         return;
613     }
614     object_property_set_bool(OBJECT(&s->mpc_irq_orgate), true,
615                              "realized", &err);
616     if (err) {
617         error_propagate(errp, err);
618         return;
619     }
620     qdev_connect_gpio_out(DEVICE(&s->mpc_irq_orgate), 0,
621                           armsse_get_common_irq_in(s, 9));
622 
623     /* Devices behind APB PPC0:
624      *   0x40000000: timer0
625      *   0x40001000: timer1
626      *   0x40002000: dual timer
627      *   0x40003000: MHU0 (SSE-200 only)
628      *   0x40004000: MHU1 (SSE-200 only)
629      * We must configure and realize each downstream device and connect
630      * it to the appropriate PPC port; then we can realize the PPC and
631      * map its upstream ends to the right place in the container.
632      */
633     qdev_prop_set_uint32(DEVICE(&s->timer0), "pclk-frq", s->mainclk_frq);
634     object_property_set_bool(OBJECT(&s->timer0), true, "realized", &err);
635     if (err) {
636         error_propagate(errp, err);
637         return;
638     }
639     sysbus_connect_irq(SYS_BUS_DEVICE(&s->timer0), 0,
640                        armsse_get_common_irq_in(s, 3));
641     mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->timer0), 0);
642     object_property_set_link(OBJECT(&s->apb_ppc0), OBJECT(mr), "port[0]", &err);
643     if (err) {
644         error_propagate(errp, err);
645         return;
646     }
647 
648     qdev_prop_set_uint32(DEVICE(&s->timer1), "pclk-frq", s->mainclk_frq);
649     object_property_set_bool(OBJECT(&s->timer1), true, "realized", &err);
650     if (err) {
651         error_propagate(errp, err);
652         return;
653     }
654     sysbus_connect_irq(SYS_BUS_DEVICE(&s->timer1), 0,
655                        armsse_get_common_irq_in(s, 4));
656     mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->timer1), 0);
657     object_property_set_link(OBJECT(&s->apb_ppc0), OBJECT(mr), "port[1]", &err);
658     if (err) {
659         error_propagate(errp, err);
660         return;
661     }
662 
663 
664     qdev_prop_set_uint32(DEVICE(&s->dualtimer), "pclk-frq", s->mainclk_frq);
665     object_property_set_bool(OBJECT(&s->dualtimer), true, "realized", &err);
666     if (err) {
667         error_propagate(errp, err);
668         return;
669     }
670     sysbus_connect_irq(SYS_BUS_DEVICE(&s->dualtimer), 0,
671                        armsse_get_common_irq_in(s, 5));
672     mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->dualtimer), 0);
673     object_property_set_link(OBJECT(&s->apb_ppc0), OBJECT(mr), "port[2]", &err);
674     if (err) {
675         error_propagate(errp, err);
676         return;
677     }
678 
679     if (info->has_mhus) {
680         for (i = 0; i < ARRAY_SIZE(s->mhu); i++) {
681             char *name = g_strdup_printf("MHU%d", i);
682             char *port = g_strdup_printf("port[%d]", i + 3);
683 
684             qdev_prop_set_string(DEVICE(&s->mhu[i]), "name", name);
685             qdev_prop_set_uint64(DEVICE(&s->mhu[i]), "size", 0x1000);
686             object_property_set_bool(OBJECT(&s->mhu[i]), true,
687                                      "realized", &err);
688             if (err) {
689                 error_propagate(errp, err);
690                 return;
691             }
692             mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->mhu[i]), 0);
693             object_property_set_link(OBJECT(&s->apb_ppc0), OBJECT(mr),
694                                      port, &err);
695             if (err) {
696                 error_propagate(errp, err);
697                 return;
698             }
699             g_free(name);
700             g_free(port);
701         }
702     }
703 
704     object_property_set_bool(OBJECT(&s->apb_ppc0), true, "realized", &err);
705     if (err) {
706         error_propagate(errp, err);
707         return;
708     }
709 
710     sbd_apb_ppc0 = SYS_BUS_DEVICE(&s->apb_ppc0);
711     dev_apb_ppc0 = DEVICE(&s->apb_ppc0);
712 
713     mr = sysbus_mmio_get_region(sbd_apb_ppc0, 0);
714     memory_region_add_subregion(&s->container, 0x40000000, mr);
715     mr = sysbus_mmio_get_region(sbd_apb_ppc0, 1);
716     memory_region_add_subregion(&s->container, 0x40001000, mr);
717     mr = sysbus_mmio_get_region(sbd_apb_ppc0, 2);
718     memory_region_add_subregion(&s->container, 0x40002000, mr);
719     if (info->has_mhus) {
720         mr = sysbus_mmio_get_region(sbd_apb_ppc0, 3);
721         memory_region_add_subregion(&s->container, 0x40003000, mr);
722         mr = sysbus_mmio_get_region(sbd_apb_ppc0, 4);
723         memory_region_add_subregion(&s->container, 0x40004000, mr);
724     }
725     for (i = 0; i < IOTS_APB_PPC0_NUM_PORTS; i++) {
726         qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_nonsec", i,
727                                     qdev_get_gpio_in_named(dev_apb_ppc0,
728                                                            "cfg_nonsec", i));
729         qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_ap", i,
730                                     qdev_get_gpio_in_named(dev_apb_ppc0,
731                                                            "cfg_ap", i));
732     }
733     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_irq_enable", 0,
734                                 qdev_get_gpio_in_named(dev_apb_ppc0,
735                                                        "irq_enable", 0));
736     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_irq_clear", 0,
737                                 qdev_get_gpio_in_named(dev_apb_ppc0,
738                                                        "irq_clear", 0));
739     qdev_connect_gpio_out(dev_splitter, 0,
740                           qdev_get_gpio_in_named(dev_apb_ppc0,
741                                                  "cfg_sec_resp", 0));
742 
743     /* All the PPC irq lines (from the 2 internal PPCs and the 8 external
744      * ones) are sent individually to the security controller, and also
745      * ORed together to give a single combined PPC interrupt to the NVIC.
746      */
747     object_property_set_int(OBJECT(&s->ppc_irq_orgate),
748                             NUM_PPCS, "num-lines", &err);
749     if (err) {
750         error_propagate(errp, err);
751         return;
752     }
753     object_property_set_bool(OBJECT(&s->ppc_irq_orgate), true,
754                              "realized", &err);
755     if (err) {
756         error_propagate(errp, err);
757         return;
758     }
759     qdev_connect_gpio_out(DEVICE(&s->ppc_irq_orgate), 0,
760                           armsse_get_common_irq_in(s, 10));
761 
762     /* 0x40010000 .. 0x4001ffff: private CPU region: unused in IoTKit */
763 
764     /* 0x40020000 .. 0x4002ffff : ARMSSE system control peripheral region */
765     /* Devices behind APB PPC1:
766      *   0x4002f000: S32K timer
767      */
768     qdev_prop_set_uint32(DEVICE(&s->s32ktimer), "pclk-frq", S32KCLK);
769     object_property_set_bool(OBJECT(&s->s32ktimer), true, "realized", &err);
770     if (err) {
771         error_propagate(errp, err);
772         return;
773     }
774     sysbus_connect_irq(SYS_BUS_DEVICE(&s->s32ktimer), 0,
775                        armsse_get_common_irq_in(s, 2));
776     mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->s32ktimer), 0);
777     object_property_set_link(OBJECT(&s->apb_ppc1), OBJECT(mr), "port[0]", &err);
778     if (err) {
779         error_propagate(errp, err);
780         return;
781     }
782 
783     object_property_set_bool(OBJECT(&s->apb_ppc1), true, "realized", &err);
784     if (err) {
785         error_propagate(errp, err);
786         return;
787     }
788     mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->apb_ppc1), 0);
789     memory_region_add_subregion(&s->container, 0x4002f000, mr);
790 
791     dev_apb_ppc1 = DEVICE(&s->apb_ppc1);
792     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_nonsec", 0,
793                                 qdev_get_gpio_in_named(dev_apb_ppc1,
794                                                        "cfg_nonsec", 0));
795     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_ap", 0,
796                                 qdev_get_gpio_in_named(dev_apb_ppc1,
797                                                        "cfg_ap", 0));
798     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_irq_enable", 0,
799                                 qdev_get_gpio_in_named(dev_apb_ppc1,
800                                                        "irq_enable", 0));
801     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_irq_clear", 0,
802                                 qdev_get_gpio_in_named(dev_apb_ppc1,
803                                                        "irq_clear", 0));
804     qdev_connect_gpio_out(dev_splitter, 1,
805                           qdev_get_gpio_in_named(dev_apb_ppc1,
806                                                  "cfg_sec_resp", 0));
807 
808     object_property_set_int(OBJECT(&s->sysinfo), info->sys_version,
809                             "SYS_VERSION", &err);
810     if (err) {
811         error_propagate(errp, err);
812         return;
813     }
814     object_property_set_int(OBJECT(&s->sysinfo),
815                             armsse_sys_config_value(s, info),
816                             "SYS_CONFIG", &err);
817     if (err) {
818         error_propagate(errp, err);
819         return;
820     }
821     object_property_set_bool(OBJECT(&s->sysinfo), true, "realized", &err);
822     if (err) {
823         error_propagate(errp, err);
824         return;
825     }
826     /* System information registers */
827     sysbus_mmio_map(SYS_BUS_DEVICE(&s->sysinfo), 0, 0x40020000);
828     /* System control registers */
829     object_property_set_bool(OBJECT(&s->sysctl), true, "realized", &err);
830     if (err) {
831         error_propagate(errp, err);
832         return;
833     }
834     sysbus_mmio_map(SYS_BUS_DEVICE(&s->sysctl), 0, 0x50021000);
835 
836     /* This OR gate wires together outputs from the secure watchdogs to NMI */
837     object_property_set_int(OBJECT(&s->nmi_orgate), 2, "num-lines", &err);
838     if (err) {
839         error_propagate(errp, err);
840         return;
841     }
842     object_property_set_bool(OBJECT(&s->nmi_orgate), true, "realized", &err);
843     if (err) {
844         error_propagate(errp, err);
845         return;
846     }
847     qdev_connect_gpio_out(DEVICE(&s->nmi_orgate), 0,
848                           qdev_get_gpio_in_named(DEVICE(&s->armv7m), "NMI", 0));
849 
850     qdev_prop_set_uint32(DEVICE(&s->s32kwatchdog), "wdogclk-frq", S32KCLK);
851     object_property_set_bool(OBJECT(&s->s32kwatchdog), true, "realized", &err);
852     if (err) {
853         error_propagate(errp, err);
854         return;
855     }
856     sysbus_connect_irq(SYS_BUS_DEVICE(&s->s32kwatchdog), 0,
857                        qdev_get_gpio_in(DEVICE(&s->nmi_orgate), 0));
858     sysbus_mmio_map(SYS_BUS_DEVICE(&s->s32kwatchdog), 0, 0x5002e000);
859 
860     /* 0x40080000 .. 0x4008ffff : ARMSSE second Base peripheral region */
861 
862     qdev_prop_set_uint32(DEVICE(&s->nswatchdog), "wdogclk-frq", s->mainclk_frq);
863     object_property_set_bool(OBJECT(&s->nswatchdog), true, "realized", &err);
864     if (err) {
865         error_propagate(errp, err);
866         return;
867     }
868     sysbus_connect_irq(SYS_BUS_DEVICE(&s->nswatchdog), 0,
869                        armsse_get_common_irq_in(s, 1));
870     sysbus_mmio_map(SYS_BUS_DEVICE(&s->nswatchdog), 0, 0x40081000);
871 
872     qdev_prop_set_uint32(DEVICE(&s->swatchdog), "wdogclk-frq", s->mainclk_frq);
873     object_property_set_bool(OBJECT(&s->swatchdog), true, "realized", &err);
874     if (err) {
875         error_propagate(errp, err);
876         return;
877     }
878     sysbus_connect_irq(SYS_BUS_DEVICE(&s->swatchdog), 0,
879                        qdev_get_gpio_in(DEVICE(&s->nmi_orgate), 1));
880     sysbus_mmio_map(SYS_BUS_DEVICE(&s->swatchdog), 0, 0x50081000);
881 
882     for (i = 0; i < ARRAY_SIZE(s->ppc_irq_splitter); i++) {
883         Object *splitter = OBJECT(&s->ppc_irq_splitter[i]);
884 
885         object_property_set_int(splitter, 2, "num-lines", &err);
886         if (err) {
887             error_propagate(errp, err);
888             return;
889         }
890         object_property_set_bool(splitter, true, "realized", &err);
891         if (err) {
892             error_propagate(errp, err);
893             return;
894         }
895     }
896 
897     for (i = 0; i < IOTS_NUM_AHB_EXP_PPC; i++) {
898         char *ppcname = g_strdup_printf("ahb_ppcexp%d", i);
899 
900         armsse_forward_ppc(s, ppcname, i);
901         g_free(ppcname);
902     }
903 
904     for (i = 0; i < IOTS_NUM_APB_EXP_PPC; i++) {
905         char *ppcname = g_strdup_printf("apb_ppcexp%d", i);
906 
907         armsse_forward_ppc(s, ppcname, i + IOTS_NUM_AHB_EXP_PPC);
908         g_free(ppcname);
909     }
910 
911     for (i = NUM_EXTERNAL_PPCS; i < NUM_PPCS; i++) {
912         /* Wire up IRQ splitter for internal PPCs */
913         DeviceState *devs = DEVICE(&s->ppc_irq_splitter[i]);
914         char *gpioname = g_strdup_printf("apb_ppc%d_irq_status",
915                                          i - NUM_EXTERNAL_PPCS);
916         TZPPC *ppc = (i == NUM_EXTERNAL_PPCS) ? &s->apb_ppc0 : &s->apb_ppc1;
917 
918         qdev_connect_gpio_out(devs, 0,
919                               qdev_get_gpio_in_named(dev_secctl, gpioname, 0));
920         qdev_connect_gpio_out(devs, 1,
921                               qdev_get_gpio_in(DEVICE(&s->ppc_irq_orgate), i));
922         qdev_connect_gpio_out_named(DEVICE(ppc), "irq", 0,
923                                     qdev_get_gpio_in(devs, 0));
924         g_free(gpioname);
925     }
926 
927     /* Wire up the splitters for the MPC IRQs */
928     for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
929         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
930         DeviceState *dev_splitter = DEVICE(splitter);
931 
932         object_property_set_int(OBJECT(splitter), 2, "num-lines", &err);
933         if (err) {
934             error_propagate(errp, err);
935             return;
936         }
937         object_property_set_bool(OBJECT(splitter), true, "realized", &err);
938         if (err) {
939             error_propagate(errp, err);
940             return;
941         }
942 
943         if (i < IOTS_NUM_EXP_MPC) {
944             /* Splitter input is from GPIO input line */
945             s->mpcexp_status_in[i] = qdev_get_gpio_in(dev_splitter, 0);
946             qdev_connect_gpio_out(dev_splitter, 0,
947                                   qdev_get_gpio_in_named(dev_secctl,
948                                                          "mpcexp_status", i));
949         } else {
950             /* Splitter input is from our own MPC */
951             qdev_connect_gpio_out_named(DEVICE(&s->mpc[i - IOTS_NUM_EXP_MPC]),
952                                         "irq", 0,
953                                         qdev_get_gpio_in(dev_splitter, 0));
954             qdev_connect_gpio_out(dev_splitter, 0,
955                                   qdev_get_gpio_in_named(dev_secctl,
956                                                          "mpc_status", 0));
957         }
958 
959         qdev_connect_gpio_out(dev_splitter, 1,
960                               qdev_get_gpio_in(DEVICE(&s->mpc_irq_orgate), i));
961     }
962     /* Create GPIO inputs which will pass the line state for our
963      * mpcexp_irq inputs to the correct splitter devices.
964      */
965     qdev_init_gpio_in_named(dev, armsse_mpcexp_status, "mpcexp_status",
966                             IOTS_NUM_EXP_MPC);
967 
968     armsse_forward_sec_resp_cfg(s);
969 
970     /* Forward the MSC related signals */
971     qdev_pass_gpios(dev_secctl, dev, "mscexp_status");
972     qdev_pass_gpios(dev_secctl, dev, "mscexp_clear");
973     qdev_pass_gpios(dev_secctl, dev, "mscexp_ns");
974     qdev_connect_gpio_out_named(dev_secctl, "msc_irq", 0,
975                                 armsse_get_common_irq_in(s, 11));
976 
977     /*
978      * Expose our container region to the board model; this corresponds
979      * to the AHB Slave Expansion ports which allow bus master devices
980      * (eg DMA controllers) in the board model to make transactions into
981      * devices in the ARMSSE.
982      */
983     sysbus_init_mmio(SYS_BUS_DEVICE(s), &s->container);
984 
985     system_clock_scale = NANOSECONDS_PER_SECOND / s->mainclk_frq;
986 }
987 
988 static void armsse_idau_check(IDAUInterface *ii, uint32_t address,
989                               int *iregion, bool *exempt, bool *ns, bool *nsc)
990 {
991     /*
992      * For ARMSSE systems the IDAU responses are simple logical functions
993      * of the address bits. The NSC attribute is guest-adjustable via the
994      * NSCCFG register in the security controller.
995      */
996     ARMSSE *s = ARMSSE(ii);
997     int region = extract32(address, 28, 4);
998 
999     *ns = !(region & 1);
1000     *nsc = (region == 1 && (s->nsccfg & 1)) || (region == 3 && (s->nsccfg & 2));
1001     /* 0xe0000000..0xe00fffff and 0xf0000000..0xf00fffff are exempt */
1002     *exempt = (address & 0xeff00000) == 0xe0000000;
1003     *iregion = region;
1004 }
1005 
1006 static const VMStateDescription armsse_vmstate = {
1007     .name = "iotkit",
1008     .version_id = 1,
1009     .minimum_version_id = 1,
1010     .fields = (VMStateField[]) {
1011         VMSTATE_UINT32(nsccfg, ARMSSE),
1012         VMSTATE_END_OF_LIST()
1013     }
1014 };
1015 
1016 static Property armsse_properties[] = {
1017     DEFINE_PROP_LINK("memory", ARMSSE, board_memory, TYPE_MEMORY_REGION,
1018                      MemoryRegion *),
1019     DEFINE_PROP_UINT32("EXP_NUMIRQ", ARMSSE, exp_numirq, 64),
1020     DEFINE_PROP_UINT32("MAINCLK", ARMSSE, mainclk_frq, 0),
1021     DEFINE_PROP_UINT32("SRAM_ADDR_WIDTH", ARMSSE, sram_addr_width, 15),
1022     DEFINE_PROP_END_OF_LIST()
1023 };
1024 
1025 static void armsse_reset(DeviceState *dev)
1026 {
1027     ARMSSE *s = ARMSSE(dev);
1028 
1029     s->nsccfg = 0;
1030 }
1031 
1032 static void armsse_class_init(ObjectClass *klass, void *data)
1033 {
1034     DeviceClass *dc = DEVICE_CLASS(klass);
1035     IDAUInterfaceClass *iic = IDAU_INTERFACE_CLASS(klass);
1036     ARMSSEClass *asc = ARMSSE_CLASS(klass);
1037 
1038     dc->realize = armsse_realize;
1039     dc->vmsd = &armsse_vmstate;
1040     dc->props = armsse_properties;
1041     dc->reset = armsse_reset;
1042     iic->check = armsse_idau_check;
1043     asc->info = data;
1044 }
1045 
1046 static const TypeInfo armsse_info = {
1047     .name = TYPE_ARMSSE,
1048     .parent = TYPE_SYS_BUS_DEVICE,
1049     .instance_size = sizeof(ARMSSE),
1050     .instance_init = armsse_init,
1051     .abstract = true,
1052     .interfaces = (InterfaceInfo[]) {
1053         { TYPE_IDAU_INTERFACE },
1054         { }
1055     }
1056 };
1057 
1058 static void armsse_register_types(void)
1059 {
1060     int i;
1061 
1062     type_register_static(&armsse_info);
1063 
1064     for (i = 0; i < ARRAY_SIZE(armsse_variants); i++) {
1065         TypeInfo ti = {
1066             .name = armsse_variants[i].name,
1067             .parent = TYPE_ARMSSE,
1068             .class_init = armsse_class_init,
1069             .class_data = (void *)&armsse_variants[i],
1070         };
1071         type_register(&ti);
1072     }
1073 }
1074 
1075 type_init(armsse_register_types);
1076