Commit b47b50fa9e55bf15570e83971c01205be11b2e1d

Authored by Paul Brook
1 parent fe7e8758

MusicPal qdev conversion

Signed-off-by: Paul Brook <paul@codesourcery.com>
Showing 1 changed file with 87 additions and 63 deletions
hw/musicpal.c
... ... @@ -6,7 +6,7 @@
6 6 * This code is licenced under the GNU GPL v2.
7 7 */
8 8  
9   -#include "hw.h"
  9 +#include "sysbus.h"
10 10 #include "arm-misc.h"
11 11 #include "devices.h"
12 12 #include "net.h"
... ... @@ -57,7 +57,8 @@
57 57 #define MP_FLASH_SIZE_MAX 32*1024*1024
58 58  
59 59 #define MP_TIMER1_IRQ 4
60   -/* ... */
  60 +#define MP_TIMER2_IRQ 5
  61 +#define MP_TIMER3_IRQ 6
61 62 #define MP_TIMER4_IRQ 7
62 63 #define MP_EHCI_IRQ 8
63 64 #define MP_ETH_IRQ 9
... ... @@ -525,6 +526,7 @@ typedef struct mv88w8618_rx_desc {
525 526 } mv88w8618_rx_desc;
526 527  
527 528 typedef struct mv88w8618_eth_state {
  529 + SysBusDevice busdev;
528 530 qemu_irq irq;
529 531 uint32_t smir;
530 532 uint32_t icr;
... ... @@ -748,20 +750,17 @@ static void eth_cleanup(VLANClientState *vc)
748 750 qemu_free(s);
749 751 }
750 752  
751   -static void mv88w8618_eth_init(NICInfo *nd, uint32_t base, qemu_irq irq)
  753 +static void mv88w8618_eth_init(SysBusDevice *dev)
752 754 {
753   - mv88w8618_eth_state *s;
754   -
755   - qemu_check_nic_model(nd, "mv88w8618");
  755 + mv88w8618_eth_state *s = FROM_SYSBUS(mv88w8618_eth_state, dev);
756 756  
757   - s = qemu_mallocz(sizeof(mv88w8618_eth_state));
758   - s->irq = irq;
759   - s->vc = qemu_new_vlan_client(nd->vlan, nd->model, nd->name,
  757 + sysbus_init_irq(dev, &s->irq);
  758 + s->vc = qdev_get_vlan_client(&dev->qdev,
760 759 eth_receive, eth_can_receive,
761 760 eth_cleanup, s);
762 761 s->mmio_index = cpu_register_io_memory(0, mv88w8618_eth_readfn,
763 762 mv88w8618_eth_writefn, s);
764   - cpu_register_physical_memory(base, MP_ETH_SIZE, s->mmio_index);
  763 + sysbus_init_mmio(dev, MP_ETH_SIZE, s->mmio_index);
765 764 }
766 765  
767 766 /* LCD register offsets */
... ... @@ -784,6 +783,7 @@ static void mv88w8618_eth_init(NICInfo *nd, uint32_t base, qemu_irq irq)
784 783 #define MP_LCD_TEXTCOLOR 0xe0e0ff /* RRGGBB */
785 784  
786 785 typedef struct musicpal_lcd_state {
  786 + SysBusDevice busdev;
787 787 uint32_t mode;
788 788 uint32_t irqctrl;
789 789 int page;
... ... @@ -943,14 +943,14 @@ static CPUWriteMemoryFunc *musicpal_lcd_writefn[] = {
943 943 musicpal_lcd_write
944 944 };
945 945  
946   -static void musicpal_lcd_init(void)
  946 +static void musicpal_lcd_init(SysBusDevice *dev)
947 947 {
948   - musicpal_lcd_state *s;
  948 + musicpal_lcd_state *s = FROM_SYSBUS(musicpal_lcd_state, dev);
949 949 int iomemtype;
950 950  
951   - s = qemu_mallocz(sizeof(musicpal_lcd_state));
952 951 iomemtype = cpu_register_io_memory(0, musicpal_lcd_readfn,
953 952 musicpal_lcd_writefn, s);
  953 + sysbus_init_mmio(dev, MP_LCD_SIZE, iomemtype);
954 954 cpu_register_physical_memory(MP_LCD_BASE, MP_LCD_SIZE, iomemtype);
955 955  
956 956 s->ds = graphic_console_init(lcd_refresh, lcd_invalidate,
... ... @@ -965,6 +965,7 @@ static void musicpal_lcd_init(void)
965 965  
966 966 typedef struct mv88w8618_pic_state
967 967 {
  968 + SysBusDevice busdev;
968 969 uint32_t level;
969 970 uint32_t enabled;
970 971 qemu_irq parent_irq;
... ... @@ -1037,22 +1038,18 @@ static CPUWriteMemoryFunc *mv88w8618_pic_writefn[] = {
1037 1038 mv88w8618_pic_write
1038 1039 };
1039 1040  
1040   -static qemu_irq *mv88w8618_pic_init(uint32_t base, qemu_irq parent_irq)
  1041 +static void mv88w8618_pic_init(SysBusDevice *dev)
1041 1042 {
1042   - mv88w8618_pic_state *s;
  1043 + mv88w8618_pic_state *s = FROM_SYSBUS(mv88w8618_pic_state, dev);
1043 1044 int iomemtype;
1044   - qemu_irq *qi;
1045 1045  
1046   - s = qemu_mallocz(sizeof(mv88w8618_pic_state));
1047   - qi = qemu_allocate_irqs(mv88w8618_pic_set_irq, s, 32);
1048   - s->parent_irq = parent_irq;
  1046 + qdev_init_irq_sink(&dev->qdev, mv88w8618_pic_set_irq, 32);
  1047 + sysbus_init_irq(dev, &s->parent_irq);
1049 1048 iomemtype = cpu_register_io_memory(0, mv88w8618_pic_readfn,
1050 1049 mv88w8618_pic_writefn, s);
1051   - cpu_register_physical_memory(base, MP_PIC_SIZE, iomemtype);
  1050 + sysbus_init_mmio(dev, MP_PIC_SIZE, iomemtype);
1052 1051  
1053 1052 qemu_register_reset(mv88w8618_pic_reset, s);
1054   -
1055   - return qi;
1056 1053 }
1057 1054  
1058 1055 /* PIT register offsets */
... ... @@ -1069,14 +1066,15 @@ static qemu_irq *mv88w8618_pic_init(uint32_t base, qemu_irq parent_irq)
1069 1066 #define MP_BOARD_RESET_MAGIC 0x10000
1070 1067  
1071 1068 typedef struct mv88w8618_timer_state {
1072   - ptimer_state *timer;
  1069 + ptimer_state *ptimer;
1073 1070 uint32_t limit;
1074 1071 int freq;
1075 1072 qemu_irq irq;
1076 1073 } mv88w8618_timer_state;
1077 1074  
1078 1075 typedef struct mv88w8618_pit_state {
1079   - void *timer[4];
  1076 + SysBusDevice busdev;
  1077 + mv88w8618_timer_state timer[4];
1080 1078 uint32_t control;
1081 1079 } mv88w8618_pit_state;
1082 1080  
... ... @@ -1087,19 +1085,16 @@ static void mv88w8618_timer_tick(void *opaque)
1087 1085 qemu_irq_raise(s->irq);
1088 1086 }
1089 1087  
1090   -static void *mv88w8618_timer_init(uint32_t freq, qemu_irq irq)
  1088 +static void mv88w8618_timer_init(SysBusDevice *dev, mv88w8618_timer_state *s,
  1089 + uint32_t freq)
1091 1090 {
1092   - mv88w8618_timer_state *s;
1093 1091 QEMUBH *bh;
1094 1092  
1095   - s = qemu_mallocz(sizeof(mv88w8618_timer_state));
1096   - s->irq = irq;
  1093 + sysbus_init_irq(dev, &s->irq);
1097 1094 s->freq = freq;
1098 1095  
1099 1096 bh = qemu_bh_new(mv88w8618_timer_tick, s);
1100   - s->timer = ptimer_init(bh);
1101   -
1102   - return s;
  1097 + s->ptimer = ptimer_init(bh);
1103 1098 }
1104 1099  
1105 1100 static uint32_t mv88w8618_pit_read(void *opaque, target_phys_addr_t offset)
... ... @@ -1109,8 +1104,8 @@ static uint32_t mv88w8618_pit_read(void *opaque, target_phys_addr_t offset)
1109 1104  
1110 1105 switch (offset) {
1111 1106 case MP_PIT_TIMER1_VALUE ... MP_PIT_TIMER4_VALUE:
1112   - t = s->timer[(offset-MP_PIT_TIMER1_VALUE) >> 2];
1113   - return ptimer_get_count(t->timer);
  1107 + t = &s->timer[(offset-MP_PIT_TIMER1_VALUE) >> 2];
  1108 + return ptimer_get_count(t->ptimer);
1114 1109  
1115 1110 default:
1116 1111 return 0;
... ... @@ -1126,18 +1121,18 @@ static void mv88w8618_pit_write(void *opaque, target_phys_addr_t offset,
1126 1121  
1127 1122 switch (offset) {
1128 1123 case MP_PIT_TIMER1_LENGTH ... MP_PIT_TIMER4_LENGTH:
1129   - t = s->timer[offset >> 2];
  1124 + t = &s->timer[offset >> 2];
1130 1125 t->limit = value;
1131   - ptimer_set_limit(t->timer, t->limit, 1);
  1126 + ptimer_set_limit(t->ptimer, t->limit, 1);
1132 1127 break;
1133 1128  
1134 1129 case MP_PIT_CONTROL:
1135 1130 for (i = 0; i < 4; i++) {
1136 1131 if (value & 0xf) {
1137   - t = s->timer[i];
1138   - ptimer_set_limit(t->timer, t->limit, 0);
1139   - ptimer_set_freq(t->timer, t->freq);
1140   - ptimer_run(t->timer, 0);
  1132 + t = &s->timer[i];
  1133 + ptimer_set_limit(t->ptimer, t->limit, 0);
  1134 + ptimer_set_freq(t->ptimer, t->freq);
  1135 + ptimer_run(t->ptimer, 0);
1141 1136 }
1142 1137 value >>= 4;
1143 1138 }
... ... @@ -1162,29 +1157,28 @@ static CPUWriteMemoryFunc *mv88w8618_pit_writefn[] = {
1162 1157 mv88w8618_pit_write
1163 1158 };
1164 1159  
1165   -static void mv88w8618_pit_init(uint32_t base, qemu_irq *pic, int irq)
  1160 +static void mv88w8618_pit_init(SysBusDevice *dev)
1166 1161 {
1167 1162 int iomemtype;
1168   - mv88w8618_pit_state *s;
1169   -
1170   - s = qemu_mallocz(sizeof(mv88w8618_pit_state));
  1163 + mv88w8618_pit_state *s = FROM_SYSBUS(mv88w8618_pit_state, dev);
  1164 + int i;
1171 1165  
1172 1166 /* Letting them all run at 1 MHz is likely just a pragmatic
1173 1167 * simplification. */
1174   - s->timer[0] = mv88w8618_timer_init(1000000, pic[irq]);
1175   - s->timer[1] = mv88w8618_timer_init(1000000, pic[irq + 1]);
1176   - s->timer[2] = mv88w8618_timer_init(1000000, pic[irq + 2]);
1177   - s->timer[3] = mv88w8618_timer_init(1000000, pic[irq + 3]);
  1168 + for (i = 0; i < 4; i++) {
  1169 + mv88w8618_timer_init(dev, &s->timer[i], 1000000);
  1170 + }
1178 1171  
1179 1172 iomemtype = cpu_register_io_memory(0, mv88w8618_pit_readfn,
1180 1173 mv88w8618_pit_writefn, s);
1181   - cpu_register_physical_memory(base, MP_PIT_SIZE, iomemtype);
  1174 + sysbus_init_mmio(dev, MP_PIT_SIZE, iomemtype);
1182 1175 }
1183 1176  
1184 1177 /* Flash config register offsets */
1185 1178 #define MP_FLASHCFG_CFGR0 0x04
1186 1179  
1187 1180 typedef struct mv88w8618_flashcfg_state {
  1181 + SysBusDevice busdev;
1188 1182 uint32_t cfgr0;
1189 1183 } mv88w8618_flashcfg_state;
1190 1184  
... ... @@ -1226,17 +1220,15 @@ static CPUWriteMemoryFunc *mv88w8618_flashcfg_writefn[] = {
1226 1220 mv88w8618_flashcfg_write
1227 1221 };
1228 1222  
1229   -static void mv88w8618_flashcfg_init(uint32_t base)
  1223 +static void mv88w8618_flashcfg_init(SysBusDevice *dev)
1230 1224 {
1231 1225 int iomemtype;
1232   - mv88w8618_flashcfg_state *s;
1233   -
1234   - s = qemu_mallocz(sizeof(mv88w8618_flashcfg_state));
  1226 + mv88w8618_flashcfg_state *s = FROM_SYSBUS(mv88w8618_flashcfg_state, dev);
1235 1227  
1236 1228 s->cfgr0 = 0xfffe4285; /* Default as set by U-Boot for 8 MB flash */
1237 1229 iomemtype = cpu_register_io_memory(0, mv88w8618_flashcfg_readfn,
1238 1230 mv88w8618_flashcfg_writefn, s);
1239   - cpu_register_physical_memory(base, MP_FLASHCFG_SIZE, iomemtype);
  1231 + sysbus_init_mmio(dev, MP_FLASHCFG_SIZE, iomemtype);
1240 1232 }
1241 1233  
1242 1234 /* Misc register offsets */
... ... @@ -1317,13 +1309,13 @@ static CPUWriteMemoryFunc *mv88w8618_wlan_writefn[] = {
1317 1309 mv88w8618_wlan_write,
1318 1310 };
1319 1311  
1320   -static void mv88w8618_wlan_init(uint32_t base)
  1312 +static void mv88w8618_wlan_init(SysBusDevice *dev)
1321 1313 {
1322 1314 int iomemtype;
1323 1315  
1324 1316 iomemtype = cpu_register_io_memory(0, mv88w8618_wlan_readfn,
1325 1317 mv88w8618_wlan_writefn, NULL);
1326   - cpu_register_physical_memory(base, MP_WLAN_SIZE, iomemtype);
  1318 + sysbus_init_mmio(dev, MP_WLAN_SIZE, iomemtype);
1327 1319 }
1328 1320  
1329 1321 /* GPIO register offsets */
... ... @@ -1518,7 +1510,10 @@ static void musicpal_init(ram_addr_t ram_size,
1518 1510 const char *initrd_filename, const char *cpu_model)
1519 1511 {
1520 1512 CPUState *env;
1521   - qemu_irq *pic;
  1513 + qemu_irq *cpu_pic;
  1514 + qemu_irq pic[32];
  1515 + DeviceState *dev;
  1516 + int i;
1522 1517 int index;
1523 1518 unsigned long flash_size;
1524 1519  
... ... @@ -1530,7 +1525,7 @@ static void musicpal_init(ram_addr_t ram_size,
1530 1525 fprintf(stderr, "Unable to find CPU definition\n");
1531 1526 exit(1);
1532 1527 }
1533   - pic = arm_pic_init_cpu(env);
  1528 + cpu_pic = arm_pic_init_cpu(env);
1534 1529  
1535 1530 /* For now we use a fixed - the original - RAM size */
1536 1531 cpu_register_physical_memory(0, MP_RAM_DEFAULT_SIZE,
... ... @@ -1539,8 +1534,14 @@ static void musicpal_init(ram_addr_t ram_size,
1539 1534 sram_off = qemu_ram_alloc(MP_SRAM_SIZE);
1540 1535 cpu_register_physical_memory(MP_SRAM_BASE, MP_SRAM_SIZE, sram_off);
1541 1536  
1542   - pic = mv88w8618_pic_init(MP_PIC_BASE, pic[ARM_PIC_CPU_IRQ]);
1543   - mv88w8618_pit_init(MP_PIT_BASE, pic, MP_TIMER1_IRQ);
  1537 + dev = sysbus_create_simple("mv88w8618_pic", MP_PIC_BASE,
  1538 + cpu_pic[ARM_PIC_CPU_IRQ]);
  1539 + for (i = 0; i < 32; i++) {
  1540 + pic[i] = qdev_get_irq_sink(dev, i);
  1541 + }
  1542 + sysbus_create_varargs("mv88w8618_pit", MP_PIT_BASE, pic[MP_TIMER1_IRQ],
  1543 + pic[MP_TIMER2_IRQ], pic[MP_TIMER3_IRQ],
  1544 + pic[MP_TIMER4_IRQ], NULL);
1544 1545  
1545 1546 if (serial_hds[0])
1546 1547 serial_mm_init(MP_UART1_BASE, 2, pic[MP_UART1_IRQ], 1825000,
... ... @@ -1571,17 +1572,22 @@ static void musicpal_init(ram_addr_t ram_size,
1571 1572 2, 0x00BF, 0x236D, 0x0000, 0x0000,
1572 1573 0x5555, 0x2AAA);
1573 1574 }
1574   - mv88w8618_flashcfg_init(MP_FLASHCFG_BASE);
  1575 + sysbus_create_simple("mv88w8618_flashcfg", MP_FLASHCFG_BASE, NULL);
1575 1576  
1576   - musicpal_lcd_init();
  1577 + sysbus_create_simple("musicpal_lcd", MP_LCD_BASE, NULL);
1577 1578  
1578 1579 qemu_add_kbd_event_handler(musicpal_key_event, pic[MP_GPIO_IRQ]);
1579 1580  
1580   - mv88w8618_eth_init(&nd_table[0], MP_ETH_BASE, pic[MP_ETH_IRQ]);
  1581 + qemu_check_nic_model(&nd_table[0], "mv88w8618");
  1582 + dev = qdev_create(NULL, "mv88w8618_eth");
  1583 + qdev_set_netdev(dev, &nd_table[0]);
  1584 + qdev_init(dev);
  1585 + sysbus_mmio_map(sysbus_from_qdev(dev), 0, MP_ETH_BASE);
  1586 + sysbus_connect_irq(sysbus_from_qdev(dev), 0, pic[MP_ETH_IRQ]);
1581 1587  
1582 1588 mixer_i2c = musicpal_audio_init(pic[MP_AUDIO_IRQ]);
1583 1589  
1584   - mv88w8618_wlan_init(MP_WLAN_BASE);
  1590 + sysbus_create_simple("mv88w8618_wlan", MP_WLAN_BASE, NULL);
1585 1591  
1586 1592 musicpal_misc_init();
1587 1593 musicpal_gpio_init();
... ... @@ -1598,3 +1604,21 @@ QEMUMachine musicpal_machine = {
1598 1604 .desc = "Marvell 88w8618 / MusicPal (ARM926EJ-S)",
1599 1605 .init = musicpal_init,
1600 1606 };
  1607 +
  1608 +static void musicpal_register_devices(void)
  1609 +{
  1610 + sysbus_register_dev("mv88w8618_pic", sizeof(mv88w8618_pic_state),
  1611 + mv88w8618_pic_init);
  1612 + sysbus_register_dev("mv88w8618_pit", sizeof(mv88w8618_pit_state),
  1613 + mv88w8618_pit_init);
  1614 + sysbus_register_dev("mv88w8618_flashcfg", sizeof(mv88w8618_flashcfg_state),
  1615 + mv88w8618_flashcfg_init);
  1616 + sysbus_register_dev("mv88w8618_eth", sizeof(mv88w8618_eth_state),
  1617 + mv88w8618_eth_init);
  1618 + sysbus_register_dev("mv88w8618_wlan", sizeof(SysBusDevice),
  1619 + mv88w8618_wlan_init);
  1620 + sysbus_register_dev("musicpal_lcd", sizeof(musicpal_lcd_state),
  1621 + musicpal_lcd_init);
  1622 +}
  1623 +
  1624 +device_init(musicpal_register_devices)
... ...