Merge branch 'upstream-merge'
[qemu-kvm.git] / hw / testdev.c
blob21125d54e52854b20104a2ba4ae0c2ed394a4f62
1 #include <sys/mman.h>
2 #include "hw.h"
3 #include "qdev.h"
4 #include "isa.h"
6 struct testdev {
7 ISADevice dev;
8 MemoryRegion iomem;
9 CharDriverState *chr;
12 #define TYPE_TESTDEV "testdev"
13 #define TESTDEV(obj) \
14 OBJECT_CHECK(struct testdev, (obj), TYPE_TESTDEV)
16 static void test_device_serial_write(void *opaque, uint32_t addr, uint32_t data)
18 struct testdev *dev = opaque;
19 uint8_t buf[1] = { data };
21 if (dev->chr) {
22 qemu_chr_fe_write(dev->chr, buf, 1);
26 static void test_device_exit(void *opaque, uint32_t addr, uint32_t data)
28 exit(data);
31 static uint32_t test_device_memsize_read(void *opaque, uint32_t addr)
33 return ram_size;
36 static void test_device_irq_line(void *opaque, uint32_t addr, uint32_t data)
38 struct testdev *dev = opaque;
40 qemu_set_irq(isa_get_irq(&dev->dev, addr - 0x2000), !!data);
43 static uint32 test_device_ioport_data;
45 static void test_device_ioport_write(void *opaque, uint32_t addr, uint32_t data)
47 test_device_ioport_data = data;
50 static uint32_t test_device_ioport_read(void *opaque, uint32_t addr)
52 return test_device_ioport_data;
55 static void test_device_flush_page(void *opaque, uint32_t addr, uint32_t data)
57 target_phys_addr_t len = 4096;
58 void *a = cpu_physical_memory_map(data & ~0xffful, &len, 0);
60 mprotect(a, 4096, PROT_NONE);
61 mprotect(a, 4096, PROT_READ|PROT_WRITE);
62 cpu_physical_memory_unmap(a, len, 0, 0);
65 static char *iomem_buf;
67 static uint32_t test_iomem_readb(void *opaque, target_phys_addr_t addr)
69 return iomem_buf[addr];
72 static uint32_t test_iomem_readw(void *opaque, target_phys_addr_t addr)
74 return *(uint16_t*)(iomem_buf + addr);
77 static uint32_t test_iomem_readl(void *opaque, target_phys_addr_t addr)
79 return *(uint32_t*)(iomem_buf + addr);
82 static void test_iomem_writeb(void *opaque, target_phys_addr_t addr, uint32_t val)
84 iomem_buf[addr] = val;
87 static void test_iomem_writew(void *opaque, target_phys_addr_t addr, uint32_t val)
89 *(uint16_t*)(iomem_buf + addr) = val;
92 static void test_iomem_writel(void *opaque, target_phys_addr_t addr, uint32_t val)
94 *(uint32_t*)(iomem_buf + addr) = val;
97 static const MemoryRegionOps test_iomem_ops = {
98 .old_mmio = {
99 .read = { test_iomem_readb, test_iomem_readw, test_iomem_readl, },
100 .write = { test_iomem_writeb, test_iomem_writew, test_iomem_writel, },
102 .endianness = DEVICE_LITTLE_ENDIAN,
105 static int init_test_device(ISADevice *isa)
107 struct testdev *dev = DO_UPCAST(struct testdev, dev, isa);
109 register_ioport_write(0xf1, 1, 1, test_device_serial_write, dev);
110 register_ioport_write(0xf4, 1, 4, test_device_exit, dev);
111 register_ioport_read(0xd1, 1, 4, test_device_memsize_read, dev);
112 register_ioport_read(0xe0, 1, 1, test_device_ioport_read, dev);
113 register_ioport_write(0xe0, 1, 1, test_device_ioport_write, dev);
114 register_ioport_read(0xe0, 1, 2, test_device_ioport_read, dev);
115 register_ioport_write(0xe0, 1, 2, test_device_ioport_write, dev);
116 register_ioport_read(0xe0, 1, 4, test_device_ioport_read, dev);
117 register_ioport_write(0xe0, 1, 4, test_device_ioport_write, dev);
118 register_ioport_write(0xe4, 1, 4, test_device_flush_page, dev);
119 register_ioport_write(0x2000, 24, 1, test_device_irq_line, NULL);
120 iomem_buf = g_malloc0(0x10000);
121 memory_region_init_io(&dev->iomem, &test_iomem_ops, dev,
122 "testdev", 0x10000);
123 memory_region_add_subregion(isa_address_space(&dev->dev), 0xff000000,
124 &dev->iomem);
125 return 0;
128 static Property testdev_isa_properties[] = {
129 DEFINE_PROP_CHR("chardev", struct testdev, chr),
130 DEFINE_PROP_END_OF_LIST(),
133 static void testdev_class_init(ObjectClass *klass, void *data)
135 DeviceClass *dc = DEVICE_CLASS(klass);
136 ISADeviceClass *k = ISA_DEVICE_CLASS(klass);
138 k->init = init_test_device;
139 dc->props = testdev_isa_properties;
142 static TypeInfo testdev_info = {
143 .name = "testdev",
144 .parent = TYPE_ISA_DEVICE,
145 .instance_size = sizeof(struct testdev),
146 .class_init = testdev_class_init,
149 static void testdev_register_types(void)
151 type_register_static(&testdev_info);
154 type_init(testdev_register_types)