/*
 * QEMU HP Artist Emulation
 *
 * Copyright (c) 2019 Sven Schnelle <svens@stackframe.org>
 *
 * This work is licensed under the terms of the GNU GPL, version 2 or later.
 */

#include "qemu/osdep.h"
#include "qemu-common.h"
#include "qemu/error-report.h"
#include "qemu/log.h"
#include "qemu/module.h"
#include "qemu/units.h"
#include "qapi/error.h"
#include "hw/sysbus.h"
#include "hw/loader.h"
#include "hw/qdev-core.h"
#include "hw/qdev-properties.h"
#include "migration/vmstate.h"
#include "ui/console.h"
#include "trace.h"
#include "framebuffer.h"
#include "qom/object.h"

#define TYPE_ARTIST "artist"
OBJECT_DECLARE_SIMPLE_TYPE(ARTISTState, ARTIST)

#ifdef HOST_WORDS_BIGENDIAN
#define ROP8OFF(_i) (3 - (_i))
#else
#define ROP8OFF
#endif

struct vram_buffer {
    MemoryRegion mr;
    uint8_t *data;
    unsigned int size;
    unsigned int width;
    unsigned int height;
};

struct ARTISTState {
    SysBusDevice parent_obj;

    QemuConsole *con;
    MemoryRegion vram_mem;
    MemoryRegion mem_as_root;
    MemoryRegion reg;
    MemoryRegionSection fbsection;

    void *vram_int_mr;
    AddressSpace as;

    struct vram_buffer vram_buffer[16];

    uint16_t width;
    uint16_t height;
    uint16_t depth;

    uint32_t fg_color;
    uint32_t bg_color;

    uint32_t vram_char_y;
    uint32_t vram_bitmask;

    uint32_t vram_start;
    uint32_t vram_pos;

    uint32_t vram_size;

    uint32_t blockmove_source;
    uint32_t blockmove_dest;
    uint32_t blockmove_size;

    uint32_t line_size;
    uint32_t line_end;
    uint32_t line_xy;
    uint32_t line_pattern_start;
    uint32_t line_pattern_skip;

    uint32_t cursor_pos;

    uint32_t cursor_height;
    uint32_t cursor_width;

    uint32_t plane_mask;

    uint32_t reg_100080;
    uint32_t reg_300200;
    uint32_t reg_300208;
    uint32_t reg_300218;

    uint32_t cmap_bm_access;
    uint32_t dst_bm_access;
    uint32_t src_bm_access;
    uint32_t control_plane;
    uint32_t transfer_data;
    uint32_t image_bitmap_op;

    uint32_t font_write1;
    uint32_t font_write2;
    uint32_t font_write_pos_y;

    int draw_line_pattern;
};

typedef enum {
    ARTIST_BUFFER_AP = 1,
    ARTIST_BUFFER_OVERLAY = 2,
    ARTIST_BUFFER_CURSOR1 = 6,
    ARTIST_BUFFER_CURSOR2 = 7,
    ARTIST_BUFFER_ATTRIBUTE = 13,
    ARTIST_BUFFER_CMAP = 15,
} artist_buffer_t;

typedef enum {
    VRAM_IDX = 0x1004a0,
    VRAM_BITMASK = 0x1005a0,
    VRAM_WRITE_INCR_X = 0x100600,
    VRAM_WRITE_INCR_X2 = 0x100604,
    VRAM_WRITE_INCR_Y = 0x100620,
    VRAM_START = 0x100800,
    BLOCK_MOVE_SIZE = 0x100804,
    BLOCK_MOVE_SOURCE = 0x100808,
    TRANSFER_DATA = 0x100820,
    FONT_WRITE_INCR_Y = 0x1008a0,
    VRAM_START_TRIGGER = 0x100a00,
    VRAM_SIZE_TRIGGER = 0x100a04,
    FONT_WRITE_START = 0x100aa0,
    BLOCK_MOVE_DEST_TRIGGER = 0x100b00,
    BLOCK_MOVE_SIZE_TRIGGER = 0x100b04,
    LINE_XY = 0x100ccc,
    PATTERN_LINE_START = 0x100ecc,
    LINE_SIZE = 0x100e04,
    LINE_END = 0x100e44,
    CMAP_BM_ACCESS = 0x118000,
    DST_BM_ACCESS = 0x118004,
    SRC_BM_ACCESS = 0x118008,
    CONTROL_PLANE = 0x11800c,
    FG_COLOR = 0x118010,
    BG_COLOR = 0x118014,
    PLANE_MASK = 0x118018,
    IMAGE_BITMAP_OP = 0x11801c,
    CURSOR_POS = 0x300100,
    CURSOR_CTRL = 0x300104,
} artist_reg_t;

typedef enum {
    ARTIST_ROP_CLEAR = 0,
    ARTIST_ROP_COPY = 3,
    ARTIST_ROP_XOR = 6,
    ARTIST_ROP_NOT_DST = 10,
    ARTIST_ROP_SET = 15,
} artist_rop_t;

#define REG_NAME(_x) case _x: return " "#_x;
static const char *artist_reg_name(uint64_t addr)
{
    switch ((artist_reg_t)addr) {
    REG_NAME(VRAM_IDX);
    REG_NAME(VRAM_BITMASK);
    REG_NAME(VRAM_WRITE_INCR_X);
    REG_NAME(VRAM_WRITE_INCR_X2);
    REG_NAME(VRAM_WRITE_INCR_Y);
    REG_NAME(VRAM_START);
    REG_NAME(BLOCK_MOVE_SIZE);
    REG_NAME(BLOCK_MOVE_SOURCE);
    REG_NAME(FG_COLOR);
    REG_NAME(BG_COLOR);
    REG_NAME(PLANE_MASK);
    REG_NAME(VRAM_START_TRIGGER);
    REG_NAME(VRAM_SIZE_TRIGGER);
    REG_NAME(BLOCK_MOVE_DEST_TRIGGER);
    REG_NAME(BLOCK_MOVE_SIZE_TRIGGER);
    REG_NAME(TRANSFER_DATA);
    REG_NAME(CONTROL_PLANE);
    REG_NAME(IMAGE_BITMAP_OP);
    REG_NAME(CMAP_BM_ACCESS);
    REG_NAME(DST_BM_ACCESS);
    REG_NAME(SRC_BM_ACCESS);
    REG_NAME(CURSOR_POS);
    REG_NAME(CURSOR_CTRL);
    REG_NAME(LINE_XY);
    REG_NAME(PATTERN_LINE_START);
    REG_NAME(LINE_SIZE);
    REG_NAME(LINE_END);
    REG_NAME(FONT_WRITE_INCR_Y);
    REG_NAME(FONT_WRITE_START);
    }
    return "";
}
#undef REG_NAME

/* artist has a fixed line length of 2048 bytes. */
#define ADDR_TO_Y(addr) extract32(addr, 11, 11)
#define ADDR_TO_X(addr) extract32(addr, 0, 11)

static int16_t artist_get_x(uint32_t reg)
{
    return reg >> 16;
}

static int16_t artist_get_y(uint32_t reg)
{
    return reg & 0xffff;
}

static void artist_invalidate_lines(struct vram_buffer *buf,
                                    int starty, int height)
{
    int start = starty * buf->width;
    int size;

    if (starty + height > buf->height)
        height = buf->height - starty;

    size = height * buf->width;

    if (start + size <= buf->size) {
        memory_region_set_dirty(&buf->mr, start, size);
    }
}

static int vram_write_pix_per_transfer(ARTISTState *s)
{
    if (s->cmap_bm_access) {
        return 1 << ((s->cmap_bm_access >> 27) & 0x0f);
    } else {
        return 1 << ((s->dst_bm_access >> 27) & 0x0f);
    }
}

static int vram_pixel_length(ARTISTState *s)
{
    if (s->cmap_bm_access) {
        return (s->cmap_bm_access >> 24) & 0x07;
    } else {
        return (s->dst_bm_access >> 24) & 0x07;
    }
}

static int vram_write_bufidx(ARTISTState *s)
{
    if (s->cmap_bm_access) {
        return (s->cmap_bm_access >> 12) & 0x0f;
    } else {
        return (s->dst_bm_access >> 12) & 0x0f;
    }
}

static int vram_read_bufidx(ARTISTState *s)
{
    if (s->cmap_bm_access) {
        return (s->cmap_bm_access >> 12) & 0x0f;
    } else {
        return (s->src_bm_access >> 12) & 0x0f;
    }
}

static struct vram_buffer *vram_read_buffer(ARTISTState *s)
{
    return &s->vram_buffer[vram_read_bufidx(s)];
}

static struct vram_buffer *vram_write_buffer(ARTISTState *s)
{
    return &s->vram_buffer[vram_write_bufidx(s)];
}

static uint8_t artist_get_color(ARTISTState *s)
{
    if (s->image_bitmap_op & 2) {
        return s->fg_color;
    } else {
        return s->bg_color;
    }
}

static artist_rop_t artist_get_op(ARTISTState *s)
{
    return (s->image_bitmap_op >> 8) & 0xf;
}

static void artist_rop8(ARTISTState *s, struct vram_buffer *buf,
                        unsigned int offset, uint8_t val)
{
    const artist_rop_t op = artist_get_op(s);
    uint8_t plane_mask;
    uint8_t *dst;

    if (offset >= buf->size) {
        qemu_log_mask(LOG_GUEST_ERROR,
                      "rop8 offset:%u bufsize:%u\n", offset, buf->size);
        return;
    }
    dst = buf->data + offset;
    plane_mask = s->plane_mask & 0xff;

    switch (op) {
    case ARTIST_ROP_CLEAR:
        *dst &= ~plane_mask;
        break;

    case ARTIST_ROP_COPY:
        *dst = (*dst & ~plane_mask) | (val & plane_mask);
        break;

    case ARTIST_ROP_XOR:
        *dst ^= val & plane_mask;
        break;

    case ARTIST_ROP_NOT_DST:
        *dst ^= plane_mask;
        break;

    case ARTIST_ROP_SET:
        *dst |= plane_mask;
        break;

    default:
        qemu_log_mask(LOG_UNIMP, "%s: unsupported rop %d\n", __func__, op);
        break;
    }
}

static void artist_get_cursor_pos(ARTISTState *s, int *x, int *y)
{
    /*
     * Don't know whether these magic offset values are configurable via
     * some register. They are the same for all resolutions, so don't
     * bother about it.
     */

    *y = 0x47a - artist_get_y(s->cursor_pos);
    *x = ((artist_get_x(s->cursor_pos) - 338) / 2);

    if (*x > s->width) {
        *x = 0;
    }

    if (*y > s->height) {
        *y = 0;
    }
}

static void artist_invalidate_cursor(ARTISTState *s)
{
    int x, y;
    artist_get_cursor_pos(s, &x, &y);
    artist_invalidate_lines(&s->vram_buffer[ARTIST_BUFFER_AP],
                            y, s->cursor_height);
}

static void vram_bit_write(ARTISTState *s, int posy, bool incr_x,
                           int size, uint32_t data)
{
    struct vram_buffer *buf;
    uint32_t vram_bitmask = s->vram_bitmask;
    int mask, i, pix_count, pix_length;
    unsigned int posx, offset, width;
    uint8_t *data8, *p;

    pix_count = vram_write_pix_per_transfer(s);
    pix_length = vram_pixel_length(s);

    buf = vram_write_buffer(s);
    width = buf->width;

    if (s->cmap_bm_access) {
        offset = s->vram_pos;
    } else {
        posx = ADDR_TO_X(s->vram_pos >> 2);
        posy += ADDR_TO_Y(s->vram_pos >> 2);
        offset = posy * width + posx;
    }

    if (!buf->size || offset >= buf->size) {
        return;
    }

    p = buf->data;

    if (pix_count > size * 8) {
        pix_count = size * 8;
    }

    switch (pix_length) {
    case 0:
        if (s->image_bitmap_op & 0x20000000) {
            data &= vram_bitmask;
        }

        for (i = 0; i < pix_count; i++) {
            uint32_t off = offset + pix_count - 1 - i;
            if (off < buf->size) {
                artist_rop8(s, buf, off,
                            (data & 1) ? (s->plane_mask >> 24) : 0);
            }
            data >>= 1;
        }
        memory_region_set_dirty(&buf->mr, offset, pix_count);
        break;

    case 3:
        if (s->cmap_bm_access) {
            if (offset + 3 < buf->size) {
                *(uint32_t *)(p + offset) = data;
            }
            break;
        }
        data8 = (uint8_t *)&data;

        for (i = 3; i >= 0; i--) {
            if (!(s->image_bitmap_op & 0x20000000) ||
                s->vram_bitmask & (1 << (28 + i))) {
                uint32_t off = offset + 3 - i;
                if (off < buf->size) {
                    artist_rop8(s, buf, off, data8[ROP8OFF(i)]);
                }
            }
        }
        memory_region_set_dirty(&buf->mr, offset, 3);
        break;

    case 6:
        switch (size) {
        default:
        case 4:
            vram_bitmask = s->vram_bitmask;
            break;

        case 2:
            vram_bitmask = s->vram_bitmask >> 16;
            break;

        case 1:
            vram_bitmask = s->vram_bitmask >> 24;
            break;
        }

        for (i = 0; i < pix_count && offset + i < buf->size; i++) {
            mask = 1 << (pix_count - 1 - i);

            if (!(s->image_bitmap_op & 0x20000000) ||
                (vram_bitmask & mask)) {
                if (data & mask) {
                    artist_rop8(s, buf, offset + i, s->fg_color);
                } else {
                    if (!(s->image_bitmap_op & 0x10000002)) {
                        artist_rop8(s, buf, offset + i, s->bg_color);
                    }
                }
            }
        }
        memory_region_set_dirty(&buf->mr, offset, pix_count);
        break;

    default:
        qemu_log_mask(LOG_UNIMP, "%s: unknown pixel length %d\n",
                      __func__, pix_length);
        break;
    }

    if (incr_x) {
        if (s->cmap_bm_access) {
            s->vram_pos += 4;
        } else {
            s->vram_pos += pix_count << 2;
        }
    }

    if (vram_write_bufidx(s) == ARTIST_BUFFER_CURSOR1 ||
        vram_write_bufidx(s) == ARTIST_BUFFER_CURSOR2) {
        artist_invalidate_cursor(s);
    }
}

static void block_move(ARTISTState *s,
                       unsigned int source_x, unsigned int source_y,
                       unsigned int dest_x,   unsigned int dest_y,
                       unsigned int width,    unsigned int height)
{
    struct vram_buffer *buf;
    int line, endline, lineincr, startcolumn, endcolumn, columnincr, column;
    unsigned int dst, src;

    trace_artist_block_move(source_x, source_y, dest_x, dest_y, width, height);

    if (s->control_plane != 0) {
        /* We don't support CONTROL_PLANE accesses */
        qemu_log_mask(LOG_UNIMP, "%s: CONTROL_PLANE: %08x\n", __func__,
                      s->control_plane);
        return;
    }

    buf = &s->vram_buffer[ARTIST_BUFFER_AP];
    if (height > buf->height) {
        height = buf->height;
    }
    if (width > buf->width) {
        width = buf->width;
    }

    if (dest_y > source_y) {
        /* move down */
        line = height - 1;
        endline = -1;
        lineincr = -1;
    } else {
        /* move up */
        line = 0;
        endline = height;
        lineincr = 1;
    }

    if (dest_x > source_x) {
        /* move right */
        startcolumn = width - 1;
        endcolumn = -1;
        columnincr = -1;
    } else {
        /* move left */
        startcolumn = 0;
        endcolumn = width;
        columnincr = 1;
    }

    for ( ; line != endline; line += lineincr) {
        src = source_x + ((line + source_y) * buf->width) + startcolumn;
        dst = dest_x + ((line + dest_y) * buf->width) + startcolumn;

        for (column = startcolumn; column != endcolumn; column += columnincr) {
            if (dst >= buf->size || src >= buf->size) {
                continue;
            }
            artist_rop8(s, buf, dst, buf->data[src]);
            src += columnincr;
            dst += columnincr;
        }
    }

    artist_invalidate_lines(buf, dest_y, height);
}

static void fill_window(ARTISTState *s,
                        unsigned int startx, unsigned int starty,
                        unsigned int width,  unsigned int height)
{
    unsigned int offset;
    uint8_t color = artist_get_color(s);
    struct vram_buffer *buf;
    int x, y;

    trace_artist_fill_window(startx, starty, width, height,
                             s->image_bitmap_op, s->control_plane);

    if (s->control_plane != 0) {
        /* We don't support CONTROL_PLANE accesses */
        qemu_log_mask(LOG_UNIMP, "%s: CONTROL_PLANE: %08x\n", __func__,
                      s->control_plane);
        return;
    }

    if (s->reg_100080 == 0x7d) {
        /*
         * Not sure what this register really does, but
         * 0x7d seems to enable autoincremt of the Y axis
         * by the current block move height.
         */
        height = artist_get_y(s->blockmove_size);
        s->vram_start += height;
    }

    buf = &s->vram_buffer[ARTIST_BUFFER_AP];

    for (y = starty; y < starty + height; y++) {
        offset = y * s->width;

        for (x = startx; x < startx + width; x++) {
            artist_rop8(s, buf, offset + x, color);
        }
    }
    artist_invalidate_lines(buf, starty, height);
}

static void draw_line(ARTISTState *s,
                      unsigned int x1, unsigned int y1,
                      unsigned int x2, unsigned int y2,
                      bool update_start, int skip_pix, int max_pix)
{
    struct vram_buffer *buf = &s->vram_buffer[ARTIST_BUFFER_AP];
    uint8_t color;
    int dx, dy, t, e, x, y, incy, diago, horiz;
    bool c1;

    trace_artist_draw_line(x1, y1, x2, y2);

    if ((x1 >= buf->width && x2 >= buf->width) ||
        (y1 >= buf->height && y2 >= buf->height)) {
	return;
    }


    if (update_start) {
        s->vram_start = (x2 << 16) | y2;
    }

    if (x2 > x1) {
        dx = x2 - x1;
    } else {
        dx = x1 - x2;
    }
    if (y2 > y1) {
        dy = y2 - y1;
    } else {
        dy = y1 - y2;
    }

    c1 = false;
    if (dy > dx) {
        t = y2;
        y2 = x2;
        x2 = t;

        t = y1;
        y1 = x1;
        x1 = t;

        t = dx;
        dx = dy;
        dy = t;

        c1 = true;
    }

    if (x1 > x2) {
        t = y2;
        y2 = y1;
        y1 = t;

        t = x1;
        x1 = x2;
        x2 = t;
    }

    horiz = dy << 1;
    diago = (dy - dx) << 1;
    e = (dy << 1) - dx;

    if (y1 <= y2) {
        incy = 1;
    } else {
        incy = -1;
    }
    x = x1;
    y = y1;
    color = artist_get_color(s);

    do {
        unsigned int ofs;

        if (c1) {
            ofs = x * s->width + y;
        } else {
            ofs = y * s->width + x;
        }

        if (skip_pix > 0) {
            skip_pix--;
        } else {
            artist_rop8(s, buf, ofs, color);
        }

        if (e > 0) {
            y  += incy;
            e  += diago;
        } else {
            e += horiz;
        }
        x++;
    } while (x <= x2 && (max_pix == -1 || --max_pix > 0));
    if (c1)
        artist_invalidate_lines(buf, x, dy+1);
    else
        artist_invalidate_lines(buf, y, dx+1);
}

static void draw_line_pattern_start(ARTISTState *s)
{

    int startx = artist_get_x(s->vram_start);
    int starty = artist_get_y(s->vram_start);
    int endx = artist_get_x(s->blockmove_size);
    int endy = artist_get_y(s->blockmove_size);
    int pstart = s->line_pattern_start >> 16;

    draw_line(s, startx, starty, endx, endy, false, -1, pstart);
    s->line_pattern_skip = pstart;
}

static void draw_line_pattern_next(ARTISTState *s)
{

    int startx = artist_get_x(s->vram_start);
    int starty = artist_get_y(s->vram_start);
    int endx = artist_get_x(s->blockmove_size);
    int endy = artist_get_y(s->blockmove_size);
    int line_xy = s->line_xy >> 16;

    draw_line(s, startx, starty, endx, endy, false, s->line_pattern_skip,
              s->line_pattern_skip + line_xy);
    s->line_pattern_skip += line_xy;
    s->image_bitmap_op ^= 2;
}

static void draw_line_size(ARTISTState *s, bool update_start)
{

    int startx = artist_get_x(s->vram_start);
    int starty = artist_get_y(s->vram_start);
    int endx = artist_get_x(s->line_size);
    int endy = artist_get_y(s->line_size);

    draw_line(s, startx, starty, endx, endy, update_start, -1, -1);
}

static void draw_line_xy(ARTISTState *s, bool update_start)
{

    int startx = artist_get_x(s->vram_start);
    int starty = artist_get_y(s->vram_start);
    int sizex = artist_get_x(s->blockmove_size);
    int sizey = artist_get_y(s->blockmove_size);
    int linexy = s->line_xy >> 16;
    int endx, endy;

    endx = startx;
    endy = starty;

    if (sizex > 0) {
        endx = startx + linexy;
    }

    if (sizex < 0) {
        endx = startx;
        startx -= linexy;
    }

    if (sizey > 0) {
        endy = starty + linexy;
    }

    if (sizey < 0) {
        endy = starty;
        starty -= linexy;
    }

    if (startx < 0) {
        startx = 0;
    }

    if (endx < 0) {
        endx = 0;
    }

    if (starty < 0) {
        starty = 0;
    }

    if (endy < 0) {
        endy = 0;
    }

    draw_line(s, startx, starty, endx, endy, false, -1, -1);
}

static void draw_line_end(ARTISTState *s, bool update_start)
{

    int startx = artist_get_x(s->vram_start);
    int starty = artist_get_y(s->vram_start);
    int endx = artist_get_x(s->line_end);
    int endy = artist_get_y(s->line_end);

    draw_line(s, startx, starty, endx, endy, update_start, -1, -1);
}

static void font_write16(ARTISTState *s, uint16_t val)
{
    struct vram_buffer *buf;
    uint32_t color = (s->image_bitmap_op & 2) ? s->fg_color : s->bg_color;
    uint16_t mask;
    int i;

    unsigned int startx = artist_get_x(s->vram_start);
    unsigned int starty = artist_get_y(s->vram_start) + s->font_write_pos_y;
    unsigned int offset = starty * s->width + startx;

    buf = &s->vram_buffer[ARTIST_BUFFER_AP];

    if (startx >= buf->width || starty >= buf->height ||
        offset + 16 >= buf->size) {
        return;
    }

    for (i = 0; i < 16; i++) {
        mask = 1 << (15 - i);
        if (val & mask) {
            artist_rop8(s, buf, offset + i, color);
        } else {
            if (!(s->image_bitmap_op & 0x20000000)) {
                artist_rop8(s, buf, offset + i, s->bg_color);
            }
        }
    }
    artist_invalidate_lines(buf, starty, 1);
}

static void font_write(ARTISTState *s, uint32_t val)
{
    font_write16(s, val >> 16);
    if (++s->font_write_pos_y == artist_get_y(s->blockmove_size)) {
        s->vram_start += (s->blockmove_size & 0xffff0000);
        return;
    }

    font_write16(s, val & 0xffff);
    if (++s->font_write_pos_y == artist_get_y(s->blockmove_size)) {
        s->vram_start += (s->blockmove_size & 0xffff0000);
        return;
    }
}

static void combine_write_reg(hwaddr addr, uint64_t val, int size, void *out)
{
    /*
     * FIXME: is there a qemu helper for this?
     */

#ifndef HOST_WORDS_BIGENDIAN
    addr ^= 3;
#endif

    switch (size) {
    case 1:
        *(uint8_t *)(out + (addr & 3)) = val;
        break;

    case 2:
        *(uint16_t *)(out + (addr & 2)) = val;
        break;

    case 4:
        *(uint32_t *)out = val;
        break;

    default:
        qemu_log_mask(LOG_UNIMP, "unsupported write size: %d\n", size);
    }
}

static void artist_reg_write(void *opaque, hwaddr addr, uint64_t val,
                             unsigned size)
{
    ARTISTState *s = opaque;
    int width, height;

    trace_artist_reg_write(size, addr, artist_reg_name(addr & ~3ULL), val);

    switch (addr & ~3ULL) {
    case 0x100080:
        combine_write_reg(addr, val, size, &s->reg_100080);
        break;

    case FG_COLOR:
        combine_write_reg(addr, val, size, &s->fg_color);
        break;

    case BG_COLOR:
        combine_write_reg(addr, val, size, &s->bg_color);
        break;

    case VRAM_BITMASK:
        combine_write_reg(addr, val, size, &s->vram_bitmask);
        break;

    case VRAM_WRITE_INCR_Y:
        vram_bit_write(s, s->vram_char_y++, false, size, val);
        break;

    case VRAM_WRITE_INCR_X:
    case VRAM_WRITE_INCR_X2:
        vram_bit_write(s, s->vram_char_y, true, size, val);
        break;

    case VRAM_IDX:
        combine_write_reg(addr, val, size, &s->vram_pos);
        s->vram_char_y = 0;
        s->draw_line_pattern = 0;
        break;

    case VRAM_START:
        combine_write_reg(addr, val, size, &s->vram_start);
        s->draw_line_pattern = 0;
        break;

    case VRAM_START_TRIGGER:
        combine_write_reg(addr, val, size, &s->vram_start);
        fill_window(s, artist_get_x(s->vram_start),
                    artist_get_y(s->vram_start),
                    artist_get_x(s->blockmove_size),
                    artist_get_y(s->blockmove_size));
        break;

    case VRAM_SIZE_TRIGGER:
        combine_write_reg(addr, val, size, &s->vram_size);

        if (size == 2 && !(addr & 2)) {
            height = artist_get_y(s->blockmove_size);
        } else {
            height = artist_get_y(s->vram_size);
        }

        if (size == 2 && (addr & 2)) {
            width = artist_get_x(s->blockmove_size);
        } else {
            width = artist_get_x(s->vram_size);
        }

        fill_window(s, artist_get_x(s->vram_start),
                    artist_get_y(s->vram_start),
                    width, height);
        break;

    case LINE_XY:
        combine_write_reg(addr, val, size, &s->line_xy);
        if (s->draw_line_pattern) {
            draw_line_pattern_next(s);
        } else {
            draw_line_xy(s, true);
        }
        break;

    case PATTERN_LINE_START:
        combine_write_reg(addr, val, size, &s->line_pattern_start);
        s->draw_line_pattern = 1;
        draw_line_pattern_start(s);
        break;

    case LINE_SIZE:
        combine_write_reg(addr, val, size, &s->line_size);
        draw_line_size(s, true);
        break;

    case LINE_END:
        combine_write_reg(addr, val, size, &s->line_end);
        draw_line_end(s, true);
        break;

    case BLOCK_MOVE_SIZE:
        combine_write_reg(addr, val, size, &s->blockmove_size);
        break;

    case BLOCK_MOVE_SOURCE:
        combine_write_reg(addr, val, size, &s->blockmove_source);
        break;

    case BLOCK_MOVE_DEST_TRIGGER:
        combine_write_reg(addr, val, size, &s->blockmove_dest);

        block_move(s, artist_get_x(s->blockmove_source),
                   artist_get_y(s->blockmove_source),
                   artist_get_x(s->blockmove_dest),
                   artist_get_y(s->blockmove_dest),
                   artist_get_x(s->blockmove_size),
                   artist_get_y(s->blockmove_size));
        break;

    case BLOCK_MOVE_SIZE_TRIGGER:
        combine_write_reg(addr, val, size, &s->blockmove_size);

        block_move(s,
                   artist_get_x(s->blockmove_source),
                   artist_get_y(s->blockmove_source),
                   artist_get_x(s->vram_start),
                   artist_get_y(s->vram_start),
                   artist_get_x(s->blockmove_size),
                   artist_get_y(s->blockmove_size));
        break;

    case PLANE_MASK:
        combine_write_reg(addr, val, size, &s->plane_mask);
        break;

    case CMAP_BM_ACCESS:
        combine_write_reg(addr, val, size, &s->cmap_bm_access);
        break;

    case DST_BM_ACCESS:
        combine_write_reg(addr, val, size, &s->dst_bm_access);
        s->cmap_bm_access = 0;
        break;

    case SRC_BM_ACCESS:
        combine_write_reg(addr, val, size, &s->src_bm_access);
        s->cmap_bm_access = 0;
        break;

    case CONTROL_PLANE:
        combine_write_reg(addr, val, size, &s->control_plane);
        break;

    case TRANSFER_DATA:
        combine_write_reg(addr, val, size, &s->transfer_data);
        break;

    case 0x300200:
        combine_write_reg(addr, val, size, &s->reg_300200);
        break;

    case 0x300208:
        combine_write_reg(addr, val, size, &s->reg_300208);
        break;

    case 0x300218:
        combine_write_reg(addr, val, size, &s->reg_300218);
        break;

    case CURSOR_POS:
        artist_invalidate_cursor(s);
        combine_write_reg(addr, val, size, &s->cursor_pos);
        artist_invalidate_cursor(s);
        break;

    case CURSOR_CTRL:
        break;

    case IMAGE_BITMAP_OP:
        combine_write_reg(addr, val, size, &s->image_bitmap_op);
        break;

    case FONT_WRITE_INCR_Y:
        combine_write_reg(addr, val, size, &s->font_write1);
        font_write(s, s->font_write1);
        break;

    case FONT_WRITE_START:
        combine_write_reg(addr, val, size, &s->font_write2);
        s->font_write_pos_y = 0;
        font_write(s, s->font_write2);
        break;

    case 300104:
        break;

    default:
        qemu_log_mask(LOG_UNIMP, "%s: unknown register: reg=%08" HWADDR_PRIx
                      " val=%08" PRIx64 " size=%d\n",
                      __func__, addr, val, size);
        break;
    }
}

static uint64_t combine_read_reg(hwaddr addr, int size, void *in)
{
    /*
     * FIXME: is there a qemu helper for this?
     */

#ifndef HOST_WORDS_BIGENDIAN
    addr ^= 3;
#endif

    switch (size) {
    case 1:
        return *(uint8_t *)(in + (addr & 3));

    case 2:
        return *(uint16_t *)(in + (addr & 2));

    case 4:
        return *(uint32_t *)in;

    default:
        qemu_log_mask(LOG_UNIMP, "unsupported read size: %d\n", size);
        return 0;
    }
}

static uint64_t artist_reg_read(void *opaque, hwaddr addr, unsigned size)
{
    ARTISTState *s = opaque;
    uint32_t val = 0;

    switch (addr & ~3ULL) {
        /* Unknown status registers */
    case 0:
        break;

    case 0x211110:
        val = (s->width << 16) | s->height;
        if (s->depth == 1) {
            val |= 1 << 31;
        }
        break;

    case 0x100000:
    case 0x300000:
    case 0x300004:
    case 0x300308:
    case 0x380000:
        break;

    case 0x300008:
    case 0x380008:
        /*
         * FIFO ready flag. we're not emulating the FIFOs
         * so we're always ready
         */
        val = 0x10;
        break;

    case 0x300200:
        val = s->reg_300200;
        break;

    case 0x300208:
        val = s->reg_300208;
        break;

    case 0x300218:
        val = s->reg_300218;
        break;

    case 0x30023c:
        val = 0xac4ffdac;
        break;

    case 0x380004:
        /* 0x02000000 Buserror */
        val = 0x6dc20006;
        break;

    default:
        qemu_log_mask(LOG_UNIMP, "%s: unknown register: %08" HWADDR_PRIx
                      " size %d\n", __func__, addr, size);
        break;
    }
    val = combine_read_reg(addr, size, &val);
    trace_artist_reg_read(size, addr, artist_reg_name(addr & ~3ULL), val);
    return val;
}

static void artist_vram_write(void *opaque, hwaddr addr, uint64_t val,
                              unsigned size)
{
    ARTISTState *s = opaque;
    struct vram_buffer *buf;
    unsigned int posy, posx;
    unsigned int offset;
    trace_artist_vram_write(size, addr, val);

    if (s->cmap_bm_access) {
        buf = &s->vram_buffer[ARTIST_BUFFER_CMAP];
        if (addr + 3 < buf->size) {
            *(uint32_t *)(buf->data + addr) = val;
        }
        return;
    }

    buf = vram_write_buffer(s);
    posy = ADDR_TO_Y(addr >> 2);
    posx = ADDR_TO_X(addr >> 2);

    if (!buf->size) {
        return;
    }

    if (posy > buf->height || posx > buf->width) {
        return;
    }

    offset = posy * buf->width + posx;
    if (offset >= buf->size) {
        return;
    }

    switch (size) {
    case 4:
        if (offset + 3 < buf->size) {
            *(uint32_t *)(buf->data + offset) = be32_to_cpu(val);
            memory_region_set_dirty(&buf->mr, offset, 4);
        }
        break;
    case 2:
        if (offset + 1 < buf->size) {
            *(uint16_t *)(buf->data + offset) = be16_to_cpu(val);
            memory_region_set_dirty(&buf->mr, offset, 2);
        }
        break;
    case 1:
        if (offset < buf->size) {
            *(uint8_t *)(buf->data + offset) = val;
            memory_region_set_dirty(&buf->mr, offset, 1);
        }
        break;
    default:
        break;
    }
}

static uint64_t artist_vram_read(void *opaque, hwaddr addr, unsigned size)
{
    ARTISTState *s = opaque;
    struct vram_buffer *buf;
    uint64_t val;
    unsigned int posy, posx;

    if (s->cmap_bm_access) {
        buf = &s->vram_buffer[ARTIST_BUFFER_CMAP];
        val = 0;
        if (addr < buf->size && addr + 3 < buf->size) {
            val = *(uint32_t *)(buf->data + addr);
        }
        trace_artist_vram_read(size, addr, 0, 0, val);
        return val;
    }

    buf = vram_read_buffer(s);
    if (!buf->size) {
        return 0;
    }

    posy = ADDR_TO_Y(addr >> 2);
    posx = ADDR_TO_X(addr >> 2);

    if (posy > buf->height || posx > buf->width) {
        return 0;
    }

    val = cpu_to_be32(*(uint32_t *)(buf->data + posy * buf->width + posx));
    trace_artist_vram_read(size, addr, posx, posy, val);
    return val;
}

static const MemoryRegionOps artist_reg_ops = {
    .read = artist_reg_read,
    .write = artist_reg_write,
    .endianness = DEVICE_NATIVE_ENDIAN,
    .impl.min_access_size = 1,
    .impl.max_access_size = 4,
};

static const MemoryRegionOps artist_vram_ops = {
    .read = artist_vram_read,
    .write = artist_vram_write,
    .endianness = DEVICE_NATIVE_ENDIAN,
    .impl.min_access_size = 1,
    .impl.max_access_size = 4,
};

static void artist_draw_cursor(ARTISTState *s)
{
    DisplaySurface *surface = qemu_console_surface(s->con);
    uint32_t *data = (uint32_t *)surface_data(surface);
    struct vram_buffer *cursor0, *cursor1 , *buf;
    int cx, cy, cursor_pos_x, cursor_pos_y;

    cursor0 = &s->vram_buffer[ARTIST_BUFFER_CURSOR1];
    cursor1 = &s->vram_buffer[ARTIST_BUFFER_CURSOR2];
    buf = &s->vram_buffer[ARTIST_BUFFER_AP];

    artist_get_cursor_pos(s, &cursor_pos_x, &cursor_pos_y);

    for (cy = 0; cy < s->cursor_height; cy++) {

        for (cx = 0; cx < s->cursor_width; cx++) {

            if (cursor_pos_y + cy < 0 ||
                cursor_pos_x + cx < 0 ||
                cursor_pos_y + cy > buf->height - 1 ||
                cursor_pos_x + cx > buf->width) {
                continue;
            }

            int dstoffset = (cursor_pos_y + cy) * s->width +
                (cursor_pos_x + cx);

            if (cursor0->data[cy * cursor0->width + cx]) {
                data[dstoffset] = 0;
            } else {
                if (cursor1->data[cy * cursor1->width + cx]) {
                    data[dstoffset] = 0xffffff;
                }
            }
        }
    }
}

static void artist_draw_line(void *opaque, uint8_t *d, const uint8_t *src,
                             int width, int pitch)
{
    ARTISTState *s = ARTIST(opaque);
    uint32_t *cmap, *data = (uint32_t *)d;
    int x;

    cmap = (uint32_t *)(s->vram_buffer[ARTIST_BUFFER_CMAP].data + 0x400);

    for (x = 0; x < s->width; x++) {
        *data++ = cmap[*src++];
    }
}

static void artist_update_display(void *opaque)
{
    ARTISTState *s = opaque;
    DisplaySurface *surface = qemu_console_surface(s->con);
    int first = 0, last;


    framebuffer_update_display(surface, &s->fbsection, s->width, s->height,
                               s->width, s->width * 4, 0, 0, artist_draw_line,
                               s, &first, &last);

    artist_draw_cursor(s);

    dpy_gfx_update(s->con, 0, 0, s->width, s->height);
}

static void artist_invalidate(void *opaque)
{
    ARTISTState *s = ARTIST(opaque);
    struct vram_buffer *buf = &s->vram_buffer[ARTIST_BUFFER_AP];
    memory_region_set_dirty(&buf->mr, 0, buf->size);
}

static const GraphicHwOps artist_ops = {
    .invalidate  = artist_invalidate,
    .gfx_update = artist_update_display,
};

static void artist_initfn(Object *obj)
{
    SysBusDevice *sbd = SYS_BUS_DEVICE(obj);
    ARTISTState *s = ARTIST(obj);

    memory_region_init_io(&s->reg, obj, &artist_reg_ops, s, "artist.reg",
                          4 * MiB);
    memory_region_init_io(&s->vram_mem, obj, &artist_vram_ops, s, "artist.vram",
                          8 * MiB);
    sysbus_init_mmio(sbd, &s->reg);
    sysbus_init_mmio(sbd, &s->vram_mem);
}

static void artist_create_buffer(ARTISTState *s, const char *name,
                                 hwaddr *offset, unsigned int idx,
                                 int width, int height)
{
    struct vram_buffer *buf = s->vram_buffer + idx;

    memory_region_init_ram(&buf->mr, NULL, name, width * height,
                           &error_fatal);
    memory_region_add_subregion_overlap(&s->mem_as_root, *offset, &buf->mr, 0);

    buf->data = memory_region_get_ram_ptr(&buf->mr);
    buf->size = height * width;
    buf->width = width;
    buf->height = height;

    *offset += buf->size;
}

static void artist_realizefn(DeviceState *dev, Error **errp)
{
    ARTISTState *s = ARTIST(dev);
    struct vram_buffer *buf;
    hwaddr offset = 0;

    if (s->width > 2048 || s->height > 2048) {
        error_report("artist: screen size can not exceed 2048 x 2048 pixel.");
        s->width = MIN(s->width, 2048);
        s->height = MIN(s->height, 2048);
    }

    if (s->width < 640 || s->height < 480) {
        error_report("artist: minimum screen size is 640 x 480 pixel.");
        s->width = MAX(s->width, 640);
        s->height = MAX(s->height, 480);
    }

    memory_region_init(&s->mem_as_root, OBJECT(dev), "artist", ~0ull);
    address_space_init(&s->as, &s->mem_as_root, "artist");

    artist_create_buffer(s, "cmap", &offset, ARTIST_BUFFER_CMAP, 2048, 4);
    artist_create_buffer(s, "ap", &offset, ARTIST_BUFFER_AP,
                         s->width, s->height);
    artist_create_buffer(s, "cursor1", &offset, ARTIST_BUFFER_CURSOR1, 64, 64);
    artist_create_buffer(s, "cursor2", &offset, ARTIST_BUFFER_CURSOR2, 64, 64);
    artist_create_buffer(s, "attribute", &offset, ARTIST_BUFFER_ATTRIBUTE,
                         64, 64);

    buf = &s->vram_buffer[ARTIST_BUFFER_AP];
    framebuffer_update_memory_section(&s->fbsection, &buf->mr, 0,
                                      buf->width, buf->height);
    /*
     * no idea whether the cursor is fixed size or not, so assume 32x32 which
     * seems sufficient for HP-UX X11.
     */
    s->cursor_height = 32;
    s->cursor_width = 32;

    s->con = graphic_console_init(dev, 0, &artist_ops, s);
    qemu_console_resize(s->con, s->width, s->height);
}

static int vmstate_artist_post_load(void *opaque, int version_id)
{
    artist_invalidate(opaque);
    return 0;
}

static const VMStateDescription vmstate_artist = {
    .name = "artist",
    .version_id = 1,
    .minimum_version_id = 1,
    .post_load = vmstate_artist_post_load,
    .fields = (VMStateField[]) {
        VMSTATE_UINT16(height, ARTISTState),
        VMSTATE_UINT16(width, ARTISTState),
        VMSTATE_UINT16(depth, ARTISTState),
        VMSTATE_UINT32(fg_color, ARTISTState),
        VMSTATE_UINT32(bg_color, ARTISTState),
        VMSTATE_UINT32(vram_char_y, ARTISTState),
        VMSTATE_UINT32(vram_bitmask, ARTISTState),
        VMSTATE_UINT32(vram_start, ARTISTState),
        VMSTATE_UINT32(vram_pos, ARTISTState),
        VMSTATE_UINT32(vram_size, ARTISTState),
        VMSTATE_UINT32(blockmove_source, ARTISTState),
        VMSTATE_UINT32(blockmove_dest, ARTISTState),
        VMSTATE_UINT32(blockmove_size, ARTISTState),
        VMSTATE_UINT32(line_size, ARTISTState),
        VMSTATE_UINT32(line_end, ARTISTState),
        VMSTATE_UINT32(line_xy, ARTISTState),
        VMSTATE_UINT32(cursor_pos, ARTISTState),
        VMSTATE_UINT32(cursor_height, ARTISTState),
        VMSTATE_UINT32(cursor_width, ARTISTState),
        VMSTATE_UINT32(plane_mask, ARTISTState),
        VMSTATE_UINT32(reg_100080, ARTISTState),
        VMSTATE_UINT32(reg_300200, ARTISTState),
        VMSTATE_UINT32(reg_300208, ARTISTState),
        VMSTATE_UINT32(reg_300218, ARTISTState),
        VMSTATE_UINT32(cmap_bm_access, ARTISTState),
        VMSTATE_UINT32(dst_bm_access, ARTISTState),
        VMSTATE_UINT32(src_bm_access, ARTISTState),
        VMSTATE_UINT32(control_plane, ARTISTState),
        VMSTATE_UINT32(transfer_data, ARTISTState),
        VMSTATE_UINT32(image_bitmap_op, ARTISTState),
        VMSTATE_UINT32(font_write1, ARTISTState),
        VMSTATE_UINT32(font_write2, ARTISTState),
        VMSTATE_UINT32(font_write_pos_y, ARTISTState),
        VMSTATE_END_OF_LIST()
    }
};

static Property artist_properties[] = {
    DEFINE_PROP_UINT16("width",        ARTISTState, width, 1280),
    DEFINE_PROP_UINT16("height",       ARTISTState, height, 1024),
    DEFINE_PROP_UINT16("depth",        ARTISTState, depth, 8),
    DEFINE_PROP_END_OF_LIST(),
};

static void artist_reset(DeviceState *qdev)
{
}

static void artist_class_init(ObjectClass *klass, void *data)
{
    DeviceClass *dc = DEVICE_CLASS(klass);

    dc->realize = artist_realizefn;
    dc->vmsd = &vmstate_artist;
    dc->reset = artist_reset;
    device_class_set_props(dc, artist_properties);
}

static const TypeInfo artist_info = {
    .name          = TYPE_ARTIST,
    .parent        = TYPE_SYS_BUS_DEVICE,
    .instance_size = sizeof(ARTISTState),
    .instance_init = artist_initfn,
    .class_init    = artist_class_init,
};

static void artist_register_types(void)
{
    type_register_static(&artist_info);
}

type_init(artist_register_types)
