Add PowerPC power-management state check callback.
[qemu] / hw / pl050.c
index 20451e5..b3a2797 100644 (file)
@@ -1,7 +1,7 @@
-/* 
+/*
  * Arm PrimeCell PL050 Keyboard / Mouse Interface
  *
- * Copyright (c) 2006 CodeSourcery.
+ * Copyright (c) 2006-2007 CodeSourcery.
  * Written by Paul Brook
  *
  * This code is licenced under the GPL.
@@ -15,12 +15,19 @@ typedef struct {
     uint32_t cr;
     uint32_t clk;
     uint32_t last;
-    void *pic;
     int pending;
-    int irq;
+    qemu_irq irq;
     int is_mouse;
 } pl050_state;
 
+#define PL050_TXEMPTY         (1 << 6)
+#define PL050_TXBUSY          (1 << 5)
+#define PL050_RXFULL          (1 << 4)
+#define PL050_RXBUSY          (1 << 3)
+#define PL050_RXPARITY        (1 << 2)
+#define PL050_KMIC            (1 << 1)
+#define PL050_KMID            (1 << 0)
+
 static const unsigned char pl050_id[] =
 { 0x50, 0x10, 0x04, 0x00, 0x0d, 0xf0, 0x05, 0xb1 };
 
@@ -32,7 +39,7 @@ static void pl050_update(void *opaque, int level)
     s->pending = level;
     raise = (s->pending && (s->cr & 0x10) != 0)
             || (s->cr & 0x08) != 0;
-    pic_set_irq_new(s->pic, s->irq, raise);
+    qemu_set_irq(s->irq, raise);
 }
 
 static uint32_t pl050_read(void *opaque, target_phys_addr_t offset)
@@ -46,11 +53,22 @@ static uint32_t pl050_read(void *opaque, target_phys_addr_t offset)
     case 0: /* KMICR */
         return s->cr;
     case 1: /* KMISTAT */
-        /* KMIC and KMID bits not implemented.  */
-        if (s->pending) {
-            return 0x10;
-        } else {
-            return 0;
+        {
+            uint8_t val;
+            uint32_t stat;
+
+            val = s->last;
+            val = val ^ (val >> 4);
+            val = val ^ (val >> 2);
+            val = (val ^ (val >> 1)) & 1;
+
+            stat = PL050_TXEMPTY;
+            if (val)
+                stat |= PL050_RXPARITY;
+            if (s->pending)
+                stat |= PL050_RXFULL;
+
+            return stat;
         }
     case 2: /* KMIDATA */
         if (s->pending)
@@ -105,7 +123,7 @@ static CPUWriteMemoryFunc *pl050_writefn[] = {
    pl050_write
 };
 
-void pl050_init(uint32_t base, void *pic, int irq, int is_mouse)
+void pl050_init(uint32_t base, qemu_irq irq, int is_mouse)
 {
     int iomemtype;
     pl050_state *s;
@@ -113,9 +131,8 @@ void pl050_init(uint32_t base, void *pic, int irq, int is_mouse)
     s = (pl050_state *)qemu_mallocz(sizeof(pl050_state));
     iomemtype = cpu_register_io_memory(0, pl050_readfn,
                                        pl050_writefn, s);
-    cpu_register_physical_memory(base, 0x00000fff, iomemtype);
+    cpu_register_physical_memory(base, 0x00001000, iomemtype);
     s->base = base;
-    s->pic = pic;
     s->irq = irq;
     s->is_mouse = is_mouse;
     if (is_mouse)