vexpress.c (ef475b5dd12684591e6264e517eaa5b3e90f7ffa) | vexpress.c (ba1ba5cca3962a9cc400c713c736b4fb8db1f38e) |
---|---|
1/* 2 * ARM Versatile Express emulation. 3 * 4 * Copyright (c) 2010 - 2011 B Labs Ltd. 5 * Copyright (c) 2011 Linaro Limited 6 * Written by Bahadir Balban, Amit Mahajan, Peter Maydell 7 * 8 * This program is free software; you can redistribute it and/or modify --- 172 unchanged lines hidden (view full) --- 181 OBJECT_CHECK(VexpressMachineState, (obj), TYPE_VEXPRESS_MACHINE) 182#define VEXPRESS_MACHINE_GET_CLASS(obj) \ 183 OBJECT_GET_CLASS(VexpressMachineClass, obj, TYPE_VEXPRESS_MACHINE) 184#define VEXPRESS_MACHINE_CLASS(klass) \ 185 OBJECT_CLASS_CHECK(VexpressMachineClass, klass, TYPE_VEXPRESS_MACHINE) 186 187typedef void DBoardInitFn(const VexpressMachineState *machine, 188 ram_addr_t ram_size, | 1/* 2 * ARM Versatile Express emulation. 3 * 4 * Copyright (c) 2010 - 2011 B Labs Ltd. 5 * Copyright (c) 2011 Linaro Limited 6 * Written by Bahadir Balban, Amit Mahajan, Peter Maydell 7 * 8 * This program is free software; you can redistribute it and/or modify --- 172 unchanged lines hidden (view full) --- 181 OBJECT_CHECK(VexpressMachineState, (obj), TYPE_VEXPRESS_MACHINE) 182#define VEXPRESS_MACHINE_GET_CLASS(obj) \ 183 OBJECT_GET_CLASS(VexpressMachineClass, obj, TYPE_VEXPRESS_MACHINE) 184#define VEXPRESS_MACHINE_CLASS(klass) \ 185 OBJECT_CLASS_CHECK(VexpressMachineClass, klass, TYPE_VEXPRESS_MACHINE) 186 187typedef void DBoardInitFn(const VexpressMachineState *machine, 188 ram_addr_t ram_size, |
189 const char *cpu_model, | 189 const char *cpu_type, |
190 qemu_irq *pic); 191 192struct VEDBoardInfo { 193 struct arm_boot_info bootinfo; 194 const hwaddr *motherboard_map; 195 hwaddr loader_start; 196 const hwaddr gic_cpu_if_addr; 197 uint32_t proc_id; 198 uint32_t num_voltage_sensors; 199 const uint32_t *voltages; 200 uint32_t num_clocks; 201 const uint32_t *clocks; 202 DBoardInitFn *init; 203}; 204 | 190 qemu_irq *pic); 191 192struct VEDBoardInfo { 193 struct arm_boot_info bootinfo; 194 const hwaddr *motherboard_map; 195 hwaddr loader_start; 196 const hwaddr gic_cpu_if_addr; 197 uint32_t proc_id; 198 uint32_t num_voltage_sensors; 199 const uint32_t *voltages; 200 uint32_t num_clocks; 201 const uint32_t *clocks; 202 DBoardInitFn *init; 203}; 204 |
205static void init_cpus(const char *cpu_model, const char *privdev, | 205static void init_cpus(const char *cpu_type, const char *privdev, |
206 hwaddr periphbase, qemu_irq *pic, bool secure) 207{ | 206 hwaddr periphbase, qemu_irq *pic, bool secure) 207{ |
208 ObjectClass *cpu_oc = cpu_class_by_name(TYPE_ARM_CPU, cpu_model); | |
209 DeviceState *dev; 210 SysBusDevice *busdev; 211 int n; 212 | 208 DeviceState *dev; 209 SysBusDevice *busdev; 210 int n; 211 |
213 if (!cpu_oc) { 214 fprintf(stderr, "Unable to find CPU definition\n"); 215 exit(1); 216 } 217 | |
218 /* Create the actual CPUs */ 219 for (n = 0; n < smp_cpus; n++) { | 212 /* Create the actual CPUs */ 213 for (n = 0; n < smp_cpus; n++) { |
220 Object *cpuobj = object_new(object_class_get_name(cpu_oc)); | 214 Object *cpuobj = object_new(cpu_type); |
221 222 if (!secure) { 223 object_property_set_bool(cpuobj, false, "has_el3", NULL); 224 } 225 226 if (object_property_find(cpuobj, "reset-cbar", NULL)) { 227 object_property_set_int(cpuobj, periphbase, 228 "reset-cbar", &error_abort); --- 28 unchanged lines hidden (view full) --- 257 sysbus_connect_irq(busdev, n, qdev_get_gpio_in(cpudev, ARM_CPU_IRQ)); 258 sysbus_connect_irq(busdev, n + smp_cpus, 259 qdev_get_gpio_in(cpudev, ARM_CPU_FIQ)); 260 } 261} 262 263static void a9_daughterboard_init(const VexpressMachineState *vms, 264 ram_addr_t ram_size, | 215 216 if (!secure) { 217 object_property_set_bool(cpuobj, false, "has_el3", NULL); 218 } 219 220 if (object_property_find(cpuobj, "reset-cbar", NULL)) { 221 object_property_set_int(cpuobj, periphbase, 222 "reset-cbar", &error_abort); --- 28 unchanged lines hidden (view full) --- 251 sysbus_connect_irq(busdev, n, qdev_get_gpio_in(cpudev, ARM_CPU_IRQ)); 252 sysbus_connect_irq(busdev, n + smp_cpus, 253 qdev_get_gpio_in(cpudev, ARM_CPU_FIQ)); 254 } 255} 256 257static void a9_daughterboard_init(const VexpressMachineState *vms, 258 ram_addr_t ram_size, |
265 const char *cpu_model, | 259 const char *cpu_type, |
266 qemu_irq *pic) 267{ 268 MemoryRegion *sysmem = get_system_memory(); 269 MemoryRegion *ram = g_new(MemoryRegion, 1); 270 MemoryRegion *lowram = g_new(MemoryRegion, 1); 271 ram_addr_t low_ram_size; 272 | 260 qemu_irq *pic) 261{ 262 MemoryRegion *sysmem = get_system_memory(); 263 MemoryRegion *ram = g_new(MemoryRegion, 1); 264 MemoryRegion *lowram = g_new(MemoryRegion, 1); 265 ram_addr_t low_ram_size; 266 |
273 if (!cpu_model) { 274 cpu_model = "cortex-a9"; 275 } 276 | |
277 if (ram_size > 0x40000000) { 278 /* 1GB is the maximum the address space permits */ 279 fprintf(stderr, "vexpress-a9: cannot model more than 1GB RAM\n"); 280 exit(1); 281 } 282 283 memory_region_allocate_system_memory(ram, NULL, "vexpress.highmem", 284 ram_size); --- 5 unchanged lines hidden (view full) --- 290 * address space should in theory be remappable to various 291 * things including ROM or RAM; we always map the RAM there. 292 */ 293 memory_region_init_alias(lowram, NULL, "vexpress.lowmem", ram, 0, low_ram_size); 294 memory_region_add_subregion(sysmem, 0x0, lowram); 295 memory_region_add_subregion(sysmem, 0x60000000, ram); 296 297 /* 0x1e000000 A9MPCore (SCU) private memory region */ | 267 if (ram_size > 0x40000000) { 268 /* 1GB is the maximum the address space permits */ 269 fprintf(stderr, "vexpress-a9: cannot model more than 1GB RAM\n"); 270 exit(1); 271 } 272 273 memory_region_allocate_system_memory(ram, NULL, "vexpress.highmem", 274 ram_size); --- 5 unchanged lines hidden (view full) --- 280 * address space should in theory be remappable to various 281 * things including ROM or RAM; we always map the RAM there. 282 */ 283 memory_region_init_alias(lowram, NULL, "vexpress.lowmem", ram, 0, low_ram_size); 284 memory_region_add_subregion(sysmem, 0x0, lowram); 285 memory_region_add_subregion(sysmem, 0x60000000, ram); 286 287 /* 0x1e000000 A9MPCore (SCU) private memory region */ |
298 init_cpus(cpu_model, TYPE_A9MPCORE_PRIV, 0x1e000000, pic, vms->secure); | 288 init_cpus(cpu_type, TYPE_A9MPCORE_PRIV, 0x1e000000, pic, vms->secure); |
299 300 /* Daughterboard peripherals : 0x10020000 .. 0x20000000 */ 301 302 /* 0x10020000 PL111 CLCD (daughterboard) */ 303 sysbus_create_simple("pl111", 0x10020000, pic[44]); 304 305 /* 0x10060000 AXI RAM */ 306 /* 0x100e0000 PL341 Dynamic Memory Controller */ --- 39 unchanged lines hidden (view full) --- 346 .voltages = a9_voltages, 347 .num_clocks = ARRAY_SIZE(a9_clocks), 348 .clocks = a9_clocks, 349 .init = a9_daughterboard_init, 350}; 351 352static void a15_daughterboard_init(const VexpressMachineState *vms, 353 ram_addr_t ram_size, | 289 290 /* Daughterboard peripherals : 0x10020000 .. 0x20000000 */ 291 292 /* 0x10020000 PL111 CLCD (daughterboard) */ 293 sysbus_create_simple("pl111", 0x10020000, pic[44]); 294 295 /* 0x10060000 AXI RAM */ 296 /* 0x100e0000 PL341 Dynamic Memory Controller */ --- 39 unchanged lines hidden (view full) --- 336 .voltages = a9_voltages, 337 .num_clocks = ARRAY_SIZE(a9_clocks), 338 .clocks = a9_clocks, 339 .init = a9_daughterboard_init, 340}; 341 342static void a15_daughterboard_init(const VexpressMachineState *vms, 343 ram_addr_t ram_size, |
354 const char *cpu_model, | 344 const char *cpu_type, |
355 qemu_irq *pic) 356{ 357 MemoryRegion *sysmem = get_system_memory(); 358 MemoryRegion *ram = g_new(MemoryRegion, 1); 359 MemoryRegion *sram = g_new(MemoryRegion, 1); 360 | 345 qemu_irq *pic) 346{ 347 MemoryRegion *sysmem = get_system_memory(); 348 MemoryRegion *ram = g_new(MemoryRegion, 1); 349 MemoryRegion *sram = g_new(MemoryRegion, 1); 350 |
361 if (!cpu_model) { 362 cpu_model = "cortex-a15"; 363 } 364 | |
365 { 366 /* We have to use a separate 64 bit variable here to avoid the gcc 367 * "comparison is always false due to limited range of data type" 368 * warning if we are on a host where ram_addr_t is 32 bits. 369 */ 370 uint64_t rsz = ram_size; 371 if (rsz > (30ULL * 1024 * 1024 * 1024)) { 372 fprintf(stderr, "vexpress-a15: cannot model more than 30GB RAM\n"); 373 exit(1); 374 } 375 } 376 377 memory_region_allocate_system_memory(ram, NULL, "vexpress.highmem", 378 ram_size); 379 /* RAM is from 0x80000000 upwards; there is no low-memory alias for it. */ 380 memory_region_add_subregion(sysmem, 0x80000000, ram); 381 382 /* 0x2c000000 A15MPCore private memory region (GIC) */ | 351 { 352 /* We have to use a separate 64 bit variable here to avoid the gcc 353 * "comparison is always false due to limited range of data type" 354 * warning if we are on a host where ram_addr_t is 32 bits. 355 */ 356 uint64_t rsz = ram_size; 357 if (rsz > (30ULL * 1024 * 1024 * 1024)) { 358 fprintf(stderr, "vexpress-a15: cannot model more than 30GB RAM\n"); 359 exit(1); 360 } 361 } 362 363 memory_region_allocate_system_memory(ram, NULL, "vexpress.highmem", 364 ram_size); 365 /* RAM is from 0x80000000 upwards; there is no low-memory alias for it. */ 366 memory_region_add_subregion(sysmem, 0x80000000, ram); 367 368 /* 0x2c000000 A15MPCore private memory region (GIC) */ |
383 init_cpus(cpu_model, TYPE_A15MPCORE_PRIV, 0x2c000000, pic, vms->secure); | 369 init_cpus(cpu_type, TYPE_A15MPCORE_PRIV, 0x2c000000, pic, vms->secure); |
384 385 /* A15 daughterboard peripherals: */ 386 387 /* 0x20000000: CoreSight interfaces: not modelled */ 388 /* 0x2a000000: PL301 AXI interconnect: not modelled */ 389 /* 0x2a420000: SCC: not modelled */ 390 /* 0x2a430000: system counter: not modelled */ 391 /* 0x2b000000: HDLCD controller: not modelled */ --- 163 unchanged lines hidden (view full) --- 555 MemoryRegion *sysmem = get_system_memory(); 556 MemoryRegion *vram = g_new(MemoryRegion, 1); 557 MemoryRegion *sram = g_new(MemoryRegion, 1); 558 MemoryRegion *flashalias = g_new(MemoryRegion, 1); 559 MemoryRegion *flash0mem; 560 const hwaddr *map = daughterboard->motherboard_map; 561 int i; 562 | 370 371 /* A15 daughterboard peripherals: */ 372 373 /* 0x20000000: CoreSight interfaces: not modelled */ 374 /* 0x2a000000: PL301 AXI interconnect: not modelled */ 375 /* 0x2a420000: SCC: not modelled */ 376 /* 0x2a430000: system counter: not modelled */ 377 /* 0x2b000000: HDLCD controller: not modelled */ --- 163 unchanged lines hidden (view full) --- 541 MemoryRegion *sysmem = get_system_memory(); 542 MemoryRegion *vram = g_new(MemoryRegion, 1); 543 MemoryRegion *sram = g_new(MemoryRegion, 1); 544 MemoryRegion *flashalias = g_new(MemoryRegion, 1); 545 MemoryRegion *flash0mem; 546 const hwaddr *map = daughterboard->motherboard_map; 547 int i; 548 |
563 daughterboard->init(vms, machine->ram_size, machine->cpu_model, pic); | 549 daughterboard->init(vms, machine->ram_size, machine->cpu_type, pic); |
564 565 /* 566 * If a bios file was provided, attempt to map it into memory 567 */ 568 if (bios_name) { 569 char *fn; 570 int image_size; 571 --- 184 unchanged lines hidden (view full) --- 756} 757 758static void vexpress_a9_class_init(ObjectClass *oc, void *data) 759{ 760 MachineClass *mc = MACHINE_CLASS(oc); 761 VexpressMachineClass *vmc = VEXPRESS_MACHINE_CLASS(oc); 762 763 mc->desc = "ARM Versatile Express for Cortex-A9"; | 550 551 /* 552 * If a bios file was provided, attempt to map it into memory 553 */ 554 if (bios_name) { 555 char *fn; 556 int image_size; 557 --- 184 unchanged lines hidden (view full) --- 742} 743 744static void vexpress_a9_class_init(ObjectClass *oc, void *data) 745{ 746 MachineClass *mc = MACHINE_CLASS(oc); 747 VexpressMachineClass *vmc = VEXPRESS_MACHINE_CLASS(oc); 748 749 mc->desc = "ARM Versatile Express for Cortex-A9"; |
750 mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-a9"); |
|
764 765 vmc->daughterboard = &a9_daughterboard; 766} 767 768static void vexpress_a15_class_init(ObjectClass *oc, void *data) 769{ 770 MachineClass *mc = MACHINE_CLASS(oc); 771 VexpressMachineClass *vmc = VEXPRESS_MACHINE_CLASS(oc); 772 773 mc->desc = "ARM Versatile Express for Cortex-A15"; | 751 752 vmc->daughterboard = &a9_daughterboard; 753} 754 755static void vexpress_a15_class_init(ObjectClass *oc, void *data) 756{ 757 MachineClass *mc = MACHINE_CLASS(oc); 758 VexpressMachineClass *vmc = VEXPRESS_MACHINE_CLASS(oc); 759 760 mc->desc = "ARM Versatile Express for Cortex-A15"; |
761 mc->default_cpu_type = ARM_CPU_TYPE_NAME("cortex-a15"); |
|
774 775 vmc->daughterboard = &a15_daughterboard; 776} 777 778static const TypeInfo vexpress_info = { 779 .name = TYPE_VEXPRESS_MACHINE, 780 .parent = TYPE_MACHINE, 781 .abstract = true, --- 26 unchanged lines hidden --- | 762 763 vmc->daughterboard = &a15_daughterboard; 764} 765 766static const TypeInfo vexpress_info = { 767 .name = TYPE_VEXPRESS_MACHINE, 768 .parent = TYPE_MACHINE, 769 .abstract = true, --- 26 unchanged lines hidden --- |