diff mbox

[2/2] hw/mips_malta: add CPC to the Malta board

Message ID 1456503598-27824-3-git-send-email-leon.alrae@imgtec.com (mailing list archive)
State New, archived
Headers show

Commit Message

Leon Alrae Feb. 26, 2016, 4:19 p.m. UTC
On Malta, after reset, only VP0 on Core0 starts the execution. Other VPs
are halted until VP0 powers them up using Cluster Power Controller.

Signed-off-by: Leon Alrae <leon.alrae@imgtec.com>
---
 hw/mips/mips_malta.c | 30 ++++++++++++++++++++++++++++++
 1 file changed, 30 insertions(+)
diff mbox

Patch

diff --git a/hw/mips/mips_malta.c b/hw/mips/mips_malta.c
index 1fb17fb..34cc4cb 100644
--- a/hw/mips/mips_malta.c
+++ b/hw/mips/mips_malta.c
@@ -57,6 +57,7 @@ 
 #include "exec/semihost.h"
 #include "hw/misc/mips_gcr.h"
 #include "hw/intc/mips_gic.h"
+#include "hw/misc/mips_cpc.h"
 
 //#define DEBUG_BOARD_INIT
 
@@ -97,6 +98,7 @@  typedef struct {
 
     MIPSGCRState gcr;
     MIPSGICState gic;
+    MIPSCPCState cpc;
     qemu_irq *i8259;
 } MaltaState;
 
@@ -617,6 +619,19 @@  static void gic_init(MaltaState *s, Error **err)
     sysbus_mmio_map(gicbusdev, 0, gicbase);
 }
 
+static void cpc_init(MaltaState *s, Error **err)
+{
+    object_initialize(&s->cpc, sizeof(s->cpc), TYPE_MIPS_CPC);
+    qdev_set_parent_bus(DEVICE(&s->cpc), sysbus_get_default());
+
+    object_property_set_bool(OBJECT(&s->cpc), true, "realized", err);
+    if (*err != NULL) {
+        return;
+    }
+
+    sysbus_mmio_map(SYS_BUS_DEVICE(&s->cpc), 0, CPC_BASE_ADDR);
+}
+
 /* Network support */
 static void network_init(PCIBus *pci_bus)
 {
@@ -937,6 +952,7 @@  static void malta_mips_config(MIPSCPU *cpu)
 static void main_cpu_reset(void *opaque)
 {
     MIPSCPU *cpu = opaque;
+    CPUState *cs = CPU(cpu);
     CPUMIPSState *env = &cpu->env;
 
     cpu_reset(CPU(cpu));
@@ -954,6 +970,15 @@  static void main_cpu_reset(void *opaque)
         /* Start running from the bootloader we wrote to end of RAM */
         env->active_tc.PC = 0x40000000 + loaderparams.ram_low_size;
     }
+
+    /* At reset only VP0 on Core0 will start executing the code, other
+       VPs are halted until VP0 powers them up through Cluster Power
+       Controller. */
+    if ((env->CP0_Config5 & (1 << CP0C5_VP)) &&
+        (env->CP0_Config3 & (1 << CP0C3_CMGCR)) &&
+        (cs->cpu_index != 0)) {
+        cs->halted = 1;
+    }
 }
 
 static
@@ -1200,6 +1225,11 @@  void mips_malta_init(MachineState *machine)
             error_report("%s", error_get_pretty(err));
             exit(1);
         }
+        cpc_init(s, &err);
+        if (err != NULL) {
+            error_report("%s", error_get_pretty(err));
+            exit(1);
+        }
     }
 
     /*