aboutsummaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorKeir Fraser <keir@xensource.com>2007-10-26 10:41:07 +0100
committerKeir Fraser <keir@xensource.com>2007-10-26 10:41:07 +0100
commita0e7ccf6864c196906d58b54cd0996b4dbc1b022 (patch)
treeb0231df2a09496de24e7446b5d60f25d422b6461 /tools
parent1ad6a137c37508e9ea5372fb2ac4b509059853a7 (diff)
downloadxen-a0e7ccf6864c196906d58b54cd0996b4dbc1b022.tar.gz
xen-a0e7ccf6864c196906d58b54cd0996b4dbc1b022.tar.bz2
xen-a0e7ccf6864c196906d58b54cd0996b4dbc1b022.zip
x86, hvm: Allow Cirrus VGA BIOS to clear framebuffer with minimal PIO writes.
Signed-off-by: Ben Guthro <bguthro@virtualron.com> Signed-off-by: Gary Grebus <ggrebus@virtualiron.com>
Diffstat (limited to 'tools')
-rw-r--r--tools/firmware/vgabios/clext.c26
-rw-r--r--tools/ioemu/hw/cirrus_vga.c12
2 files changed, 31 insertions, 7 deletions
diff --git a/tools/firmware/vgabios/clext.c b/tools/firmware/vgabios/clext.c
index 1eb3c69734..97ae080b2c 100644
--- a/tools/firmware/vgabios/clext.c
+++ b/tools/firmware/vgabios/clext.c
@@ -1489,14 +1489,26 @@ cirrus_clear_vram_1:
mov dx, #0x3ce
out dx, ax
push ax
- mov cx, #0xa000
- mov es, cx
- xor di, di
+
+;; Windows Vista appears to be emulating this sequence as part of changing
+;; screen resolution, but it generates 4096 writes per iteration.
+;; Instead, use a magic register sequence to write the whole bank.
+;;mov cx, #0xa000
+;;mov es, cx
+;;xor di, di
+;;mov ax, si
+;;mov cx, #8192
+;;cld
+;;rep
+;; stosw
mov ax, si
- mov cx, #8192
- cld
- rep
- stosw
+ shl ax, #8
+ mov al, #0xfe
+ out dx, ax ;; Low byte of value to be written to the bank
+ mov ax, si
+ mov al, #0xff
+ out dx, ax ;; High byte and trigger the write
+
pop ax
inc ah
cmp ah, bl
diff --git a/tools/ioemu/hw/cirrus_vga.c b/tools/ioemu/hw/cirrus_vga.c
index 2fd1626362..8a637c57fd 100644
--- a/tools/ioemu/hw/cirrus_vga.c
+++ b/tools/ioemu/hw/cirrus_vga.c
@@ -294,6 +294,7 @@ void *shared_vram;
static void cirrus_bitblt_reset(CirrusVGAState *s);
static void cirrus_update_memory_access(CirrusVGAState *s);
+static void cirrus_vga_mem_writew(void *opaque, target_phys_addr_t addr, uint32_t val);
/***************************************
*
@@ -1497,6 +1498,17 @@ cirrus_hook_write_gr(CirrusVGAState * s, unsigned reg_index, int reg_value)
case 0x31: // BLT STATUS/START
cirrus_write_bitblt(s, reg_value);
break;
+
+ // Extension to allow BIOS to clear 16K VRAM bank in one operation
+ case 0xFE:
+ s->gr[reg_index] = reg_value; // Lower byte of value to be written
+ break;
+ case 0xFF: {
+ target_phys_addr_t addr;
+ for (addr = 0xa0000; addr < 0xa4000; addr += 2)
+ cirrus_vga_mem_writew(s, addr, (reg_value << 8) | s->gr[0xFE]);
+ }
+ break;
default:
#ifdef DEBUG_CIRRUS
printf("cirrus: outport gr_index %02x, gr_value %02x\n", reg_index,