Revision 9586fefe hw/vga.c
b/hw/vga.c | ||
---|---|---|
36 | 36 |
|
37 | 37 |
//#define DEBUG_BOCHS_VBE |
38 | 38 |
|
39 |
#define GMODE_TEXT 0 |
|
40 |
#define GMODE_GRAPH 1 |
|
41 |
#define GMODE_BLANK 2 |
|
42 |
|
|
39 | 43 |
/* force some bits to zero */ |
40 | 44 |
const uint8_t sr_mask[8] = { |
41 | 45 |
0x03, |
... | ... | |
393 | 397 |
if (s->ar_flip_flop == 0) { |
394 | 398 |
val &= 0x3f; |
395 | 399 |
s->ar_index = val; |
400 |
vga_update_resolution(s); |
|
396 | 401 |
} else { |
397 | 402 |
index = s->ar_index & 0x1f; |
398 | 403 |
switch(index) { |
... | ... | |
433 | 438 |
#endif |
434 | 439 |
s->sr[s->sr_index] = val & sr_mask[s->sr_index]; |
435 | 440 |
if (s->sr_index == 1) s->update_retrace_info(s); |
441 |
vga_update_resolution(s); |
|
436 | 442 |
break; |
437 | 443 |
case 0x3c7: |
438 | 444 |
s->dac_read_index = val; |
... | ... | |
460 | 466 |
printf("vga: write GR%x = 0x%02x\n", s->gr_index, val); |
461 | 467 |
#endif |
462 | 468 |
s->gr[s->gr_index] = val & gr_mask[s->gr_index]; |
469 |
vga_update_resolution(s); |
|
463 | 470 |
break; |
464 | 471 |
case 0x3b4: |
465 | 472 |
case 0x3d4: |
... | ... | |
475 | 482 |
/* can always write bit 4 of CR7 */ |
476 | 483 |
if (s->cr_index == 7) |
477 | 484 |
s->cr[7] = (s->cr[7] & ~0x10) | (val & 0x10); |
485 |
vga_update_resolution(s); |
|
478 | 486 |
return; |
479 | 487 |
} |
480 | 488 |
switch(s->cr_index) { |
... | ... | |
502 | 510 |
s->update_retrace_info(s); |
503 | 511 |
break; |
504 | 512 |
} |
513 |
vga_update_resolution(s); |
|
505 | 514 |
break; |
506 | 515 |
case 0x3ba: |
507 | 516 |
case 0x3da: |
... | ... | |
581 | 590 |
if ((val <= VBE_DISPI_MAX_XRES) && ((val & 7) == 0)) { |
582 | 591 |
s->vbe_regs[s->vbe_index] = val; |
583 | 592 |
} |
593 |
vga_update_resolution(s); |
|
584 | 594 |
break; |
585 | 595 |
case VBE_DISPI_INDEX_YRES: |
586 | 596 |
if (val <= VBE_DISPI_MAX_YRES) { |
587 | 597 |
s->vbe_regs[s->vbe_index] = val; |
588 | 598 |
} |
599 |
vga_update_resolution(s); |
|
589 | 600 |
break; |
590 | 601 |
case VBE_DISPI_INDEX_BPP: |
591 | 602 |
if (val == 0) |
... | ... | |
594 | 605 |
val == 16 || val == 24 || val == 32) { |
595 | 606 |
s->vbe_regs[s->vbe_index] = val; |
596 | 607 |
} |
608 |
vga_update_resolution(s); |
|
597 | 609 |
break; |
598 | 610 |
case VBE_DISPI_INDEX_BANK: |
599 | 611 |
if (s->vbe_regs[VBE_DISPI_INDEX_BPP] == 4) { |
... | ... | |
662 | 674 |
} |
663 | 675 |
s->dac_8bit = (val & VBE_DISPI_8BIT_DAC) > 0; |
664 | 676 |
s->vbe_regs[s->vbe_index] = val; |
677 |
vga_update_resolution(s); |
|
665 | 678 |
break; |
666 | 679 |
case VBE_DISPI_INDEX_VIRT_WIDTH: |
667 | 680 |
{ |
... | ... | |
682 | 695 |
s->vbe_regs[VBE_DISPI_INDEX_VIRT_HEIGHT] = h; |
683 | 696 |
s->vbe_line_offset = line_offset; |
684 | 697 |
} |
698 |
vga_update_resolution(s); |
|
685 | 699 |
break; |
686 | 700 |
case VBE_DISPI_INDEX_X_OFFSET: |
687 | 701 |
case VBE_DISPI_INDEX_Y_OFFSET: |
... | ... | |
696 | 710 |
s->vbe_start_addr += x * ((s->vbe_regs[VBE_DISPI_INDEX_BPP] + 7) >> 3); |
697 | 711 |
s->vbe_start_addr >>= 2; |
698 | 712 |
} |
713 |
vga_update_resolution(s); |
|
699 | 714 |
break; |
700 | 715 |
default: |
701 | 716 |
break; |
... | ... | |
1302 | 1317 |
s->plane_updated = 0; |
1303 | 1318 |
full_update = 1; |
1304 | 1319 |
} |
1305 |
full_update |= update_basic_params(s); |
|
1306 | 1320 |
|
1307 | 1321 |
line_offset = s->line_offset; |
1308 | 1322 |
s1 = s->vram_ptr + (s->start_addr * 4); |
... | ... | |
1314 | 1328 |
return; |
1315 | 1329 |
} |
1316 | 1330 |
|
1317 |
if (width != s->last_width || height != s->last_height || |
|
1318 |
cw != s->last_cw || cheight != s->last_ch || s->last_depth) { |
|
1319 |
s->last_scr_width = width * cw; |
|
1320 |
s->last_scr_height = height * cheight; |
|
1321 |
qemu_console_resize(s->ds, s->last_scr_width, s->last_scr_height); |
|
1322 |
s->last_depth = 0; |
|
1323 |
s->last_width = width; |
|
1324 |
s->last_height = height; |
|
1325 |
s->last_ch = cheight; |
|
1326 |
s->last_cw = cw; |
|
1327 |
full_update = 1; |
|
1328 |
} |
|
1329 | 1331 |
s->rgb_to_pixel = |
1330 | 1332 |
rgb_to_pixel_dup_table[get_depth_index(s->ds)]; |
1331 | 1333 |
full_update |= update_palette16(s); |
... | ... | |
1582 | 1584 |
vga_dirty_log_start(s); |
1583 | 1585 |
} |
1584 | 1586 |
|
1585 |
/* |
|
1586 |
* graphic modes |
|
1587 |
*/ |
|
1588 |
static void vga_draw_graphic(VGAState *s, int full_update) |
|
1587 |
static void vga_update_resolution_graphics(VGAState *s) |
|
1589 | 1588 |
{ |
1590 |
int y1, y, update, page_min, page_max, linesize, y_start, double_scan, mask, depth;
|
|
1591 |
int width, height, shift_control, line_offset, page0, page1, bwidth, bits;
|
|
1589 |
int depth = s->get_bpp(s);
|
|
1590 |
int width, height, shift_control, double_scan;
|
|
1592 | 1591 |
int disp_width, multi_scan, multi_run; |
1593 |
uint8_t *d; |
|
1594 |
uint32_t v, addr1, addr; |
|
1595 |
vga_draw_line_func *vga_draw_line; |
|
1596 |
|
|
1597 |
full_update |= update_basic_params(s); |
|
1598 |
|
|
1599 |
if (!full_update) |
|
1600 |
vga_sync_dirty_bitmap(s); |
|
1601 | 1592 |
|
1602 | 1593 |
s->get_resolution(s, &width, &height); |
1603 | 1594 |
disp_width = width; |
1604 | 1595 |
|
1605 | 1596 |
shift_control = (s->gr[0x05] >> 5) & 3; |
1606 | 1597 |
double_scan = (s->cr[0x09] >> 7); |
1607 |
if (shift_control != 1) { |
|
1608 |
multi_scan = (((s->cr[0x09] & 0x1f) + 1) << double_scan) - 1; |
|
1609 |
} else { |
|
1610 |
/* in CGA modes, multi_scan is ignored */ |
|
1611 |
/* XXX: is it correct ? */ |
|
1612 |
multi_scan = double_scan; |
|
1613 |
} |
|
1614 |
multi_run = multi_scan; |
|
1598 |
|
|
1615 | 1599 |
if (shift_control != s->shift_control || |
1616 | 1600 |
double_scan != s->double_scan) { |
1617 |
full_update = 1; |
|
1601 |
s->want_full_update = 1;
|
|
1618 | 1602 |
s->shift_control = shift_control; |
1619 | 1603 |
s->double_scan = double_scan; |
1620 | 1604 |
} |
... | ... | |
1628 | 1612 |
disp_width <<= 1; |
1629 | 1613 |
} |
1630 | 1614 |
} |
1615 |
disp_width = width; |
|
1616 |
|
|
1617 |
if (shift_control != 1) { |
|
1618 |
multi_scan = (((s->cr[0x09] & 0x1f) + 1) << double_scan) - 1; |
|
1619 |
} else { |
|
1620 |
/* in CGA modes, multi_scan is ignored */ |
|
1621 |
/* XXX: is it correct ? */ |
|
1622 |
multi_scan = double_scan; |
|
1623 |
} |
|
1624 |
|
|
1625 |
multi_run = multi_scan; |
|
1631 | 1626 |
|
1632 |
depth = s->get_bpp(s); |
|
1633 | 1627 |
if (s->line_offset != s->last_line_offset || |
1634 | 1628 |
disp_width != s->last_width || |
1635 | 1629 |
height != s->last_height || |
1636 |
s->last_depth != depth) { |
|
1630 |
s->last_depth != depth || |
|
1631 |
s->multi_run != multi_run || |
|
1632 |
s->multi_scan != multi_scan || |
|
1633 |
s->want_full_update) { |
|
1634 |
if (s->ds->surface->pf.depth == 0) { |
|
1635 |
goto dont_touch_display_surface; |
|
1636 |
} |
|
1637 | 1637 |
#if defined(WORDS_BIGENDIAN) == defined(TARGET_WORDS_BIGENDIAN) |
1638 | 1638 |
if (depth == 16 || depth == 32) { |
1639 | 1639 |
#else |
... | ... | |
1650 | 1650 |
} else { |
1651 | 1651 |
qemu_console_resize(s->ds, disp_width, height); |
1652 | 1652 |
} |
1653 |
dont_touch_display_surface: |
|
1653 | 1654 |
s->last_scr_width = disp_width; |
1654 | 1655 |
s->last_scr_height = height; |
1655 | 1656 |
s->last_width = disp_width; |
1656 | 1657 |
s->last_height = height; |
1657 | 1658 |
s->last_line_offset = s->line_offset; |
1658 | 1659 |
s->last_depth = depth; |
1659 |
full_update = 1; |
|
1660 |
} else if (is_buffer_shared(s->ds->surface) && |
|
1660 |
s->multi_run = multi_run; |
|
1661 |
s->multi_scan = multi_scan; |
|
1662 |
s->want_full_update = 1; |
|
1663 |
} |
|
1664 |
} |
|
1665 |
|
|
1666 |
static void vga_update_resolution_text(VGAState *s) |
|
1667 |
{ |
|
1668 |
int width, height, cw, cheight; |
|
1669 |
|
|
1670 |
vga_get_text_resolution(s, &width, &height, &cw, &cheight); |
|
1671 |
if (width != s->last_width || height != s->last_height || |
|
1672 |
cw != s->last_cw || cheight != s->last_ch || s->last_depth) { |
|
1673 |
s->last_scr_width = width * cw; |
|
1674 |
s->last_scr_height = height * cheight; |
|
1675 |
if (s->ds->surface->pf.depth != 0) { |
|
1676 |
qemu_console_resize(s->ds, s->last_scr_width, s->last_scr_height); |
|
1677 |
} else { |
|
1678 |
/* |
|
1679 |
* curses expects width and height to be in character cell |
|
1680 |
* dimensions, not pixels. |
|
1681 |
*/ |
|
1682 |
s->ds->surface->width = width; |
|
1683 |
s->ds->surface->height = height; |
|
1684 |
dpy_resize(s->ds); |
|
1685 |
} |
|
1686 |
s->last_depth = 0; |
|
1687 |
s->last_width = width; |
|
1688 |
s->last_height = height; |
|
1689 |
s->last_ch = cheight; |
|
1690 |
s->last_cw = cw; |
|
1691 |
s->want_full_update = 1; |
|
1692 |
} |
|
1693 |
} |
|
1694 |
|
|
1695 |
void vga_update_resolution(VGAState *s) |
|
1696 |
{ |
|
1697 |
int graphic_mode; |
|
1698 |
|
|
1699 |
if (!(s->ar_index & 0x20)) { |
|
1700 |
graphic_mode = GMODE_BLANK; |
|
1701 |
} else { |
|
1702 |
graphic_mode = s->gr[6] & 1; |
|
1703 |
} |
|
1704 |
if (graphic_mode != s->graphic_mode) { |
|
1705 |
s->graphic_mode = graphic_mode; |
|
1706 |
s->want_full_update = 1; |
|
1707 |
} |
|
1708 |
s->want_full_update |= update_basic_params(s); |
|
1709 |
switch (graphic_mode) { |
|
1710 |
case GMODE_TEXT: |
|
1711 |
vga_update_resolution_text(s); |
|
1712 |
break; |
|
1713 |
case GMODE_GRAPH: |
|
1714 |
vga_update_resolution_graphics(s); |
|
1715 |
break; |
|
1716 |
} |
|
1717 |
} |
|
1718 |
|
|
1719 |
/* |
|
1720 |
* graphic modes |
|
1721 |
*/ |
|
1722 |
static void vga_draw_graphic(VGAState *s, int full_update) |
|
1723 |
{ |
|
1724 |
int y1, y, update, linesize, y_start, mask; |
|
1725 |
int width, height, line_offset, bwidth, bits; |
|
1726 |
int multi_run; |
|
1727 |
uint8_t *d; |
|
1728 |
uint32_t v, addr1, addr; |
|
1729 |
long page0, page1, page_min, page_max; |
|
1730 |
vga_draw_line_func *vga_draw_line; |
|
1731 |
|
|
1732 |
if (!full_update) |
|
1733 |
vga_sync_dirty_bitmap(s); |
|
1734 |
|
|
1735 |
s->get_resolution(s, &width, &height); |
|
1736 |
multi_run = s->multi_run; |
|
1737 |
if (is_buffer_shared(s->ds->surface) && |
|
1661 | 1738 |
(full_update || s->ds->surface->data != s->vram_ptr + (s->start_addr * 4))) { |
1662 | 1739 |
s->ds->surface->data = s->vram_ptr + (s->start_addr * 4); |
1663 | 1740 |
dpy_setdata(s->ds); |
... | ... | |
1666 | 1743 |
s->rgb_to_pixel = |
1667 | 1744 |
rgb_to_pixel_dup_table[get_depth_index(s->ds)]; |
1668 | 1745 |
|
1669 |
if (shift_control == 0) { |
|
1746 |
if (s->shift_control == 0) {
|
|
1670 | 1747 |
full_update |= update_palette16(s); |
1671 | 1748 |
if (s->sr[0x01] & 8) { |
1672 | 1749 |
v = VGA_DRAW_LINE4D2; |
... | ... | |
1674 | 1751 |
v = VGA_DRAW_LINE4; |
1675 | 1752 |
} |
1676 | 1753 |
bits = 4; |
1677 |
} else if (shift_control == 1) { |
|
1754 |
} else if (s->shift_control == 1) {
|
|
1678 | 1755 |
full_update |= update_palette16(s); |
1679 | 1756 |
if (s->sr[0x01] & 8) { |
1680 | 1757 |
v = VGA_DRAW_LINE2D2; |
... | ... | |
1770 | 1847 |
if (y_start >= 0) { |
1771 | 1848 |
/* flush to display */ |
1772 | 1849 |
dpy_update(s->ds, 0, y_start, |
1773 |
disp_width, y - y_start);
|
|
1850 |
s->last_width, y - y_start);
|
|
1774 | 1851 |
y_start = -1; |
1775 | 1852 |
} |
1776 | 1853 |
} |
... | ... | |
1779 | 1856 |
if ((y1 & mask) == mask) |
1780 | 1857 |
addr1 += line_offset; |
1781 | 1858 |
y1++; |
1782 |
multi_run = multi_scan; |
|
1859 |
multi_run = s->multi_scan;
|
|
1783 | 1860 |
} else { |
1784 | 1861 |
multi_run--; |
1785 | 1862 |
} |
... | ... | |
1791 | 1868 |
if (y_start >= 0) { |
1792 | 1869 |
/* flush to display */ |
1793 | 1870 |
dpy_update(s->ds, 0, y_start, |
1794 |
disp_width, y - y_start);
|
|
1871 |
s->last_width, y - y_start);
|
|
1795 | 1872 |
} |
1796 | 1873 |
/* reset modified pages */ |
1797 | 1874 |
if (page_max != -1) { |
... | ... | |
1828 | 1905 |
s->last_scr_width, s->last_scr_height); |
1829 | 1906 |
} |
1830 | 1907 |
|
1831 |
#define GMODE_TEXT 0 |
|
1832 |
#define GMODE_GRAPH 1 |
|
1833 |
#define GMODE_BLANK 2 |
|
1834 |
|
|
1835 | 1908 |
static void vga_update_display(void *opaque) |
1836 | 1909 |
{ |
1837 | 1910 |
VGAState *s = (VGAState *)opaque; |
1838 |
int full_update, graphic_mode;
|
|
1911 |
int full_update; |
|
1839 | 1912 |
|
1840 | 1913 |
if (ds_get_bits_per_pixel(s->ds) == 0) { |
1841 | 1914 |
/* nothing to do */ |
1842 | 1915 |
} else { |
1843 |
full_update = 0; |
|
1844 |
if (!(s->ar_index & 0x20)) { |
|
1845 |
graphic_mode = GMODE_BLANK; |
|
1846 |
} else { |
|
1847 |
graphic_mode = s->gr[6] & 1; |
|
1848 |
} |
|
1849 |
if (graphic_mode != s->graphic_mode) { |
|
1850 |
s->graphic_mode = graphic_mode; |
|
1851 |
full_update = 1; |
|
1852 |
} |
|
1853 |
switch(graphic_mode) { |
|
1916 |
full_update = s->want_full_update; |
|
1917 |
s->want_full_update = 0; |
|
1918 |
switch(s->graphic_mode) { |
|
1854 | 1919 |
case GMODE_TEXT: |
1855 | 1920 |
vga_draw_text(s, full_update); |
1856 | 1921 |
break; |
... | ... | |
1870 | 1935 |
{ |
1871 | 1936 |
VGAState *s = (VGAState *)opaque; |
1872 | 1937 |
|
1873 |
s->last_width = -1;
|
|
1874 |
s->last_height = -1;
|
|
1938 |
vga_update_resolution(s);
|
|
1939 |
s->want_full_update = 1;
|
|
1875 | 1940 |
} |
1876 | 1941 |
|
1877 | 1942 |
void vga_reset(void *opaque) |
... | ... | |
1915 | 1980 |
s->vbe_bank_mask = (s->vram_size >> 16) - 1; |
1916 | 1981 |
#endif |
1917 | 1982 |
memset(s->font_offsets, '\0', sizeof(s->font_offsets)); |
1918 |
s->graphic_mode = -1; /* force full update */ |
|
1919 | 1983 |
s->shift_control = 0; |
1920 | 1984 |
s->double_scan = 0; |
1921 | 1985 |
s->line_offset = 0; |
... | ... | |
1941 | 2005 |
memset(&s->retrace_info, 0, sizeof (s->retrace_info)); |
1942 | 2006 |
break; |
1943 | 2007 |
} |
2008 |
vga_update_resolution(s); |
|
1944 | 2009 |
} |
1945 | 2010 |
|
1946 | 2011 |
#define TEXTMODE_X(x) ((x) % width) |
... | ... | |
1952 | 2017 |
static void vga_update_text(void *opaque, console_ch_t *chardata) |
1953 | 2018 |
{ |
1954 | 2019 |
VGAState *s = (VGAState *) opaque; |
1955 |
int graphic_mode, i, cursor_offset, cursor_visible;
|
|
2020 |
int i, cursor_offset, cursor_visible; |
|
1956 | 2021 |
int cw, cheight, width, height, size, c_min, c_max; |
1957 | 2022 |
uint32_t *src; |
1958 | 2023 |
console_ch_t *dst, val; |
1959 | 2024 |
char msg_buffer[80]; |
1960 |
int full_update = 0; |
|
1961 |
|
|
1962 |
if (!(s->ar_index & 0x20)) { |
|
1963 |
graphic_mode = GMODE_BLANK; |
|
1964 |
} else { |
|
1965 |
graphic_mode = s->gr[6] & 1; |
|
1966 |
} |
|
1967 |
if (graphic_mode != s->graphic_mode) { |
|
1968 |
s->graphic_mode = graphic_mode; |
|
1969 |
full_update = 1; |
|
1970 |
} |
|
1971 |
if (s->last_width == -1) { |
|
1972 |
s->last_width = 0; |
|
1973 |
full_update = 1; |
|
1974 |
} |
|
2025 |
int full_update = s->want_full_update; |
|
1975 | 2026 |
|
1976 |
switch (graphic_mode) { |
|
2027 |
s->want_full_update = 0; |
|
2028 |
switch (s->graphic_mode) { |
|
1977 | 2029 |
case GMODE_TEXT: |
1978 | 2030 |
/* TODO: update palette */ |
1979 |
full_update |= update_basic_params(s); |
|
1980 | 2031 |
|
1981 |
/* total width & height */ |
|
1982 |
cheight = (s->cr[9] & 0x1f) + 1; |
|
1983 |
cw = 8; |
|
1984 |
if (!(s->sr[1] & 0x01)) |
|
1985 |
cw = 9; |
|
1986 |
if (s->sr[1] & 0x08) |
|
1987 |
cw = 16; /* NOTE: no 18 pixel wide */ |
|
1988 |
width = (s->cr[0x01] + 1); |
|
1989 |
if (s->cr[0x06] == 100) { |
|
1990 |
/* ugly hack for CGA 160x100x16 - explain me the logic */ |
|
1991 |
height = 100; |
|
1992 |
} else { |
|
1993 |
height = s->cr[0x12] | |
|
1994 |
((s->cr[0x07] & 0x02) << 7) | |
|
1995 |
((s->cr[0x07] & 0x40) << 3); |
|
1996 |
height = (height + 1) / cheight; |
|
2032 |
vga_get_text_resolution(s, &width, &height, &cw, &cheight); |
|
2033 |
|
|
2034 |
if (s->ds->surface->width != width |
|
2035 |
|| s->ds->surface->height != height) { |
|
2036 |
s->ds->surface->width = width; |
|
2037 |
s->ds->surface->height = height; |
|
2038 |
dpy_resize(s->ds); |
|
1997 | 2039 |
} |
1998 | 2040 |
|
2041 |
/* total width & height */ |
|
1999 | 2042 |
size = (height * width); |
2000 | 2043 |
if (size > CH_ATTR_SIZE) { |
2001 | 2044 |
if (!full_update) |
... | ... | |
2006 | 2049 |
break; |
2007 | 2050 |
} |
2008 | 2051 |
|
2009 |
if (width != s->last_width || height != s->last_height || |
|
2010 |
cw != s->last_cw || cheight != s->last_ch) { |
|
2011 |
s->last_scr_width = width * cw; |
|
2012 |
s->last_scr_height = height * cheight; |
|
2013 |
s->ds->surface->width = width; |
|
2014 |
s->ds->surface->height = height; |
|
2015 |
dpy_resize(s->ds); |
|
2016 |
s->last_width = width; |
|
2017 |
s->last_height = height; |
|
2018 |
s->last_ch = cheight; |
|
2019 |
s->last_cw = cw; |
|
2020 |
full_update = 1; |
|
2021 |
} |
|
2022 |
|
|
2023 | 2052 |
/* Update "hardware" cursor */ |
2024 | 2053 |
cursor_offset = ((s->cr[0x0e] << 8) | s->cr[0x0f]) - s->start_addr; |
2025 | 2054 |
if (cursor_offset != s->cursor_offset || |
... | ... | |
2218 | 2247 |
#endif |
2219 | 2248 |
|
2220 | 2249 |
/* force refresh */ |
2221 |
s->graphic_mode = -1; |
|
2250 |
vga_update_resolution(s); |
|
2251 |
s->want_full_update = 1; |
|
2222 | 2252 |
return 0; |
2223 | 2253 |
} |
2224 | 2254 |
|
... | ... | |
2641 | 2671 |
ds->surface = qemu_create_displaysurface(ds, w, h); |
2642 | 2672 |
|
2643 | 2673 |
s->ds = ds; |
2644 |
s->graphic_mode = -1; |
|
2674 |
vga_update_resolution(s); |
|
2675 |
s->want_full_update = 1; |
|
2645 | 2676 |
vga_update_display(s); |
2646 | 2677 |
|
2647 | 2678 |
ppm_save(filename, ds->surface); |
... | ... | |
2672 | 2703 |
{ |
2673 | 2704 |
VGAState *s = (VGAState *)opaque; |
2674 | 2705 |
|
2675 |
if (!(s->ar_index & 0x20)) |
|
2676 |
vga_screen_dump_blank(s, filename); |
|
2677 |
else if (s->gr[6] & 1) |
|
2678 |
vga_screen_dump_graphic(s, filename); |
|
2679 |
else |
|
2706 |
switch (s->graphic_mode) { |
|
2707 |
case GMODE_TEXT: |
|
2680 | 2708 |
vga_screen_dump_text(s, filename); |
2709 |
break; |
|
2710 |
case GMODE_GRAPH: |
|
2711 |
vga_screen_dump_graphic(s, filename); |
|
2712 |
break; |
|
2713 |
case GMODE_BLANK: |
|
2714 |
default: |
|
2715 |
vga_screen_dump_blank(s, filename); |
|
2716 |
break; |
|
2717 |
} |
|
2681 | 2718 |
} |
Also available in: Unified diff