Commit 4abc796d41ee01a698032e74ac17c1cdc5d290c3

Authored by blueswir1
1 parent 785f451b

Add cirrus reset handler

The vga reset handler overwrites some cirrus registers, causing reboots
to corrupt cirrus state to the point that guests can only bring up 640x480
resolutions.

Fix by adding a dedicated cirrus reset handler (which calls the common vga
handler).

Signed-off-by: Avi Kivity <avi@redhat.com>


git-svn-id: svn://svn.savannah.nongnu.org/qemu/trunk@6191 c046a42c-6fe2-441c-8c8c-71466251a162
hw/cirrus_vga.c
... ... @@ -287,6 +287,8 @@ typedef struct CirrusVGAState {
287 287 int last_hw_cursor_y_end;
288 288 int real_vram_size; /* XXX: suppress that */
289 289 CPUWriteMemoryFunc **cirrus_linear_write;
  290 + int device_id;
  291 + int bustype;
290 292 } CirrusVGAState;
291 293  
292 294 typedef struct PCICirrusVGAState {
... ... @@ -3175,55 +3177,13 @@ static int cirrus_vga_load(QEMUFile *f, void *opaque, int version_id)
3175 3177 *
3176 3178 ***************************************/
3177 3179  
3178   -static void cirrus_init_common(CirrusVGAState * s, int device_id, int is_pci)
  3180 +static void cirrus_reset(void *opaque)
3179 3181 {
3180   - int i;
3181   - static int inited;
3182   -
3183   - if (!inited) {
3184   - inited = 1;
3185   - for(i = 0;i < 256; i++)
3186   - rop_to_index[i] = CIRRUS_ROP_NOP_INDEX; /* nop rop */
3187   - rop_to_index[CIRRUS_ROP_0] = 0;
3188   - rop_to_index[CIRRUS_ROP_SRC_AND_DST] = 1;
3189   - rop_to_index[CIRRUS_ROP_NOP] = 2;
3190   - rop_to_index[CIRRUS_ROP_SRC_AND_NOTDST] = 3;
3191   - rop_to_index[CIRRUS_ROP_NOTDST] = 4;
3192   - rop_to_index[CIRRUS_ROP_SRC] = 5;
3193   - rop_to_index[CIRRUS_ROP_1] = 6;
3194   - rop_to_index[CIRRUS_ROP_NOTSRC_AND_DST] = 7;
3195   - rop_to_index[CIRRUS_ROP_SRC_XOR_DST] = 8;
3196   - rop_to_index[CIRRUS_ROP_SRC_OR_DST] = 9;
3197   - rop_to_index[CIRRUS_ROP_NOTSRC_OR_NOTDST] = 10;
3198   - rop_to_index[CIRRUS_ROP_SRC_NOTXOR_DST] = 11;
3199   - rop_to_index[CIRRUS_ROP_SRC_OR_NOTDST] = 12;
3200   - rop_to_index[CIRRUS_ROP_NOTSRC] = 13;
3201   - rop_to_index[CIRRUS_ROP_NOTSRC_OR_DST] = 14;
3202   - rop_to_index[CIRRUS_ROP_NOTSRC_AND_NOTDST] = 15;
3203   - }
3204   -
3205   - register_ioport_write(0x3c0, 16, 1, vga_ioport_write, s);
3206   -
3207   - register_ioport_write(0x3b4, 2, 1, vga_ioport_write, s);
3208   - register_ioport_write(0x3d4, 2, 1, vga_ioport_write, s);
3209   - register_ioport_write(0x3ba, 1, 1, vga_ioport_write, s);
3210   - register_ioport_write(0x3da, 1, 1, vga_ioport_write, s);
3211   -
3212   - register_ioport_read(0x3c0, 16, 1, vga_ioport_read, s);
3213   -
3214   - register_ioport_read(0x3b4, 2, 1, vga_ioport_read, s);
3215   - register_ioport_read(0x3d4, 2, 1, vga_ioport_read, s);
3216   - register_ioport_read(0x3ba, 1, 1, vga_ioport_read, s);
3217   - register_ioport_read(0x3da, 1, 1, vga_ioport_read, s);
3218   -
3219   - s->vga_io_memory = cpu_register_io_memory(0, cirrus_vga_mem_read,
3220   - cirrus_vga_mem_write, s);
3221   - cpu_register_physical_memory(isa_mem_base + 0x000a0000, 0x20000,
3222   - s->vga_io_memory);
3223   - qemu_register_coalesced_mmio(isa_mem_base + 0x000a0000, 0x20000);
  3182 + CirrusVGAState *s = opaque;
3224 3183  
  3184 + vga_reset(s);
3225 3185 s->sr[0x06] = 0x0f;
3226   - if (device_id == CIRRUS_ID_CLGD5446) {
  3186 + if (s->device_id == CIRRUS_ID_CLGD5446) {
3227 3187 /* 4MB 64 bit memory config, always PCI */
3228 3188 s->sr[0x1F] = 0x2d; // MemClock
3229 3189 s->gr[0x18] = 0x0f; // fastest memory configuration
... ... @@ -3241,14 +3201,11 @@ static void cirrus_init_common(CirrusVGAState * s, int device_id, int is_pci)
3241 3201 } else {
3242 3202 s->sr[0x1F] = 0x22; // MemClock
3243 3203 s->sr[0x0F] = CIRRUS_MEMSIZE_2M;
3244   - if (is_pci)
3245   - s->sr[0x17] = CIRRUS_BUSTYPE_PCI;
3246   - else
3247   - s->sr[0x17] = CIRRUS_BUSTYPE_ISA;
  3204 + s->sr[0x17] = s->bustype;
3248 3205 s->real_vram_size = 2048 * 1024;
3249 3206 s->sr[0x15] = 0x03; /* memory size, 3=2MB, 4=4MB */
3250 3207 }
3251   - s->cr[0x27] = device_id;
  3208 + s->cr[0x27] = s->device_id;
3252 3209  
3253 3210 /* Win2K seems to assume that the pattern buffer is at 0xff
3254 3211 initially ! */
... ... @@ -3281,7 +3238,62 @@ static void cirrus_init_common(CirrusVGAState * s, int device_id, int is_pci)
3281 3238 s->get_resolution = cirrus_get_resolution;
3282 3239 s->cursor_invalidate = cirrus_cursor_invalidate;
3283 3240 s->cursor_draw_line = cirrus_cursor_draw_line;
  3241 +}
  3242 +
  3243 +static void cirrus_init_common(CirrusVGAState * s, int device_id, int is_pci)
  3244 +{
  3245 + int i;
  3246 + static int inited;
  3247 +
  3248 + if (!inited) {
  3249 + inited = 1;
  3250 + for(i = 0;i < 256; i++)
  3251 + rop_to_index[i] = CIRRUS_ROP_NOP_INDEX; /* nop rop */
  3252 + rop_to_index[CIRRUS_ROP_0] = 0;
  3253 + rop_to_index[CIRRUS_ROP_SRC_AND_DST] = 1;
  3254 + rop_to_index[CIRRUS_ROP_NOP] = 2;
  3255 + rop_to_index[CIRRUS_ROP_SRC_AND_NOTDST] = 3;
  3256 + rop_to_index[CIRRUS_ROP_NOTDST] = 4;
  3257 + rop_to_index[CIRRUS_ROP_SRC] = 5;
  3258 + rop_to_index[CIRRUS_ROP_1] = 6;
  3259 + rop_to_index[CIRRUS_ROP_NOTSRC_AND_DST] = 7;
  3260 + rop_to_index[CIRRUS_ROP_SRC_XOR_DST] = 8;
  3261 + rop_to_index[CIRRUS_ROP_SRC_OR_DST] = 9;
  3262 + rop_to_index[CIRRUS_ROP_NOTSRC_OR_NOTDST] = 10;
  3263 + rop_to_index[CIRRUS_ROP_SRC_NOTXOR_DST] = 11;
  3264 + rop_to_index[CIRRUS_ROP_SRC_OR_NOTDST] = 12;
  3265 + rop_to_index[CIRRUS_ROP_NOTSRC] = 13;
  3266 + rop_to_index[CIRRUS_ROP_NOTSRC_OR_DST] = 14;
  3267 + rop_to_index[CIRRUS_ROP_NOTSRC_AND_NOTDST] = 15;
  3268 + s->device_id = device_id;
  3269 + if (is_pci)
  3270 + s->bustype = CIRRUS_BUSTYPE_PCI;
  3271 + else
  3272 + s->bustype = CIRRUS_BUSTYPE_ISA;
  3273 + }
  3274 +
  3275 + register_ioport_write(0x3c0, 16, 1, vga_ioport_write, s);
  3276 +
  3277 + register_ioport_write(0x3b4, 2, 1, vga_ioport_write, s);
  3278 + register_ioport_write(0x3d4, 2, 1, vga_ioport_write, s);
  3279 + register_ioport_write(0x3ba, 1, 1, vga_ioport_write, s);
  3280 + register_ioport_write(0x3da, 1, 1, vga_ioport_write, s);
  3281 +
  3282 + register_ioport_read(0x3c0, 16, 1, vga_ioport_read, s);
  3283 +
  3284 + register_ioport_read(0x3b4, 2, 1, vga_ioport_read, s);
  3285 + register_ioport_read(0x3d4, 2, 1, vga_ioport_read, s);
  3286 + register_ioport_read(0x3ba, 1, 1, vga_ioport_read, s);
  3287 + register_ioport_read(0x3da, 1, 1, vga_ioport_read, s);
  3288 +
  3289 + s->vga_io_memory = cpu_register_io_memory(0, cirrus_vga_mem_read,
  3290 + cirrus_vga_mem_write, s);
  3291 + cpu_register_physical_memory(isa_mem_base + 0x000a0000, 0x20000,
  3292 + s->vga_io_memory);
  3293 + qemu_register_coalesced_mmio(isa_mem_base + 0x000a0000, 0x20000);
3284 3294  
  3295 + qemu_register_reset(cirrus_reset, s);
  3296 + cirrus_reset(s);
3285 3297 register_savevm("cirrus_vga", 0, 2, cirrus_vga_save, cirrus_vga_load, s);
3286 3298 }
3287 3299  
... ...
hw/vga.c
... ... @@ -1839,7 +1839,7 @@ static void vga_invalidate_display(void *opaque)
1839 1839 s->last_height = -1;
1840 1840 }
1841 1841  
1842   -static void vga_reset(void *opaque)
  1842 +void vga_reset(void *opaque)
1843 1843 {
1844 1844 VGAState *s = (VGAState *) opaque;
1845 1845  
... ... @@ -2277,7 +2277,6 @@ void vga_common_init(VGAState *s, DisplayState *ds, uint8_t *vga_ram_base,
2277 2277 s->update_retrace_info = vga_precise_update_retrace_info;
2278 2278 break;
2279 2279 }
2280   - qemu_register_reset(vga_reset, s);
2281 2280 vga_reset(s);
2282 2281 }
2283 2282  
... ... @@ -2286,6 +2285,7 @@ void vga_init(VGAState *s)
2286 2285 {
2287 2286 int vga_io_memory;
2288 2287  
  2288 + qemu_register_reset(vga_reset, s);
2289 2289 register_savevm("vga", 0, 2, vga_save, vga_load, s);
2290 2290  
2291 2291 register_ioport_write(0x3c0, 16, 1, vga_ioport_write, s);
... ...
hw/vga_int.h
... ... @@ -193,6 +193,7 @@ static inline int c6_to_8(int v)
193 193 void vga_common_init(VGAState *s, DisplayState *ds, uint8_t *vga_ram_base,
194 194 ram_addr_t vga_ram_offset, int vga_ram_size);
195 195 void vga_init(VGAState *s);
  196 +void vga_reset(void *s);
196 197  
197 198 void vga_dirty_log_start(VGAState *s);
198 199 void vga_dirty_log_stop(VGAState *s);
... ...