[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[PATCH 2/8] vga: introduce VGADisplayParams
From: |
Paolo Bonzini |
Subject: |
[PATCH 2/8] vga: introduce VGADisplayParams |
Date: |
Sun, 31 Dec 2023 10:39:12 +0100 |
The next patches will introduce more parameters that cause a full
refresh. Instead of adding arguments to get_offsets and lines to
update_basic_params, do everything through a struct.
Signed-off-by: Paolo Bonzini <pbonzini@redhat.com>
---
hw/display/cirrus_vga.c | 24 +++++-------
hw/display/vga.c | 82 +++++++++++++++++------------------------
hw/display/vga_int.h | 15 ++++----
3 files changed, 52 insertions(+), 69 deletions(-)
diff --git a/hw/display/cirrus_vga.c b/hw/display/cirrus_vga.c
index b80f98b6c4c..e6d2581d4eb 100644
--- a/hw/display/cirrus_vga.c
+++ b/hw/display/cirrus_vga.c
@@ -798,9 +798,9 @@ static int cirrus_bitblt_videotovideo_copy(CirrusVGAState *
s)
if (blit_is_unsafe(s, false))
return 0;
- return cirrus_do_copy(s, s->cirrus_blt_dstaddr - s->vga.start_addr,
- s->cirrus_blt_srcaddr - s->vga.start_addr,
- s->cirrus_blt_width, s->cirrus_blt_height);
+ return cirrus_do_copy(s, s->cirrus_blt_dstaddr - s->vga.params.start_addr,
+ s->cirrus_blt_srcaddr - s->vga.params.start_addr,
+ s->cirrus_blt_width, s->cirrus_blt_height);
}
/***************************************
@@ -1101,30 +1101,26 @@ static void cirrus_write_bitblt(CirrusVGAState * s,
unsigned reg_value)
*
***************************************/
-static void cirrus_get_offsets(VGACommonState *s1,
- uint32_t *pline_offset,
- uint32_t *pstart_addr,
- uint32_t *pline_compare)
+static void cirrus_get_params(VGACommonState *s1,
+ VGADisplayParams *params)
{
CirrusVGAState * s = container_of(s1, CirrusVGAState, vga);
- uint32_t start_addr, line_offset, line_compare;
+ uint32_t line_offset;
line_offset = s->vga.cr[0x13]
| ((s->vga.cr[0x1b] & 0x10) << 4);
line_offset <<= 3;
- *pline_offset = line_offset;
+ params->line_offset = line_offset;
- start_addr = (s->vga.cr[0x0c] << 8)
+ params->start_addr = (s->vga.cr[0x0c] << 8)
| s->vga.cr[0x0d]
| ((s->vga.cr[0x1b] & 0x01) << 16)
| ((s->vga.cr[0x1b] & 0x0c) << 15)
| ((s->vga.cr[0x1d] & 0x80) << 12);
- *pstart_addr = start_addr;
- line_compare = s->vga.cr[0x18] |
+ params->line_compare = s->vga.cr[0x18] |
((s->vga.cr[0x07] & 0x10) << 4) |
((s->vga.cr[0x09] & 0x40) << 3);
- *pline_compare = line_compare;
}
static uint32_t cirrus_get_bpp16_depth(CirrusVGAState * s)
@@ -2925,7 +2921,7 @@ void cirrus_init_common(CirrusVGAState *s, Object *owner,
s->linear_mmio_mask = s->real_vram_size - 256;
s->vga.get_bpp = cirrus_get_bpp;
- s->vga.get_offsets = cirrus_get_offsets;
+ s->vga.get_params = cirrus_get_params;
s->vga.get_resolution = cirrus_get_resolution;
s->vga.cursor_invalidate = cirrus_cursor_invalidate;
s->vga.cursor_draw_line = cirrus_cursor_draw_line;
diff --git a/hw/display/vga.c b/hw/display/vga.c
index 18d966ecd3e..3bd357d72c2 100644
--- a/hw/display/vga.c
+++ b/hw/display/vga.c
@@ -1059,52 +1059,40 @@ static int update_palette256(VGACommonState *s)
return full_update;
}
-static void vga_get_offsets(VGACommonState *s,
- uint32_t *pline_offset,
- uint32_t *pstart_addr,
- uint32_t *pline_compare)
+static void vga_get_params(VGACommonState *s,
+ VGADisplayParams *params)
{
- uint32_t start_addr, line_offset, line_compare;
-
if (vbe_enabled(s)) {
- line_offset = s->vbe_line_offset;
- start_addr = s->vbe_start_addr;
- line_compare = 65535;
+ params->line_offset = s->vbe_line_offset;
+ params->start_addr = s->vbe_start_addr;
+ params->line_compare = 65535;
} else {
/* compute line_offset in bytes */
- line_offset = s->cr[VGA_CRTC_OFFSET];
- line_offset <<= 3;
+ params->line_offset = s->cr[VGA_CRTC_OFFSET] << 3;
/* starting address */
- start_addr = s->cr[VGA_CRTC_START_LO] |
+ params->start_addr = s->cr[VGA_CRTC_START_LO] |
(s->cr[VGA_CRTC_START_HI] << 8);
/* line compare */
- line_compare = s->cr[VGA_CRTC_LINE_COMPARE] |
+ params->line_compare = s->cr[VGA_CRTC_LINE_COMPARE] |
((s->cr[VGA_CRTC_OVERFLOW] & 0x10) << 4) |
((s->cr[VGA_CRTC_MAX_SCAN] & 0x40) << 3);
}
- *pline_offset = line_offset;
- *pstart_addr = start_addr;
- *pline_compare = line_compare;
}
/* update start_addr and line_offset. Return TRUE if modified */
static int update_basic_params(VGACommonState *s)
{
int full_update;
- uint32_t start_addr, line_offset, line_compare;
+ VGADisplayParams current;
full_update = 0;
- s->get_offsets(s, &line_offset, &start_addr, &line_compare);
+ s->get_params(s, ¤t);
- if (line_offset != s->line_offset ||
- start_addr != s->start_addr ||
- line_compare != s->line_compare) {
- s->line_offset = line_offset;
- s->start_addr = start_addr;
- s->line_compare = line_compare;
+ if (memcmp(¤t, &s->params, sizeof(current))) {
+ s->params = current;
full_update = 1;
}
return full_update;
@@ -1205,7 +1193,7 @@ static void vga_draw_text(VGACommonState *s, int
full_update)
}
full_update |= update_basic_params(s);
- line_offset = s->line_offset;
+ line_offset = s->params.line_offset;
vga_get_text_resolution(s, &width, &height, &cw, &cheight);
if ((height * width) <= 1) {
@@ -1244,7 +1232,7 @@ static void vga_draw_text(VGACommonState *s, int
full_update)
}
cursor_offset = ((s->cr[VGA_CRTC_CURSOR_HI] << 8) |
- s->cr[VGA_CRTC_CURSOR_LO]) - s->start_addr;
+ s->cr[VGA_CRTC_CURSOR_LO]) - s->params.start_addr;
if (cursor_offset != s->cursor_offset ||
s->cr[VGA_CRTC_CURSOR_START] != s->cursor_start ||
s->cr[VGA_CRTC_CURSOR_END] != s->cursor_end) {
@@ -1258,7 +1246,7 @@ static void vga_draw_text(VGACommonState *s, int
full_update)
s->cursor_start = s->cr[VGA_CRTC_CURSOR_START];
s->cursor_end = s->cr[VGA_CRTC_CURSOR_END];
}
- cursor_ptr = s->vram_ptr + (s->start_addr + cursor_offset) * 4;
+ cursor_ptr = s->vram_ptr + (s->params.start_addr + cursor_offset) * 4;
if (now >= s->cursor_blink_time) {
s->cursor_blink_time = now + VGA_TEXT_CURSOR_PERIOD_MS / 2;
s->cursor_visible_phase = !s->cursor_visible_phase;
@@ -1268,7 +1256,7 @@ static void vga_draw_text(VGACommonState *s, int
full_update)
linesize = surface_stride(surface);
ch_attr_ptr = s->last_ch_attr;
line = 0;
- offset = s->start_addr * 4;
+ offset = s->params.start_addr * 4;
for(cy = 0; cy < height; cy++) {
d1 = dest;
src = s->vram_ptr + offset;
@@ -1348,7 +1336,7 @@ static void vga_draw_text(VGACommonState *s, int
full_update)
dest += linesize * cheight;
line1 = line + cheight;
offset += line_offset;
- if (line < s->line_compare && line1 >= s->line_compare) {
+ if (line < s->params.line_compare && line1 >= s->params.line_compare) {
offset = 0;
}
line = line1;
@@ -1478,10 +1466,10 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
disp_width = width;
depth = s->get_bpp(s);
- region_start = (s->start_addr * 4);
- region_end = region_start + (ram_addr_t)s->line_offset * height;
+ region_start = (s->params.start_addr * 4);
+ region_end = region_start + (ram_addr_t)s->params.line_offset * height;
region_end += width * depth / 8; /* scanline length */
- region_end -= s->line_offset;
+ region_end -= s->params.line_offset;
if (region_end > s->vbe_size || depth == 0 || depth == 15) {
/*
* We land here on:
@@ -1546,7 +1534,7 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
share_surface = false;
}
- if (s->line_offset != s->last_line_offset ||
+ if (s->params.line_offset != s->last_line_offset ||
disp_width != s->last_width ||
height != s->last_height ||
s->last_depth != depth ||
@@ -1557,12 +1545,12 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
s->last_scr_height = height;
s->last_width = disp_width;
s->last_height = height;
- s->last_line_offset = s->line_offset;
+ s->last_line_offset = s->params.line_offset;
s->last_depth = depth;
s->last_byteswap = byteswap;
full_update = 1;
}
- if (surface_data(surface) != s->vram_ptr + (s->start_addr * 4)
+ if (surface_data(surface) != s->vram_ptr + (s->params.start_addr * 4)
&& is_buffer_shared(surface)) {
/* base address changed (page flip) -> shared display surfaces
* must be updated with the new base address */
@@ -1572,8 +1560,8 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
if (full_update) {
if (share_surface) {
surface = qemu_create_displaysurface_from(disp_width,
- height, format, s->line_offset,
- s->vram_ptr + (s->start_addr * 4));
+ height, format, s->params.line_offset,
+ s->vram_ptr + (s->params.start_addr * 4));
dpy_gfx_replace_surface(s->con, surface);
} else {
qemu_console_resize(s->con, disp_width, height);
@@ -1637,9 +1625,9 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
#if 0
printf("w=%d h=%d v=%d line_offset=%d cr[0x09]=0x%02x cr[0x17]=0x%02x
linecmp=%d sr[0x01]=0x%02x\n",
width, height, v, line_offset, s->cr[9], s->cr[VGA_CRTC_MODE],
- s->line_compare, sr(s, VGA_SEQ_CLOCK_MODE));
+ s->params.line_compare, sr(s, VGA_SEQ_CLOCK_MODE));
#endif
- addr1 = (s->start_addr * 4);
+ addr1 = (s->params.start_addr * 4);
bwidth = DIV_ROUND_UP(width * bits, 8);
y_start = -1;
d = surface_data(surface);
@@ -1647,7 +1635,7 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
y1 = 0;
if (!full_update) {
- if (s->line_compare < height) {
+ if (s->params.line_compare < height) {
/* split screen mode */
region_start = 0;
}
@@ -1703,14 +1691,14 @@ static void vga_draw_graphic(VGACommonState *s, int
full_update)
if (!multi_run) {
mask = (s->cr[VGA_CRTC_MODE] & 3) ^ 3;
if ((y1 & mask) == mask)
- addr1 += s->line_offset;
+ addr1 += s->params.line_offset;
y1++;
multi_run = multi_scan;
} else {
multi_run--;
}
/* line compare acts on the displayed lines */
- if (y == s->line_compare)
+ if (y == s->params.line_compare)
addr1 = 0;
d += linesize;
}
@@ -1827,9 +1815,7 @@ void vga_common_reset(VGACommonState *s)
s->graphic_mode = -1; /* force full update */
s->shift_control = 0;
s->double_scan = 0;
- s->line_offset = 0;
- s->line_compare = 0;
- s->start_addr = 0;
+ memset(&s->params, '\0', sizeof(s->params));
s->plane_updated = 0;
s->last_cw = 0;
s->last_ch = 0;
@@ -1951,7 +1937,7 @@ static void vga_update_text(void *opaque, console_ch_t
*chardata)
/* Update "hardware" cursor */
cursor_offset = ((s->cr[VGA_CRTC_CURSOR_HI] << 8) |
- s->cr[VGA_CRTC_CURSOR_LO]) - s->start_addr;
+ s->cr[VGA_CRTC_CURSOR_LO]) - s->params.start_addr;
if (cursor_offset != s->cursor_offset ||
s->cr[VGA_CRTC_CURSOR_START] != s->cursor_start ||
s->cr[VGA_CRTC_CURSOR_END] != s->cursor_end || full_update) {
@@ -1967,7 +1953,7 @@ static void vga_update_text(void *opaque, console_ch_t
*chardata)
s->cursor_end = s->cr[VGA_CRTC_CURSOR_END];
}
- src = (uint32_t *) s->vram_ptr + s->start_addr;
+ src = (uint32_t *) s->vram_ptr + s->params.start_addr;
dst = chardata;
if (full_update) {
@@ -2212,7 +2198,7 @@ bool vga_common_init(VGACommonState *s, Object *obj,
Error **errp)
xen_register_framebuffer(&s->vram);
s->vram_ptr = memory_region_get_ram_ptr(&s->vram);
s->get_bpp = vga_get_bpp;
- s->get_offsets = vga_get_offsets;
+ s->get_params = vga_get_params;
s->get_resolution = vga_get_resolution;
s->hw_ops = &vga_ops;
switch (vga_retrace_method) {
diff --git a/hw/display/vga_int.h b/hw/display/vga_int.h
index 7cf0d11201a..6be61e04284 100644
--- a/hw/display/vga_int.h
+++ b/hw/display/vga_int.h
@@ -56,6 +56,12 @@ struct VGACommonState;
typedef uint8_t (* vga_retrace_fn)(struct VGACommonState *s);
typedef void (* vga_update_retrace_info_fn)(struct VGACommonState *s);
+typedef struct VGADisplayParams {
+ uint32_t line_offset;
+ uint32_t start_addr;
+ uint32_t line_compare;
+} VGADisplayParams;
+
typedef struct VGACommonState {
MemoryRegion *legacy_address_space;
uint8_t *vram_ptr;
@@ -90,10 +96,7 @@ typedef struct VGACommonState {
uint8_t palette[768];
int32_t bank_offset;
int (*get_bpp)(struct VGACommonState *s);
- void (*get_offsets)(struct VGACommonState *s,
- uint32_t *pline_offset,
- uint32_t *pstart_addr,
- uint32_t *pline_compare);
+ void (*get_params)(struct VGACommonState *s, VGADisplayParams *params);
void (*get_resolution)(struct VGACommonState *s,
int *pwidth,
int *pheight);
@@ -111,9 +114,7 @@ typedef struct VGACommonState {
int graphic_mode;
uint8_t shift_control;
uint8_t double_scan;
- uint32_t line_offset;
- uint32_t line_compare;
- uint32_t start_addr;
+ VGADisplayParams params;
uint32_t plane_updated;
uint32_t last_line_offset;
uint8_t last_cw, last_ch;
--
2.43.0
- [PATCH 0/8] vga: improve emulation fidelity, Paolo Bonzini, 2023/12/31
- [PATCH 3/8] vga: mask addresses in non-VESA modes to 256k, Paolo Bonzini, 2023/12/31
- [PATCH 1/8] vga: remove unused macros, Paolo Bonzini, 2023/12/31
- [PATCH 7/8] vga: use latches in odd/even mode too, Paolo Bonzini, 2023/12/31
- [PATCH 2/8] vga: introduce VGADisplayParams,
Paolo Bonzini <=
- [PATCH 4/8] vga: implement horizontal pel panning in graphics modes, Paolo Bonzini, 2023/12/31
- [PATCH 5/8] vga: optimize horizontal pel panning in 256-color modes, Paolo Bonzini, 2023/12/31
- [PATCH 6/8] vga: reindent memory access code, Paolo Bonzini, 2023/12/31
- [PATCH 8/8] vga: sort-of implement word and double-word access modes, Paolo Bonzini, 2023/12/31