X-Git-Url: https://git.proxmox.com/?a=blobdiff_plain;f=ioport.c;h=1a65addb666456414da8cda90ab1a4f923f806c2;hb=c309434ee97ff2ce46c97b0452bb0f83bfd4432b;hp=b345bd9abe1e833e2e1d69187d80a3a567cadaf1;hpb=84cbd63f87c1d246f51ec8eee5367a5588f367fd;p=mirror_qemu.git diff --git a/ioport.c b/ioport.c index b345bd9abe..1a65addb66 100644 --- a/ioport.c +++ b/ioport.c @@ -25,19 +25,14 @@ * splitted out ioport related stuffs from vl.c. */ +#include "qemu/osdep.h" +#include "qemu-common.h" +#include "cpu.h" #include "exec/ioport.h" -#include "trace.h" +#include "trace-root.h" #include "exec/memory.h" #include "exec/address-spaces.h" -//#define DEBUG_IOPORT - -#ifdef DEBUG_IOPORT -# define LOG_IOPORT(...) qemu_log_mask(CPU_LOG_IOPORT, ## __VA_ARGS__) -#else -# define LOG_IOPORT(...) do { } while (0) -#endif - typedef struct MemoryRegionPortioList { MemoryRegion mr; void *portio_opaque; @@ -60,68 +55,62 @@ const MemoryRegionOps unassigned_io_ops = { .endianness = DEVICE_NATIVE_ENDIAN, }; -void cpu_outb(pio_addr_t addr, uint8_t val) +void cpu_outb(uint32_t addr, uint8_t val) { - LOG_IOPORT("outb: %04"FMT_pioaddr" %02"PRIx8"\n", addr, val); - trace_cpu_out(addr, val); + trace_cpu_out(addr, 'b', val); address_space_write(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, &val, 1); } -void cpu_outw(pio_addr_t addr, uint16_t val) +void cpu_outw(uint32_t addr, uint16_t val) { uint8_t buf[2]; - LOG_IOPORT("outw: %04"FMT_pioaddr" %04"PRIx16"\n", addr, val); - trace_cpu_out(addr, val); + trace_cpu_out(addr, 'w', val); stw_p(buf, val); address_space_write(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, buf, 2); } -void cpu_outl(pio_addr_t addr, uint32_t val) +void cpu_outl(uint32_t addr, uint32_t val) { uint8_t buf[4]; - LOG_IOPORT("outl: %04"FMT_pioaddr" %08"PRIx32"\n", addr, val); - trace_cpu_out(addr, val); + trace_cpu_out(addr, 'l', val); stl_p(buf, val); address_space_write(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, buf, 4); } -uint8_t cpu_inb(pio_addr_t addr) +uint8_t cpu_inb(uint32_t addr) { uint8_t val; address_space_read(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, &val, 1); - trace_cpu_in(addr, val); - LOG_IOPORT("inb : %04"FMT_pioaddr" %02"PRIx8"\n", addr, val); + trace_cpu_in(addr, 'b', val); return val; } -uint16_t cpu_inw(pio_addr_t addr) +uint16_t cpu_inw(uint32_t addr) { uint8_t buf[2]; uint16_t val; address_space_read(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, buf, 2); val = lduw_p(buf); - trace_cpu_in(addr, val); - LOG_IOPORT("inw : %04"FMT_pioaddr" %04"PRIx16"\n", addr, val); + trace_cpu_in(addr, 'w', val); return val; } -uint32_t cpu_inl(pio_addr_t addr) +uint32_t cpu_inl(uint32_t addr) { uint8_t buf[4]; uint32_t val; address_space_read(&address_space_io, addr, MEMTXATTRS_UNSPECIFIED, buf, 4); val = ldl_p(buf); - trace_cpu_in(addr, val); - LOG_IOPORT("inl : %04"FMT_pioaddr" %08"PRIx32"\n", addr, val); + trace_cpu_in(addr, 'l', val); return val; } @@ -191,9 +180,14 @@ static uint64_t portio_read(void *opaque, hwaddr addr, unsigned size) data = mrp->read(mrpio->portio_opaque, mrp->base + addr); } else if (size == 2) { mrp = find_portio(mrpio, addr, 1, false); - assert(mrp); - data = mrp->read(mrpio->portio_opaque, mrp->base + addr) | - (mrp->read(mrpio->portio_opaque, mrp->base + addr + 1) << 8); + if (mrp) { + data = mrp->read(mrpio->portio_opaque, mrp->base + addr); + if (addr + 1 < mrp->offset + mrp->len) { + data |= mrp->read(mrpio->portio_opaque, mrp->base + addr + 1) << 8; + } else { + data |= 0xff00; + } + } } return data; } @@ -208,9 +202,12 @@ static void portio_write(void *opaque, hwaddr addr, uint64_t data, mrp->write(mrpio->portio_opaque, mrp->base + addr, data); } else if (size == 2) { mrp = find_portio(mrpio, addr, 1, true); - assert(mrp); - mrp->write(mrpio->portio_opaque, mrp->base + addr, data & 0xff); - mrp->write(mrpio->portio_opaque, mrp->base + addr + 1, data >> 8); + if (mrp) { + mrp->write(mrpio->portio_opaque, mrp->base + addr, data & 0xff); + if (addr + 1 < mrp->offset + mrp->len) { + mrp->write(mrpio->portio_opaque, mrp->base + addr + 1, data >> 8); + } + } } } @@ -243,10 +240,6 @@ static void portio_list_add_1(PortioList *piolist, mrpio->ports[i].base = start + off_low; } - /* - * Use an alias so that the callback is called with an absolute address, - * rather than an offset relative to to start + off_low. - */ memory_region_init_io(&mrpio->mr, piolist->owner, &portio_ops, mrpio, piolist->name, off_high - off_low); if (piolist->flush_coalesced_mmio) { @@ -269,7 +262,7 @@ void portio_list_add(PortioList *piolist, /* Handle the first entry specially. */ off_last = off_low = pio_start->offset; - off_high = off_low + pio_start->len; + off_high = off_low + pio_start->len + pio_start->size - 1; count = 1; for (pio = pio_start + 1; pio->size != 0; pio++, count++) { @@ -284,10 +277,10 @@ void portio_list_add(PortioList *piolist, /* ... and start collecting anew. */ pio_start = pio; off_low = off_last; - off_high = off_low + pio->len; + off_high = off_low + pio->len + pio_start->size - 1; count = 0; } else if (off_last + pio->len > off_high) { - off_high = off_last + pio->len; + off_high = off_last + pio->len + pio_start->size - 1; } }