xref: /qemu/hw/arm/armsse.c (revision a459e849aa2b683fac20fc72db9b4b1d90a4b4b9)
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 "qemu/module.h"
15 #include "qemu/bitops.h"
16 #include "qapi/error.h"
17 #include "trace.h"
18 #include "hw/sysbus.h"
19 #include "migration/vmstate.h"
20 #include "hw/registerfields.h"
21 #include "hw/arm/armsse.h"
22 #include "hw/arm/armsse-version.h"
23 #include "hw/arm/boot.h"
24 #include "hw/irq.h"
25 #include "hw/qdev-clock.h"
26 
27 /*
28  * The SSE-300 puts some devices in different places to the
29  * SSE-200 (and original IoTKit). We use an array of these structs
30  * to define how each variant lays out these devices. (Parts of the
31  * SoC that are the same for all variants aren't handled via these
32  * data structures.)
33  */
34 
35 #define NO_IRQ -1
36 #define NO_PPC -1
37 /*
38  * Special values for ARMSSEDeviceInfo::irq to indicate that this
39  * device uses one of the inputs to the OR gate that feeds into the
40  * CPU NMI input.
41  */
42 #define NMI_0 10000
43 #define NMI_1 10001
44 
45 typedef struct ARMSSEDeviceInfo {
46     const char *name; /* name to use for the QOM object; NULL terminates list */
47     const char *type; /* QOM type name */
48     unsigned int index; /* Which of the N devices of this type is this ? */
49     hwaddr addr;
50     hwaddr size; /* only needed for TYPE_UNIMPLEMENTED_DEVICE */
51     int ppc; /* Index of APB PPC this device is wired up to, or NO_PPC */
52     int ppc_port; /* Port number of this device on the PPC */
53     int irq; /* NO_IRQ, or 0..NUM_SSE_IRQS-1, or NMI_0 or NMI_1 */
54     bool slowclk; /* true if device uses the slow 32KHz clock */
55 } ARMSSEDeviceInfo;
56 
57 struct ARMSSEInfo {
58     const char *name;
59     uint32_t sse_version;
60     int sram_banks;
61     int num_cpus;
62     uint32_t sys_version;
63     uint32_t iidr;
64     uint32_t cpuwait_rst;
65     bool has_mhus;
66     bool has_cachectrl;
67     bool has_cpusecctrl;
68     bool has_cpuid;
69     Property *props;
70     const ARMSSEDeviceInfo *devinfo;
71 };
72 
73 static Property iotkit_properties[] = {
74     DEFINE_PROP_LINK("memory", ARMSSE, board_memory, TYPE_MEMORY_REGION,
75                      MemoryRegion *),
76     DEFINE_PROP_UINT32("EXP_NUMIRQ", ARMSSE, exp_numirq, 64),
77     DEFINE_PROP_UINT32("SRAM_ADDR_WIDTH", ARMSSE, sram_addr_width, 15),
78     DEFINE_PROP_UINT32("init-svtor", ARMSSE, init_svtor, 0x10000000),
79     DEFINE_PROP_BOOL("CPU0_FPU", ARMSSE, cpu_fpu[0], true),
80     DEFINE_PROP_BOOL("CPU0_DSP", ARMSSE, cpu_dsp[0], true),
81     DEFINE_PROP_END_OF_LIST()
82 };
83 
84 static Property armsse_properties[] = {
85     DEFINE_PROP_LINK("memory", ARMSSE, board_memory, TYPE_MEMORY_REGION,
86                      MemoryRegion *),
87     DEFINE_PROP_UINT32("EXP_NUMIRQ", ARMSSE, exp_numirq, 64),
88     DEFINE_PROP_UINT32("SRAM_ADDR_WIDTH", ARMSSE, sram_addr_width, 15),
89     DEFINE_PROP_UINT32("init-svtor", ARMSSE, init_svtor, 0x10000000),
90     DEFINE_PROP_BOOL("CPU0_FPU", ARMSSE, cpu_fpu[0], false),
91     DEFINE_PROP_BOOL("CPU0_DSP", ARMSSE, cpu_dsp[0], false),
92     DEFINE_PROP_BOOL("CPU1_FPU", ARMSSE, cpu_fpu[1], true),
93     DEFINE_PROP_BOOL("CPU1_DSP", ARMSSE, cpu_dsp[1], true),
94     DEFINE_PROP_END_OF_LIST()
95 };
96 
97 static const ARMSSEDeviceInfo iotkit_devices[] = {
98     {
99         .name = "timer0",
100         .type = TYPE_CMSDK_APB_TIMER,
101         .index = 0,
102         .addr = 0x40000000,
103         .ppc = 0,
104         .ppc_port = 0,
105         .irq = 3,
106     },
107     {
108         .name = "timer1",
109         .type = TYPE_CMSDK_APB_TIMER,
110         .index = 1,
111         .addr = 0x40001000,
112         .ppc = 0,
113         .ppc_port = 1,
114         .irq = 4,
115     },
116     {
117         .name = "s32ktimer",
118         .type = TYPE_CMSDK_APB_TIMER,
119         .index = 2,
120         .addr = 0x4002f000,
121         .ppc = 1,
122         .ppc_port = 0,
123         .irq = 2,
124         .slowclk = true,
125     },
126     {
127         .name = "dualtimer",
128         .type = TYPE_CMSDK_APB_DUALTIMER,
129         .index = 0,
130         .addr = 0x40002000,
131         .ppc = 0,
132         .ppc_port = 2,
133         .irq = 5,
134     },
135     {
136         .name = "s32kwatchdog",
137         .type = TYPE_CMSDK_APB_WATCHDOG,
138         .index = 0,
139         .addr = 0x5002e000,
140         .ppc = NO_PPC,
141         .irq = NMI_0,
142         .slowclk = true,
143     },
144     {
145         .name = "nswatchdog",
146         .type = TYPE_CMSDK_APB_WATCHDOG,
147         .index = 1,
148         .addr = 0x40081000,
149         .ppc = NO_PPC,
150         .irq = 1,
151     },
152     {
153         .name = "swatchdog",
154         .type = TYPE_CMSDK_APB_WATCHDOG,
155         .index = 2,
156         .addr = 0x50081000,
157         .ppc = NO_PPC,
158         .irq = NMI_1,
159     },
160     {
161         .name = "armsse-sysinfo",
162         .type = TYPE_IOTKIT_SYSINFO,
163         .index = 0,
164         .addr = 0x40020000,
165         .ppc = NO_PPC,
166         .irq = NO_IRQ,
167     },
168     {
169         .name = "armsse-sysctl",
170         .type = TYPE_IOTKIT_SYSCTL,
171         .index = 0,
172         .addr = 0x50021000,
173         .ppc = NO_PPC,
174         .irq = NO_IRQ,
175     },
176     {
177         .name = NULL,
178     }
179 };
180 
181 static const ARMSSEDeviceInfo sse200_devices[] = {
182     {
183         .name = "timer0",
184         .type = TYPE_CMSDK_APB_TIMER,
185         .index = 0,
186         .addr = 0x40000000,
187         .ppc = 0,
188         .ppc_port = 0,
189         .irq = 3,
190     },
191     {
192         .name = "timer1",
193         .type = TYPE_CMSDK_APB_TIMER,
194         .index = 1,
195         .addr = 0x40001000,
196         .ppc = 0,
197         .ppc_port = 1,
198         .irq = 4,
199     },
200     {
201         .name = "s32ktimer",
202         .type = TYPE_CMSDK_APB_TIMER,
203         .index = 2,
204         .addr = 0x4002f000,
205         .ppc = 1,
206         .ppc_port = 0,
207         .irq = 2,
208         .slowclk = true,
209     },
210     {
211         .name = "dualtimer",
212         .type = TYPE_CMSDK_APB_DUALTIMER,
213         .index = 0,
214         .addr = 0x40002000,
215         .ppc = 0,
216         .ppc_port = 2,
217         .irq = 5,
218     },
219     {
220         .name = "s32kwatchdog",
221         .type = TYPE_CMSDK_APB_WATCHDOG,
222         .index = 0,
223         .addr = 0x5002e000,
224         .ppc = NO_PPC,
225         .irq = NMI_0,
226         .slowclk = true,
227     },
228     {
229         .name = "nswatchdog",
230         .type = TYPE_CMSDK_APB_WATCHDOG,
231         .index = 1,
232         .addr = 0x40081000,
233         .ppc = NO_PPC,
234         .irq = 1,
235     },
236     {
237         .name = "swatchdog",
238         .type = TYPE_CMSDK_APB_WATCHDOG,
239         .index = 2,
240         .addr = 0x50081000,
241         .ppc = NO_PPC,
242         .irq = NMI_1,
243     },
244     {
245         .name = "armsse-sysinfo",
246         .type = TYPE_IOTKIT_SYSINFO,
247         .index = 0,
248         .addr = 0x40020000,
249         .ppc = NO_PPC,
250         .irq = NO_IRQ,
251     },
252     {
253         .name = "armsse-sysctl",
254         .type = TYPE_IOTKIT_SYSCTL,
255         .index = 0,
256         .addr = 0x50021000,
257         .ppc = NO_PPC,
258         .irq = NO_IRQ,
259     },
260     {
261         .name = "CPU0CORE_PPU",
262         .type = TYPE_UNIMPLEMENTED_DEVICE,
263         .index = 0,
264         .addr = 0x50023000,
265         .size = 0x1000,
266         .ppc = NO_PPC,
267         .irq = NO_IRQ,
268     },
269     {
270         .name = "CPU1CORE_PPU",
271         .type = TYPE_UNIMPLEMENTED_DEVICE,
272         .index = 1,
273         .addr = 0x50025000,
274         .size = 0x1000,
275         .ppc = NO_PPC,
276         .irq = NO_IRQ,
277     },
278     {
279         .name = "DBG_PPU",
280         .type = TYPE_UNIMPLEMENTED_DEVICE,
281         .index = 2,
282         .addr = 0x50029000,
283         .size = 0x1000,
284         .ppc = NO_PPC,
285         .irq = NO_IRQ,
286     },
287     {
288         .name = "RAM0_PPU",
289         .type = TYPE_UNIMPLEMENTED_DEVICE,
290         .index = 3,
291         .addr = 0x5002a000,
292         .size = 0x1000,
293         .ppc = NO_PPC,
294         .irq = NO_IRQ,
295     },
296     {
297         .name = "RAM1_PPU",
298         .type = TYPE_UNIMPLEMENTED_DEVICE,
299         .index = 4,
300         .addr = 0x5002b000,
301         .size = 0x1000,
302         .ppc = NO_PPC,
303         .irq = NO_IRQ,
304     },
305     {
306         .name = "RAM2_PPU",
307         .type = TYPE_UNIMPLEMENTED_DEVICE,
308         .index = 5,
309         .addr = 0x5002c000,
310         .size = 0x1000,
311         .ppc = NO_PPC,
312         .irq = NO_IRQ,
313     },
314     {
315         .name = "RAM3_PPU",
316         .type = TYPE_UNIMPLEMENTED_DEVICE,
317         .index = 6,
318         .addr = 0x5002d000,
319         .size = 0x1000,
320         .ppc = NO_PPC,
321         .irq = NO_IRQ,
322     },
323     {
324         .name = NULL,
325     }
326 };
327 
328 static const ARMSSEInfo armsse_variants[] = {
329     {
330         .name = TYPE_IOTKIT,
331         .sse_version = ARMSSE_IOTKIT,
332         .sram_banks = 1,
333         .num_cpus = 1,
334         .sys_version = 0x41743,
335         .iidr = 0,
336         .cpuwait_rst = 0,
337         .has_mhus = false,
338         .has_cachectrl = false,
339         .has_cpusecctrl = false,
340         .has_cpuid = false,
341         .props = iotkit_properties,
342         .devinfo = iotkit_devices,
343     },
344     {
345         .name = TYPE_SSE200,
346         .sse_version = ARMSSE_SSE200,
347         .sram_banks = 4,
348         .num_cpus = 2,
349         .sys_version = 0x22041743,
350         .iidr = 0,
351         .cpuwait_rst = 2,
352         .has_mhus = true,
353         .has_cachectrl = true,
354         .has_cpusecctrl = true,
355         .has_cpuid = true,
356         .props = armsse_properties,
357         .devinfo = sse200_devices,
358     },
359 };
360 
361 static uint32_t armsse_sys_config_value(ARMSSE *s, const ARMSSEInfo *info)
362 {
363     /* Return the SYS_CONFIG value for this SSE */
364     uint32_t sys_config;
365 
366     switch (info->sse_version) {
367     case ARMSSE_IOTKIT:
368         sys_config = 0;
369         sys_config = deposit32(sys_config, 0, 4, info->sram_banks);
370         sys_config = deposit32(sys_config, 4, 4, s->sram_addr_width - 12);
371         break;
372     case ARMSSE_SSE200:
373         sys_config = 0;
374         sys_config = deposit32(sys_config, 0, 4, info->sram_banks);
375         sys_config = deposit32(sys_config, 4, 5, s->sram_addr_width);
376         sys_config = deposit32(sys_config, 24, 4, 2);
377         if (info->num_cpus > 1) {
378             sys_config = deposit32(sys_config, 10, 1, 1);
379             sys_config = deposit32(sys_config, 20, 4, info->sram_banks - 1);
380             sys_config = deposit32(sys_config, 28, 4, 2);
381         }
382         break;
383     case ARMSSE_SSE300:
384         sys_config = 0;
385         sys_config = deposit32(sys_config, 0, 4, info->sram_banks);
386         sys_config = deposit32(sys_config, 4, 5, s->sram_addr_width);
387         sys_config = deposit32(sys_config, 16, 3, 3); /* CPU0 = Cortex-M55 */
388         break;
389     default:
390         g_assert_not_reached();
391     }
392     return sys_config;
393 }
394 
395 /* Clock frequency in HZ of the 32KHz "slow clock" */
396 #define S32KCLK (32 * 1000)
397 
398 /* Is internal IRQ n shared between CPUs in a multi-core SSE ? */
399 static bool irq_is_common[32] = {
400     [0 ... 5] = true,
401     /* 6, 7: per-CPU MHU interrupts */
402     [8 ... 12] = true,
403     /* 13: per-CPU icache interrupt */
404     /* 14: reserved */
405     [15 ... 20] = true,
406     /* 21: reserved */
407     [22 ... 26] = true,
408     /* 27: reserved */
409     /* 28, 29: per-CPU CTI interrupts */
410     /* 30, 31: reserved */
411 };
412 
413 /*
414  * Create an alias region in @container of @size bytes starting at @base
415  * which mirrors the memory starting at @orig.
416  */
417 static void make_alias(ARMSSE *s, MemoryRegion *mr, MemoryRegion *container,
418                        const char *name, hwaddr base, hwaddr size, hwaddr orig)
419 {
420     memory_region_init_alias(mr, NULL, name, container, orig, size);
421     /* The alias is even lower priority than unimplemented_device regions */
422     memory_region_add_subregion_overlap(container, base, mr, -1500);
423 }
424 
425 static void irq_status_forwarder(void *opaque, int n, int level)
426 {
427     qemu_irq destirq = opaque;
428 
429     qemu_set_irq(destirq, level);
430 }
431 
432 static void nsccfg_handler(void *opaque, int n, int level)
433 {
434     ARMSSE *s = ARM_SSE(opaque);
435 
436     s->nsccfg = level;
437 }
438 
439 static void armsse_forward_ppc(ARMSSE *s, const char *ppcname, int ppcnum)
440 {
441     /* Each of the 4 AHB and 4 APB PPCs that might be present in a
442      * system using the ARMSSE has a collection of control lines which
443      * are provided by the security controller and which we want to
444      * expose as control lines on the ARMSSE device itself, so the
445      * code using the ARMSSE can wire them up to the PPCs.
446      */
447     SplitIRQ *splitter = &s->ppc_irq_splitter[ppcnum];
448     DeviceState *armssedev = DEVICE(s);
449     DeviceState *dev_secctl = DEVICE(&s->secctl);
450     DeviceState *dev_splitter = DEVICE(splitter);
451     char *name;
452 
453     name = g_strdup_printf("%s_nonsec", ppcname);
454     qdev_pass_gpios(dev_secctl, armssedev, name);
455     g_free(name);
456     name = g_strdup_printf("%s_ap", ppcname);
457     qdev_pass_gpios(dev_secctl, armssedev, name);
458     g_free(name);
459     name = g_strdup_printf("%s_irq_enable", ppcname);
460     qdev_pass_gpios(dev_secctl, armssedev, name);
461     g_free(name);
462     name = g_strdup_printf("%s_irq_clear", ppcname);
463     qdev_pass_gpios(dev_secctl, armssedev, name);
464     g_free(name);
465 
466     /* irq_status is a little more tricky, because we need to
467      * split it so we can send it both to the security controller
468      * and to our OR gate for the NVIC interrupt line.
469      * Connect up the splitter's outputs, and create a GPIO input
470      * which will pass the line state to the input splitter.
471      */
472     name = g_strdup_printf("%s_irq_status", ppcname);
473     qdev_connect_gpio_out(dev_splitter, 0,
474                           qdev_get_gpio_in_named(dev_secctl,
475                                                  name, 0));
476     qdev_connect_gpio_out(dev_splitter, 1,
477                           qdev_get_gpio_in(DEVICE(&s->ppc_irq_orgate), ppcnum));
478     s->irq_status_in[ppcnum] = qdev_get_gpio_in(dev_splitter, 0);
479     qdev_init_gpio_in_named_with_opaque(armssedev, irq_status_forwarder,
480                                         s->irq_status_in[ppcnum], name, 1);
481     g_free(name);
482 }
483 
484 static void armsse_forward_sec_resp_cfg(ARMSSE *s)
485 {
486     /* Forward the 3rd output from the splitter device as a
487      * named GPIO output of the armsse object.
488      */
489     DeviceState *dev = DEVICE(s);
490     DeviceState *dev_splitter = DEVICE(&s->sec_resp_splitter);
491 
492     qdev_init_gpio_out_named(dev, &s->sec_resp_cfg, "sec_resp_cfg", 1);
493     s->sec_resp_cfg_in = qemu_allocate_irq(irq_status_forwarder,
494                                            s->sec_resp_cfg, 1);
495     qdev_connect_gpio_out(dev_splitter, 2, s->sec_resp_cfg_in);
496 }
497 
498 static void armsse_mainclk_update(void *opaque, ClockEvent event)
499 {
500     ARMSSE *s = ARM_SSE(opaque);
501 
502     /*
503      * Set system_clock_scale from our Clock input; this is what
504      * controls the tick rate of the CPU SysTick timer.
505      */
506     system_clock_scale = clock_ticks_to_ns(s->mainclk, 1);
507 }
508 
509 static void armsse_init(Object *obj)
510 {
511     ARMSSE *s = ARM_SSE(obj);
512     ARMSSEClass *asc = ARM_SSE_GET_CLASS(obj);
513     const ARMSSEInfo *info = asc->info;
514     const ARMSSEDeviceInfo *devinfo;
515     int i;
516 
517     assert(info->sram_banks <= MAX_SRAM_BANKS);
518     assert(info->num_cpus <= SSE_MAX_CPUS);
519 
520     s->mainclk = qdev_init_clock_in(DEVICE(s), "MAINCLK",
521                                     armsse_mainclk_update, s, ClockUpdate);
522     s->s32kclk = qdev_init_clock_in(DEVICE(s), "S32KCLK", NULL, NULL, 0);
523 
524     memory_region_init(&s->container, obj, "armsse-container", UINT64_MAX);
525 
526     for (i = 0; i < info->num_cpus; i++) {
527         /*
528          * We put each CPU in its own cluster as they are logically
529          * distinct and may be configured differently.
530          */
531         char *name;
532 
533         name = g_strdup_printf("cluster%d", i);
534         object_initialize_child(obj, name, &s->cluster[i], TYPE_CPU_CLUSTER);
535         qdev_prop_set_uint32(DEVICE(&s->cluster[i]), "cluster-id", i);
536         g_free(name);
537 
538         name = g_strdup_printf("armv7m%d", i);
539         object_initialize_child(OBJECT(&s->cluster[i]), name, &s->armv7m[i],
540                                 TYPE_ARMV7M);
541         qdev_prop_set_string(DEVICE(&s->armv7m[i]), "cpu-type",
542                              ARM_CPU_TYPE_NAME("cortex-m33"));
543         g_free(name);
544         name = g_strdup_printf("arm-sse-cpu-container%d", i);
545         memory_region_init(&s->cpu_container[i], obj, name, UINT64_MAX);
546         g_free(name);
547         if (i > 0) {
548             name = g_strdup_printf("arm-sse-container-alias%d", i);
549             memory_region_init_alias(&s->container_alias[i - 1], obj,
550                                      name, &s->container, 0, UINT64_MAX);
551             g_free(name);
552         }
553     }
554 
555     for (devinfo = info->devinfo; devinfo->name; devinfo++) {
556         assert(devinfo->ppc == NO_PPC || devinfo->ppc < ARRAY_SIZE(s->apb_ppc));
557         if (!strcmp(devinfo->type, TYPE_CMSDK_APB_TIMER)) {
558             assert(devinfo->index < ARRAY_SIZE(s->timer));
559             object_initialize_child(obj, devinfo->name,
560                                     &s->timer[devinfo->index],
561                                     TYPE_CMSDK_APB_TIMER);
562         } else if (!strcmp(devinfo->type, TYPE_CMSDK_APB_DUALTIMER)) {
563             assert(devinfo->index == 0);
564             object_initialize_child(obj, devinfo->name, &s->dualtimer,
565                                     TYPE_CMSDK_APB_DUALTIMER);
566         } else if (!strcmp(devinfo->type, TYPE_CMSDK_APB_WATCHDOG)) {
567             assert(devinfo->index < ARRAY_SIZE(s->cmsdk_watchdog));
568             object_initialize_child(obj, devinfo->name,
569                                     &s->cmsdk_watchdog[devinfo->index],
570                                     TYPE_CMSDK_APB_WATCHDOG);
571         } else if (!strcmp(devinfo->type, TYPE_IOTKIT_SYSINFO)) {
572             assert(devinfo->index == 0);
573             object_initialize_child(obj, devinfo->name, &s->sysinfo,
574                                     TYPE_IOTKIT_SYSINFO);
575         } else if (!strcmp(devinfo->type, TYPE_IOTKIT_SYSCTL)) {
576             assert(devinfo->index == 0);
577             object_initialize_child(obj, devinfo->name, &s->sysctl,
578                                     TYPE_IOTKIT_SYSCTL);
579         } else if (!strcmp(devinfo->type, TYPE_UNIMPLEMENTED_DEVICE)) {
580             assert(devinfo->index < ARRAY_SIZE(s->unimp));
581             object_initialize_child(obj, devinfo->name,
582                                     &s->unimp[devinfo->index],
583                                     TYPE_UNIMPLEMENTED_DEVICE);
584         } else {
585             g_assert_not_reached();
586         }
587     }
588 
589     object_initialize_child(obj, "secctl", &s->secctl, TYPE_IOTKIT_SECCTL);
590 
591     for (i = 0; i < ARRAY_SIZE(s->apb_ppc); i++) {
592         g_autofree char *name = g_strdup_printf("apb-ppc%d", i);
593         object_initialize_child(obj, name, &s->apb_ppc[i], TYPE_TZ_PPC);
594     }
595 
596     for (i = 0; i < info->sram_banks; i++) {
597         char *name = g_strdup_printf("mpc%d", i);
598         object_initialize_child(obj, name, &s->mpc[i], TYPE_TZ_MPC);
599         g_free(name);
600     }
601     object_initialize_child(obj, "mpc-irq-orgate", &s->mpc_irq_orgate,
602                             TYPE_OR_IRQ);
603 
604     for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
605         char *name = g_strdup_printf("mpc-irq-splitter-%d", i);
606         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
607 
608         object_initialize_child(obj, name, splitter, TYPE_SPLIT_IRQ);
609         g_free(name);
610     }
611 
612     if (info->has_mhus) {
613         object_initialize_child(obj, "mhu0", &s->mhu[0], TYPE_ARMSSE_MHU);
614         object_initialize_child(obj, "mhu1", &s->mhu[1], TYPE_ARMSSE_MHU);
615     }
616     if (info->has_cachectrl) {
617         for (i = 0; i < info->num_cpus; i++) {
618             char *name = g_strdup_printf("cachectrl%d", i);
619 
620             object_initialize_child(obj, name, &s->cachectrl[i],
621                                     TYPE_UNIMPLEMENTED_DEVICE);
622             g_free(name);
623         }
624     }
625     if (info->has_cpusecctrl) {
626         for (i = 0; i < info->num_cpus; i++) {
627             char *name = g_strdup_printf("cpusecctrl%d", i);
628 
629             object_initialize_child(obj, name, &s->cpusecctrl[i],
630                                     TYPE_UNIMPLEMENTED_DEVICE);
631             g_free(name);
632         }
633     }
634     if (info->has_cpuid) {
635         for (i = 0; i < info->num_cpus; i++) {
636             char *name = g_strdup_printf("cpuid%d", i);
637 
638             object_initialize_child(obj, name, &s->cpuid[i],
639                                     TYPE_ARMSSE_CPUID);
640             g_free(name);
641         }
642     }
643     object_initialize_child(obj, "nmi-orgate", &s->nmi_orgate, TYPE_OR_IRQ);
644     object_initialize_child(obj, "ppc-irq-orgate", &s->ppc_irq_orgate,
645                             TYPE_OR_IRQ);
646     object_initialize_child(obj, "sec-resp-splitter", &s->sec_resp_splitter,
647                             TYPE_SPLIT_IRQ);
648     for (i = 0; i < ARRAY_SIZE(s->ppc_irq_splitter); i++) {
649         char *name = g_strdup_printf("ppc-irq-splitter-%d", i);
650         SplitIRQ *splitter = &s->ppc_irq_splitter[i];
651 
652         object_initialize_child(obj, name, splitter, TYPE_SPLIT_IRQ);
653         g_free(name);
654     }
655     if (info->num_cpus > 1) {
656         for (i = 0; i < ARRAY_SIZE(s->cpu_irq_splitter); i++) {
657             if (irq_is_common[i]) {
658                 char *name = g_strdup_printf("cpu-irq-splitter%d", i);
659                 SplitIRQ *splitter = &s->cpu_irq_splitter[i];
660 
661                 object_initialize_child(obj, name, splitter, TYPE_SPLIT_IRQ);
662                 g_free(name);
663             }
664         }
665     }
666 }
667 
668 static void armsse_exp_irq(void *opaque, int n, int level)
669 {
670     qemu_irq *irqarray = opaque;
671 
672     qemu_set_irq(irqarray[n], level);
673 }
674 
675 static void armsse_mpcexp_status(void *opaque, int n, int level)
676 {
677     ARMSSE *s = ARM_SSE(opaque);
678     qemu_set_irq(s->mpcexp_status_in[n], level);
679 }
680 
681 static qemu_irq armsse_get_common_irq_in(ARMSSE *s, int irqno)
682 {
683     /*
684      * Return a qemu_irq which can be used to signal IRQ n to
685      * all CPUs in the SSE.
686      */
687     ARMSSEClass *asc = ARM_SSE_GET_CLASS(s);
688     const ARMSSEInfo *info = asc->info;
689 
690     assert(irq_is_common[irqno]);
691 
692     if (info->num_cpus == 1) {
693         /* Only one CPU -- just connect directly to it */
694         return qdev_get_gpio_in(DEVICE(&s->armv7m[0]), irqno);
695     } else {
696         /* Connect to the splitter which feeds all CPUs */
697         return qdev_get_gpio_in(DEVICE(&s->cpu_irq_splitter[irqno]), 0);
698     }
699 }
700 
701 static void armsse_realize(DeviceState *dev, Error **errp)
702 {
703     ARMSSE *s = ARM_SSE(dev);
704     ARMSSEClass *asc = ARM_SSE_GET_CLASS(dev);
705     const ARMSSEInfo *info = asc->info;
706     const ARMSSEDeviceInfo *devinfo;
707     int i;
708     MemoryRegion *mr;
709     Error *err = NULL;
710     SysBusDevice *sbd_apb_ppc0;
711     SysBusDevice *sbd_secctl;
712     DeviceState *dev_apb_ppc0;
713     DeviceState *dev_apb_ppc1;
714     DeviceState *dev_secctl;
715     DeviceState *dev_splitter;
716     uint32_t addr_width_max;
717 
718     if (!s->board_memory) {
719         error_setg(errp, "memory property was not set");
720         return;
721     }
722 
723     if (!clock_has_source(s->mainclk)) {
724         error_setg(errp, "MAINCLK clock was not connected");
725     }
726     if (!clock_has_source(s->s32kclk)) {
727         error_setg(errp, "S32KCLK clock was not connected");
728     }
729 
730     assert(info->num_cpus <= SSE_MAX_CPUS);
731 
732     /* max SRAM_ADDR_WIDTH: 24 - log2(SRAM_NUM_BANK) */
733     assert(is_power_of_2(info->sram_banks));
734     addr_width_max = 24 - ctz32(info->sram_banks);
735     if (s->sram_addr_width < 1 || s->sram_addr_width > addr_width_max) {
736         error_setg(errp, "SRAM_ADDR_WIDTH must be between 1 and %d",
737                    addr_width_max);
738         return;
739     }
740 
741     /* Handling of which devices should be available only to secure
742      * code is usually done differently for M profile than for A profile.
743      * Instead of putting some devices only into the secure address space,
744      * devices exist in both address spaces but with hard-wired security
745      * permissions that will cause the CPU to fault for non-secure accesses.
746      *
747      * The ARMSSE has an IDAU (Implementation Defined Access Unit),
748      * which specifies hard-wired security permissions for different
749      * areas of the physical address space. For the ARMSSE IDAU, the
750      * top 4 bits of the physical address are the IDAU region ID, and
751      * if bit 28 (ie the lowest bit of the ID) is 0 then this is an NS
752      * region, otherwise it is an S region.
753      *
754      * The various devices and RAMs are generally all mapped twice,
755      * once into a region that the IDAU defines as secure and once
756      * into a non-secure region. They sit behind either a Memory
757      * Protection Controller (for RAM) or a Peripheral Protection
758      * Controller (for devices), which allow a more fine grained
759      * configuration of whether non-secure accesses are permitted.
760      *
761      * (The other place that guest software can configure security
762      * permissions is in the architected SAU (Security Attribution
763      * Unit), which is entirely inside the CPU. The IDAU can upgrade
764      * the security attributes for a region to more restrictive than
765      * the SAU specifies, but cannot downgrade them.)
766      *
767      * 0x10000000..0x1fffffff  alias of 0x00000000..0x0fffffff
768      * 0x20000000..0x2007ffff  32KB FPGA block RAM
769      * 0x30000000..0x3fffffff  alias of 0x20000000..0x2fffffff
770      * 0x40000000..0x4000ffff  base peripheral region 1
771      * 0x40010000..0x4001ffff  CPU peripherals (none for ARMSSE)
772      * 0x40020000..0x4002ffff  system control element peripherals
773      * 0x40080000..0x400fffff  base peripheral region 2
774      * 0x50000000..0x5fffffff  alias of 0x40000000..0x4fffffff
775      */
776 
777     memory_region_add_subregion_overlap(&s->container, 0, s->board_memory, -2);
778 
779     for (i = 0; i < info->num_cpus; i++) {
780         DeviceState *cpudev = DEVICE(&s->armv7m[i]);
781         Object *cpuobj = OBJECT(&s->armv7m[i]);
782         int j;
783         char *gpioname;
784 
785         qdev_prop_set_uint32(cpudev, "num-irq", s->exp_numirq + NUM_SSE_IRQS);
786         /*
787          * In real hardware the initial Secure VTOR is set from the INITSVTOR*
788          * registers in the IoT Kit System Control Register block. In QEMU
789          * we set the initial value here, and also the reset value of the
790          * sysctl register, from this object's QOM init-svtor property.
791          * If the guest changes the INITSVTOR* registers at runtime then the
792          * code in iotkit-sysctl.c will update the CPU init-svtor property
793          * (which will then take effect on the next CPU warm-reset).
794          *
795          * Note that typically a board using the SSE-200 will have a system
796          * control processor whose boot firmware initializes the INITSVTOR*
797          * registers before powering up the CPUs. QEMU doesn't emulate
798          * the control processor, so instead we behave in the way that the
799          * firmware does: the initial value should be set by the board code
800          * (using the init-svtor property on the ARMSSE object) to match
801          * whatever its firmware does.
802          */
803         qdev_prop_set_uint32(cpudev, "init-svtor", s->init_svtor);
804         /*
805          * CPUs start powered down if the corresponding bit in the CPUWAIT
806          * register is 1. In real hardware the CPUWAIT register reset value is
807          * a configurable property of the SSE-200 (via the CPUWAIT0_RST and
808          * CPUWAIT1_RST parameters), but since all the boards we care about
809          * start CPU0 and leave CPU1 powered off, we hard-code that in
810          * info->cpuwait_rst for now. We can add QOM properties for this
811          * later if necessary.
812          */
813         if (extract32(info->cpuwait_rst, i, 1)) {
814             if (!object_property_set_bool(cpuobj, "start-powered-off", true,
815                                           errp)) {
816                 return;
817             }
818         }
819         if (!s->cpu_fpu[i]) {
820             if (!object_property_set_bool(cpuobj, "vfp", false, errp)) {
821                 return;
822             }
823         }
824         if (!s->cpu_dsp[i]) {
825             if (!object_property_set_bool(cpuobj, "dsp", false, errp)) {
826                 return;
827             }
828         }
829 
830         if (i > 0) {
831             memory_region_add_subregion_overlap(&s->cpu_container[i], 0,
832                                                 &s->container_alias[i - 1], -1);
833         } else {
834             memory_region_add_subregion_overlap(&s->cpu_container[i], 0,
835                                                 &s->container, -1);
836         }
837         object_property_set_link(cpuobj, "memory",
838                                  OBJECT(&s->cpu_container[i]), &error_abort);
839         object_property_set_link(cpuobj, "idau", OBJECT(s), &error_abort);
840         if (!sysbus_realize(SYS_BUS_DEVICE(cpuobj), errp)) {
841             return;
842         }
843         /*
844          * The cluster must be realized after the armv7m container, as
845          * the container's CPU object is only created on realize, and the
846          * CPU must exist and have been parented into the cluster before
847          * the cluster is realized.
848          */
849         if (!qdev_realize(DEVICE(&s->cluster[i]), NULL, errp)) {
850             return;
851         }
852 
853         /* Connect EXP_IRQ/EXP_CPUn_IRQ GPIOs to the NVIC's lines 32 and up */
854         s->exp_irqs[i] = g_new(qemu_irq, s->exp_numirq);
855         for (j = 0; j < s->exp_numirq; j++) {
856             s->exp_irqs[i][j] = qdev_get_gpio_in(cpudev, j + NUM_SSE_IRQS);
857         }
858         if (i == 0) {
859             gpioname = g_strdup("EXP_IRQ");
860         } else {
861             gpioname = g_strdup_printf("EXP_CPU%d_IRQ", i);
862         }
863         qdev_init_gpio_in_named_with_opaque(dev, armsse_exp_irq,
864                                             s->exp_irqs[i],
865                                             gpioname, s->exp_numirq);
866         g_free(gpioname);
867     }
868 
869     /* Wire up the splitters that connect common IRQs to all CPUs */
870     if (info->num_cpus > 1) {
871         for (i = 0; i < ARRAY_SIZE(s->cpu_irq_splitter); i++) {
872             if (irq_is_common[i]) {
873                 Object *splitter = OBJECT(&s->cpu_irq_splitter[i]);
874                 DeviceState *devs = DEVICE(splitter);
875                 int cpunum;
876 
877                 if (!object_property_set_int(splitter, "num-lines",
878                                              info->num_cpus, errp)) {
879                     return;
880                 }
881                 if (!qdev_realize(DEVICE(splitter), NULL, errp)) {
882                     return;
883                 }
884                 for (cpunum = 0; cpunum < info->num_cpus; cpunum++) {
885                     DeviceState *cpudev = DEVICE(&s->armv7m[cpunum]);
886 
887                     qdev_connect_gpio_out(devs, cpunum,
888                                           qdev_get_gpio_in(cpudev, i));
889                 }
890             }
891         }
892     }
893 
894     /* Set up the big aliases first */
895     make_alias(s, &s->alias1, &s->container, "alias 1",
896                0x10000000, 0x10000000, 0x00000000);
897     make_alias(s, &s->alias2, &s->container,
898                "alias 2", 0x30000000, 0x10000000, 0x20000000);
899     /* The 0x50000000..0x5fffffff region is not a pure alias: it has
900      * a few extra devices that only appear there (generally the
901      * control interfaces for the protection controllers).
902      * We implement this by mapping those devices over the top of this
903      * alias MR at a higher priority. Some of the devices in this range
904      * are per-CPU, so we must put this alias in the per-cpu containers.
905      */
906     for (i = 0; i < info->num_cpus; i++) {
907         make_alias(s, &s->alias3[i], &s->cpu_container[i],
908                    "alias 3", 0x50000000, 0x10000000, 0x40000000);
909     }
910 
911     /* Security controller */
912     object_property_set_int(OBJECT(&s->secctl), "sse-version",
913                             info->sse_version, &error_abort);
914     if (!sysbus_realize(SYS_BUS_DEVICE(&s->secctl), errp)) {
915         return;
916     }
917     sbd_secctl = SYS_BUS_DEVICE(&s->secctl);
918     dev_secctl = DEVICE(&s->secctl);
919     sysbus_mmio_map(sbd_secctl, 0, 0x50080000);
920     sysbus_mmio_map(sbd_secctl, 1, 0x40080000);
921 
922     s->nsc_cfg_in = qemu_allocate_irq(nsccfg_handler, s, 1);
923     qdev_connect_gpio_out_named(dev_secctl, "nsc_cfg", 0, s->nsc_cfg_in);
924 
925     /* The sec_resp_cfg output from the security controller must be split into
926      * multiple lines, one for each of the PPCs within the ARMSSE and one
927      * that will be an output from the ARMSSE to the system.
928      */
929     if (!object_property_set_int(OBJECT(&s->sec_resp_splitter),
930                                  "num-lines", 3, errp)) {
931         return;
932     }
933     if (!qdev_realize(DEVICE(&s->sec_resp_splitter), NULL, errp)) {
934         return;
935     }
936     dev_splitter = DEVICE(&s->sec_resp_splitter);
937     qdev_connect_gpio_out_named(dev_secctl, "sec_resp_cfg", 0,
938                                 qdev_get_gpio_in(dev_splitter, 0));
939 
940     /* Each SRAM bank lives behind its own Memory Protection Controller */
941     for (i = 0; i < info->sram_banks; i++) {
942         char *ramname = g_strdup_printf("armsse.sram%d", i);
943         SysBusDevice *sbd_mpc;
944         uint32_t sram_bank_size = 1 << s->sram_addr_width;
945 
946         memory_region_init_ram(&s->sram[i], NULL, ramname,
947                                sram_bank_size, &err);
948         g_free(ramname);
949         if (err) {
950             error_propagate(errp, err);
951             return;
952         }
953         object_property_set_link(OBJECT(&s->mpc[i]), "downstream",
954                                  OBJECT(&s->sram[i]), &error_abort);
955         if (!sysbus_realize(SYS_BUS_DEVICE(&s->mpc[i]), errp)) {
956             return;
957         }
958         /* Map the upstream end of the MPC into the right place... */
959         sbd_mpc = SYS_BUS_DEVICE(&s->mpc[i]);
960         memory_region_add_subregion(&s->container,
961                                     0x20000000 + i * sram_bank_size,
962                                     sysbus_mmio_get_region(sbd_mpc, 1));
963         /* ...and its register interface */
964         memory_region_add_subregion(&s->container, 0x50083000 + i * 0x1000,
965                                     sysbus_mmio_get_region(sbd_mpc, 0));
966     }
967 
968     /* We must OR together lines from the MPC splitters to go to the NVIC */
969     if (!object_property_set_int(OBJECT(&s->mpc_irq_orgate), "num-lines",
970                                  IOTS_NUM_EXP_MPC + info->sram_banks,
971                                  errp)) {
972         return;
973     }
974     if (!qdev_realize(DEVICE(&s->mpc_irq_orgate), NULL, errp)) {
975         return;
976     }
977     qdev_connect_gpio_out(DEVICE(&s->mpc_irq_orgate), 0,
978                           armsse_get_common_irq_in(s, 9));
979 
980     /* This OR gate wires together outputs from the secure watchdogs to NMI */
981     if (!object_property_set_int(OBJECT(&s->nmi_orgate), "num-lines", 2,
982                                  errp)) {
983         return;
984     }
985     if (!qdev_realize(DEVICE(&s->nmi_orgate), NULL, errp)) {
986         return;
987     }
988     qdev_connect_gpio_out(DEVICE(&s->nmi_orgate), 0,
989                           qdev_get_gpio_in_named(DEVICE(&s->armv7m), "NMI", 0));
990 
991     /* Devices behind APB PPC0:
992      *   0x40000000: timer0
993      *   0x40001000: timer1
994      *   0x40002000: dual timer
995      *   0x40003000: MHU0 (SSE-200 only)
996      *   0x40004000: MHU1 (SSE-200 only)
997      * We must configure and realize each downstream device and connect
998      * it to the appropriate PPC port; then we can realize the PPC and
999      * map its upstream ends to the right place in the container.
1000      */
1001     for (devinfo = info->devinfo; devinfo->name; devinfo++) {
1002         SysBusDevice *sbd;
1003         qemu_irq irq;
1004 
1005         if (!strcmp(devinfo->type, TYPE_CMSDK_APB_TIMER)) {
1006             sbd = SYS_BUS_DEVICE(&s->timer[devinfo->index]);
1007 
1008             qdev_connect_clock_in(DEVICE(sbd), "pclk",
1009                                   devinfo->slowclk ? s->s32kclk : s->mainclk);
1010             if (!sysbus_realize(sbd, errp)) {
1011                 return;
1012             }
1013             mr = sysbus_mmio_get_region(sbd, 0);
1014         } else if (!strcmp(devinfo->type, TYPE_CMSDK_APB_DUALTIMER)) {
1015             sbd = SYS_BUS_DEVICE(&s->dualtimer);
1016 
1017             qdev_connect_clock_in(DEVICE(sbd), "TIMCLK", s->mainclk);
1018             if (!sysbus_realize(sbd, errp)) {
1019                 return;
1020             }
1021             mr = sysbus_mmio_get_region(sbd, 0);
1022         } else if (!strcmp(devinfo->type, TYPE_CMSDK_APB_WATCHDOG)) {
1023             sbd = SYS_BUS_DEVICE(&s->cmsdk_watchdog[devinfo->index]);
1024 
1025             qdev_connect_clock_in(DEVICE(sbd), "WDOGCLK",
1026                                   devinfo->slowclk ? s->s32kclk : s->mainclk);
1027             if (!sysbus_realize(sbd, errp)) {
1028                 return;
1029             }
1030             mr = sysbus_mmio_get_region(sbd, 0);
1031         } else if (!strcmp(devinfo->type, TYPE_IOTKIT_SYSINFO)) {
1032             sbd = SYS_BUS_DEVICE(&s->sysinfo);
1033 
1034             object_property_set_int(OBJECT(&s->sysinfo), "SYS_VERSION",
1035                                     info->sys_version, &error_abort);
1036             object_property_set_int(OBJECT(&s->sysinfo), "SYS_CONFIG",
1037                                     armsse_sys_config_value(s, info),
1038                                     &error_abort);
1039             object_property_set_int(OBJECT(&s->sysinfo), "sse-version",
1040                                     info->sse_version, &error_abort);
1041             object_property_set_int(OBJECT(&s->sysinfo), "IIDR",
1042                                     info->iidr, &error_abort);
1043             if (!sysbus_realize(sbd, errp)) {
1044                 return;
1045             }
1046             mr = sysbus_mmio_get_region(sbd, 0);
1047         } else if (!strcmp(devinfo->type, TYPE_IOTKIT_SYSCTL)) {
1048             /* System control registers */
1049             sbd = SYS_BUS_DEVICE(&s->sysctl);
1050 
1051             object_property_set_int(OBJECT(&s->sysctl), "sse-version",
1052                                     info->sse_version, &error_abort);
1053             object_property_set_int(OBJECT(&s->sysctl), "CPUWAIT_RST",
1054                                     info->cpuwait_rst, &error_abort);
1055             object_property_set_int(OBJECT(&s->sysctl), "INITSVTOR0_RST",
1056                                     s->init_svtor, &error_abort);
1057             object_property_set_int(OBJECT(&s->sysctl), "INITSVTOR1_RST",
1058                                     s->init_svtor, &error_abort);
1059             if (!sysbus_realize(sbd, errp)) {
1060                 return;
1061             }
1062             mr = sysbus_mmio_get_region(sbd, 0);
1063         } else if (!strcmp(devinfo->type, TYPE_UNIMPLEMENTED_DEVICE)) {
1064             sbd = SYS_BUS_DEVICE(&s->unimp[devinfo->index]);
1065 
1066             qdev_prop_set_string(DEVICE(sbd), "name", devinfo->name);
1067             qdev_prop_set_uint64(DEVICE(sbd), "size", devinfo->size);
1068             if (!sysbus_realize(sbd, errp)) {
1069                 return;
1070             }
1071             mr = sysbus_mmio_get_region(sbd, 0);
1072         } else {
1073             g_assert_not_reached();
1074         }
1075 
1076         switch (devinfo->irq) {
1077         case NO_IRQ:
1078             irq = NULL;
1079             break;
1080         case 0 ... NUM_SSE_IRQS - 1:
1081             irq = armsse_get_common_irq_in(s, devinfo->irq);
1082             break;
1083         case NMI_0:
1084         case NMI_1:
1085             irq = qdev_get_gpio_in(DEVICE(&s->nmi_orgate),
1086                                    devinfo->irq - NMI_0);
1087             break;
1088         default:
1089             g_assert_not_reached();
1090         }
1091 
1092         if (irq) {
1093             sysbus_connect_irq(sbd, 0, irq);
1094         }
1095 
1096         /*
1097          * Devices connected to a PPC are connected to the port here;
1098          * we will map the upstream end of that port to the right address
1099          * in the container later after the PPC has been realized.
1100          * Devices not connected to a PPC can be mapped immediately.
1101          */
1102         if (devinfo->ppc != NO_PPC) {
1103             TZPPC *ppc = &s->apb_ppc[devinfo->ppc];
1104             g_autofree char *portname = g_strdup_printf("port[%d]",
1105                                                         devinfo->ppc_port);
1106             object_property_set_link(OBJECT(ppc), portname, OBJECT(mr),
1107                                      &error_abort);
1108         } else {
1109             memory_region_add_subregion(&s->container, devinfo->addr, mr);
1110         }
1111     }
1112 
1113     if (info->has_mhus) {
1114         /*
1115          * An SSE-200 with only one CPU should have only one MHU created,
1116          * with the region where the second MHU usually is being RAZ/WI.
1117          * We don't implement that SSE-200 config; if we want to support
1118          * it then this code needs to be enhanced to handle creating the
1119          * RAZ/WI region instead of the second MHU.
1120          */
1121         assert(info->num_cpus == ARRAY_SIZE(s->mhu));
1122 
1123         for (i = 0; i < ARRAY_SIZE(s->mhu); i++) {
1124             char *port;
1125             int cpunum;
1126             SysBusDevice *mhu_sbd = SYS_BUS_DEVICE(&s->mhu[i]);
1127 
1128             if (!sysbus_realize(SYS_BUS_DEVICE(&s->mhu[i]), errp)) {
1129                 return;
1130             }
1131             port = g_strdup_printf("port[%d]", i + 3);
1132             mr = sysbus_mmio_get_region(mhu_sbd, 0);
1133             object_property_set_link(OBJECT(&s->apb_ppc[0]), port, OBJECT(mr),
1134                                      &error_abort);
1135             g_free(port);
1136 
1137             /*
1138              * Each MHU has an irq line for each CPU:
1139              *  MHU 0 irq line 0 -> CPU 0 IRQ 6
1140              *  MHU 0 irq line 1 -> CPU 1 IRQ 6
1141              *  MHU 1 irq line 0 -> CPU 0 IRQ 7
1142              *  MHU 1 irq line 1 -> CPU 1 IRQ 7
1143              */
1144             for (cpunum = 0; cpunum < info->num_cpus; cpunum++) {
1145                 DeviceState *cpudev = DEVICE(&s->armv7m[cpunum]);
1146 
1147                 sysbus_connect_irq(mhu_sbd, cpunum,
1148                                    qdev_get_gpio_in(cpudev, 6 + i));
1149             }
1150         }
1151     }
1152 
1153     if (!sysbus_realize(SYS_BUS_DEVICE(&s->apb_ppc[0]), errp)) {
1154         return;
1155     }
1156 
1157     sbd_apb_ppc0 = SYS_BUS_DEVICE(&s->apb_ppc[0]);
1158     dev_apb_ppc0 = DEVICE(&s->apb_ppc[0]);
1159 
1160     if (info->has_mhus) {
1161         mr = sysbus_mmio_get_region(sbd_apb_ppc0, 3);
1162         memory_region_add_subregion(&s->container, 0x40003000, mr);
1163         mr = sysbus_mmio_get_region(sbd_apb_ppc0, 4);
1164         memory_region_add_subregion(&s->container, 0x40004000, mr);
1165     }
1166     for (i = 0; i < IOTS_APB_PPC0_NUM_PORTS; i++) {
1167         qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_nonsec", i,
1168                                     qdev_get_gpio_in_named(dev_apb_ppc0,
1169                                                            "cfg_nonsec", i));
1170         qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_ap", i,
1171                                     qdev_get_gpio_in_named(dev_apb_ppc0,
1172                                                            "cfg_ap", i));
1173     }
1174     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_irq_enable", 0,
1175                                 qdev_get_gpio_in_named(dev_apb_ppc0,
1176                                                        "irq_enable", 0));
1177     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc0_irq_clear", 0,
1178                                 qdev_get_gpio_in_named(dev_apb_ppc0,
1179                                                        "irq_clear", 0));
1180     qdev_connect_gpio_out(dev_splitter, 0,
1181                           qdev_get_gpio_in_named(dev_apb_ppc0,
1182                                                  "cfg_sec_resp", 0));
1183 
1184     /* All the PPC irq lines (from the 2 internal PPCs and the 8 external
1185      * ones) are sent individually to the security controller, and also
1186      * ORed together to give a single combined PPC interrupt to the NVIC.
1187      */
1188     if (!object_property_set_int(OBJECT(&s->ppc_irq_orgate),
1189                                  "num-lines", NUM_PPCS, errp)) {
1190         return;
1191     }
1192     if (!qdev_realize(DEVICE(&s->ppc_irq_orgate), NULL, errp)) {
1193         return;
1194     }
1195     qdev_connect_gpio_out(DEVICE(&s->ppc_irq_orgate), 0,
1196                           armsse_get_common_irq_in(s, 10));
1197 
1198     /*
1199      * 0x40010000 .. 0x4001ffff (and the 0x5001000... secure-only alias):
1200      * private per-CPU region (all these devices are SSE-200 only):
1201      *  0x50010000: L1 icache control registers
1202      *  0x50011000: CPUSECCTRL (CPU local security control registers)
1203      *  0x4001f000 and 0x5001f000: CPU_IDENTITY register block
1204      */
1205     if (info->has_cachectrl) {
1206         for (i = 0; i < info->num_cpus; i++) {
1207             char *name = g_strdup_printf("cachectrl%d", i);
1208             MemoryRegion *mr;
1209 
1210             qdev_prop_set_string(DEVICE(&s->cachectrl[i]), "name", name);
1211             g_free(name);
1212             qdev_prop_set_uint64(DEVICE(&s->cachectrl[i]), "size", 0x1000);
1213             if (!sysbus_realize(SYS_BUS_DEVICE(&s->cachectrl[i]), errp)) {
1214                 return;
1215             }
1216 
1217             mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->cachectrl[i]), 0);
1218             memory_region_add_subregion(&s->cpu_container[i], 0x50010000, mr);
1219         }
1220     }
1221     if (info->has_cpusecctrl) {
1222         for (i = 0; i < info->num_cpus; i++) {
1223             char *name = g_strdup_printf("CPUSECCTRL%d", i);
1224             MemoryRegion *mr;
1225 
1226             qdev_prop_set_string(DEVICE(&s->cpusecctrl[i]), "name", name);
1227             g_free(name);
1228             qdev_prop_set_uint64(DEVICE(&s->cpusecctrl[i]), "size", 0x1000);
1229             if (!sysbus_realize(SYS_BUS_DEVICE(&s->cpusecctrl[i]), errp)) {
1230                 return;
1231             }
1232 
1233             mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->cpusecctrl[i]), 0);
1234             memory_region_add_subregion(&s->cpu_container[i], 0x50011000, mr);
1235         }
1236     }
1237     if (info->has_cpuid) {
1238         for (i = 0; i < info->num_cpus; i++) {
1239             MemoryRegion *mr;
1240 
1241             qdev_prop_set_uint32(DEVICE(&s->cpuid[i]), "CPUID", i);
1242             if (!sysbus_realize(SYS_BUS_DEVICE(&s->cpuid[i]), errp)) {
1243                 return;
1244             }
1245 
1246             mr = sysbus_mmio_get_region(SYS_BUS_DEVICE(&s->cpuid[i]), 0);
1247             memory_region_add_subregion(&s->cpu_container[i], 0x4001F000, mr);
1248         }
1249     }
1250 
1251     if (!sysbus_realize(SYS_BUS_DEVICE(&s->apb_ppc[1]), errp)) {
1252         return;
1253     }
1254 
1255     dev_apb_ppc1 = DEVICE(&s->apb_ppc[1]);
1256     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_nonsec", 0,
1257                                 qdev_get_gpio_in_named(dev_apb_ppc1,
1258                                                        "cfg_nonsec", 0));
1259     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_ap", 0,
1260                                 qdev_get_gpio_in_named(dev_apb_ppc1,
1261                                                        "cfg_ap", 0));
1262     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_irq_enable", 0,
1263                                 qdev_get_gpio_in_named(dev_apb_ppc1,
1264                                                        "irq_enable", 0));
1265     qdev_connect_gpio_out_named(dev_secctl, "apb_ppc1_irq_clear", 0,
1266                                 qdev_get_gpio_in_named(dev_apb_ppc1,
1267                                                        "irq_clear", 0));
1268     qdev_connect_gpio_out(dev_splitter, 1,
1269                           qdev_get_gpio_in_named(dev_apb_ppc1,
1270                                                  "cfg_sec_resp", 0));
1271 
1272     /*
1273      * Now both PPCs are realized we can map the upstream ends of
1274      * ports which correspond to entries in the devinfo array.
1275      * The ports which are connected to non-devinfo devices have
1276      * already been mapped.
1277      */
1278     for (devinfo = info->devinfo; devinfo->name; devinfo++) {
1279         SysBusDevice *ppc_sbd;
1280 
1281         if (devinfo->ppc == NO_PPC) {
1282             continue;
1283         }
1284         ppc_sbd = SYS_BUS_DEVICE(&s->apb_ppc[devinfo->ppc]);
1285         mr = sysbus_mmio_get_region(ppc_sbd, devinfo->ppc_port);
1286         memory_region_add_subregion(&s->container, devinfo->addr, mr);
1287     }
1288 
1289     for (i = 0; i < ARRAY_SIZE(s->ppc_irq_splitter); i++) {
1290         Object *splitter = OBJECT(&s->ppc_irq_splitter[i]);
1291 
1292         if (!object_property_set_int(splitter, "num-lines", 2, errp)) {
1293             return;
1294         }
1295         if (!qdev_realize(DEVICE(splitter), NULL, errp)) {
1296             return;
1297         }
1298     }
1299 
1300     for (i = 0; i < IOTS_NUM_AHB_EXP_PPC; i++) {
1301         char *ppcname = g_strdup_printf("ahb_ppcexp%d", i);
1302 
1303         armsse_forward_ppc(s, ppcname, i);
1304         g_free(ppcname);
1305     }
1306 
1307     for (i = 0; i < IOTS_NUM_APB_EXP_PPC; i++) {
1308         char *ppcname = g_strdup_printf("apb_ppcexp%d", i);
1309 
1310         armsse_forward_ppc(s, ppcname, i + IOTS_NUM_AHB_EXP_PPC);
1311         g_free(ppcname);
1312     }
1313 
1314     for (i = NUM_EXTERNAL_PPCS; i < NUM_PPCS; i++) {
1315         /* Wire up IRQ splitter for internal PPCs */
1316         DeviceState *devs = DEVICE(&s->ppc_irq_splitter[i]);
1317         char *gpioname = g_strdup_printf("apb_ppc%d_irq_status",
1318                                          i - NUM_EXTERNAL_PPCS);
1319         TZPPC *ppc = &s->apb_ppc[i - NUM_EXTERNAL_PPCS];
1320 
1321         qdev_connect_gpio_out(devs, 0,
1322                               qdev_get_gpio_in_named(dev_secctl, gpioname, 0));
1323         qdev_connect_gpio_out(devs, 1,
1324                               qdev_get_gpio_in(DEVICE(&s->ppc_irq_orgate), i));
1325         qdev_connect_gpio_out_named(DEVICE(ppc), "irq", 0,
1326                                     qdev_get_gpio_in(devs, 0));
1327         g_free(gpioname);
1328     }
1329 
1330     /* Wire up the splitters for the MPC IRQs */
1331     for (i = 0; i < IOTS_NUM_EXP_MPC + info->sram_banks; i++) {
1332         SplitIRQ *splitter = &s->mpc_irq_splitter[i];
1333         DeviceState *dev_splitter = DEVICE(splitter);
1334 
1335         if (!object_property_set_int(OBJECT(splitter), "num-lines", 2,
1336                                      errp)) {
1337             return;
1338         }
1339         if (!qdev_realize(DEVICE(splitter), NULL, errp)) {
1340             return;
1341         }
1342 
1343         if (i < IOTS_NUM_EXP_MPC) {
1344             /* Splitter input is from GPIO input line */
1345             s->mpcexp_status_in[i] = qdev_get_gpio_in(dev_splitter, 0);
1346             qdev_connect_gpio_out(dev_splitter, 0,
1347                                   qdev_get_gpio_in_named(dev_secctl,
1348                                                          "mpcexp_status", i));
1349         } else {
1350             /* Splitter input is from our own MPC */
1351             qdev_connect_gpio_out_named(DEVICE(&s->mpc[i - IOTS_NUM_EXP_MPC]),
1352                                         "irq", 0,
1353                                         qdev_get_gpio_in(dev_splitter, 0));
1354             qdev_connect_gpio_out(dev_splitter, 0,
1355                                   qdev_get_gpio_in_named(dev_secctl,
1356                                                          "mpc_status",
1357                                                          i - IOTS_NUM_EXP_MPC));
1358         }
1359 
1360         qdev_connect_gpio_out(dev_splitter, 1,
1361                               qdev_get_gpio_in(DEVICE(&s->mpc_irq_orgate), i));
1362     }
1363     /* Create GPIO inputs which will pass the line state for our
1364      * mpcexp_irq inputs to the correct splitter devices.
1365      */
1366     qdev_init_gpio_in_named(dev, armsse_mpcexp_status, "mpcexp_status",
1367                             IOTS_NUM_EXP_MPC);
1368 
1369     armsse_forward_sec_resp_cfg(s);
1370 
1371     /* Forward the MSC related signals */
1372     qdev_pass_gpios(dev_secctl, dev, "mscexp_status");
1373     qdev_pass_gpios(dev_secctl, dev, "mscexp_clear");
1374     qdev_pass_gpios(dev_secctl, dev, "mscexp_ns");
1375     qdev_connect_gpio_out_named(dev_secctl, "msc_irq", 0,
1376                                 armsse_get_common_irq_in(s, 11));
1377 
1378     /*
1379      * Expose our container region to the board model; this corresponds
1380      * to the AHB Slave Expansion ports which allow bus master devices
1381      * (eg DMA controllers) in the board model to make transactions into
1382      * devices in the ARMSSE.
1383      */
1384     sysbus_init_mmio(SYS_BUS_DEVICE(s), &s->container);
1385 
1386     /* Set initial system_clock_scale from MAINCLK */
1387     armsse_mainclk_update(s, ClockUpdate);
1388 }
1389 
1390 static void armsse_idau_check(IDAUInterface *ii, uint32_t address,
1391                               int *iregion, bool *exempt, bool *ns, bool *nsc)
1392 {
1393     /*
1394      * For ARMSSE systems the IDAU responses are simple logical functions
1395      * of the address bits. The NSC attribute is guest-adjustable via the
1396      * NSCCFG register in the security controller.
1397      */
1398     ARMSSE *s = ARM_SSE(ii);
1399     int region = extract32(address, 28, 4);
1400 
1401     *ns = !(region & 1);
1402     *nsc = (region == 1 && (s->nsccfg & 1)) || (region == 3 && (s->nsccfg & 2));
1403     /* 0xe0000000..0xe00fffff and 0xf0000000..0xf00fffff are exempt */
1404     *exempt = (address & 0xeff00000) == 0xe0000000;
1405     *iregion = region;
1406 }
1407 
1408 static const VMStateDescription armsse_vmstate = {
1409     .name = "iotkit",
1410     .version_id = 2,
1411     .minimum_version_id = 2,
1412     .fields = (VMStateField[]) {
1413         VMSTATE_CLOCK(mainclk, ARMSSE),
1414         VMSTATE_CLOCK(s32kclk, ARMSSE),
1415         VMSTATE_UINT32(nsccfg, ARMSSE),
1416         VMSTATE_END_OF_LIST()
1417     }
1418 };
1419 
1420 static void armsse_reset(DeviceState *dev)
1421 {
1422     ARMSSE *s = ARM_SSE(dev);
1423 
1424     s->nsccfg = 0;
1425 }
1426 
1427 static void armsse_class_init(ObjectClass *klass, void *data)
1428 {
1429     DeviceClass *dc = DEVICE_CLASS(klass);
1430     IDAUInterfaceClass *iic = IDAU_INTERFACE_CLASS(klass);
1431     ARMSSEClass *asc = ARM_SSE_CLASS(klass);
1432     const ARMSSEInfo *info = data;
1433 
1434     dc->realize = armsse_realize;
1435     dc->vmsd = &armsse_vmstate;
1436     device_class_set_props(dc, info->props);
1437     dc->reset = armsse_reset;
1438     iic->check = armsse_idau_check;
1439     asc->info = info;
1440 }
1441 
1442 static const TypeInfo armsse_info = {
1443     .name = TYPE_ARM_SSE,
1444     .parent = TYPE_SYS_BUS_DEVICE,
1445     .instance_size = sizeof(ARMSSE),
1446     .class_size = sizeof(ARMSSEClass),
1447     .instance_init = armsse_init,
1448     .abstract = true,
1449     .interfaces = (InterfaceInfo[]) {
1450         { TYPE_IDAU_INTERFACE },
1451         { }
1452     }
1453 };
1454 
1455 static void armsse_register_types(void)
1456 {
1457     int i;
1458 
1459     type_register_static(&armsse_info);
1460 
1461     for (i = 0; i < ARRAY_SIZE(armsse_variants); i++) {
1462         TypeInfo ti = {
1463             .name = armsse_variants[i].name,
1464             .parent = TYPE_ARM_SSE,
1465             .class_init = armsse_class_init,
1466             .class_data = (void *)&armsse_variants[i],
1467         };
1468         type_register(&ti);
1469     }
1470 }
1471 
1472 type_init(armsse_register_types);
1473