📄 90x60.c
字号:
0, 256, 8, _bitmaps_8x8
};
static font_t _font_8x16 =
{
0, 256, 16, _bitmaps_8x16
};
/*****************************************************************************
*****************************************************************************/
static void write_regs(unsigned char *regs)
{
unsigned index;
/* enable writes to CRTC regs 0-7 */
outportb(VGA_CRTC_INDEX, 17);
outportb(VGA_CRTC_DATA,
inportb(VGA_CRTC_DATA) & 0x7F);
/* enable access to vertical retrace regs */
outportb(VGA_CRTC_INDEX, 3);
outportb(VGA_CRTC_DATA,
inportb(VGA_CRTC_DATA) | 0x80);
/* CRTC
make sure we don't disable writes to the CRTC registers: */
regs[17] &= 0x7F; /* undo write-protect on CRTC regs 0-7 */
regs[3] |= 0x80; /* enable access to vertical retrace regs */
for(index = 0; index < NUM_CRTC_REGS; index++)
{
outportb(VGA_CRTC_INDEX, index);
outportb(VGA_CRTC_DATA, *regs);
regs++;
}
/* attribute controller */
#if 0
/* we don't need to monkey with these just to change text resolution... */
for(index = 0; index < NUM_AC_REGS; index++)
{
(void)inportb(VGA_INSTAT_READ);
nsleep(250);
outportb(VGA_AC_INDEX, index & 0x1F);
nsleep(250);
outportb(VGA_AC_WRITE, *regs);
nsleep(250);
regs++;
}
/* lock palette and unblank display */
(void)inportb(VGA_INSTAT_READ);
nsleep(250);
outportb(VGA_AC_INDEX, 0x20);
nsleep(250);
/* graphics controller */
for(index = 0; index < NUM_GC_REGS; index++)
{
outportb(VGA_GC_INDEX, index);
outportb(VGA_GC_DATA, *regs);
regs++;
}
#else
regs += (NUM_AC_REGS + NUM_GC_REGS);// + NUM_SEQ_REGS);
#endif
/* sequencer */
for(index = 0; index < NUM_SEQ_REGS; index++)
{
outportb(VGA_SEQ_INDEX, index);
outportb(VGA_SEQ_DATA, *regs);
regs++;
}
/* other regs */
outportb(VGA_MISC_WRITE, *regs);
}
/*****************************************************************************
*****************************************************************************/
static void outsw(unsigned short adr, unsigned short *data, unsigned count)
{
for(; count != 0; count--)
{
outport(adr, *data);
data++;
}
}
/*****************************************************************************
*****************************************************************************/
static void set_font(font_t *font)
{
/* 0x0100: synchronous reset
0x0402: enable plane 4; disable planes 8, 2, and 1
0x0704: ModeX off, even/odd mode ON (?), >64K on, text mode
0x0300: undo synchronous reset */
static unsigned short seq_set[] =
{
0x0100, 0x0402, 0x0704, 0x0300
};
/* 0x0204: read mode 0 reads from plane 4
0x0005: 256-color mode off, even/odd mode OFF, read mode 0, write mode 0
0x0C06: screen at B8000, even/odd mode OFF, text mode */
static unsigned short gc_set[] =
{
0x0204, 0x0005, 0x0C06
};
/* 0x0100: synchronous reset
0x0302: enable planes 1 and 2; disable planes 4 and 8
0x0304: Mode X off, even/odd mode OFF, >64K on, text mode
0x0300: undo synchronous reset */
static unsigned short seq_reset[] =
{
0x0100, 0x0302, 0x0304, 0x0300
};
/* 0x0004: read mode 0 reads from none of the four planes
0x1005: 256-color mode off, even/odd mode ON, read mode 0, write mode 0
0x0C06: screen at B8000, even/odd mode ON, text mode */
static unsigned short gc_reset[] =
{
0x0004, 0x1005, 0x0E06
};
unsigned short temp, dst;
unsigned char *src;
/* access font memory (plane 4) instead of text memory (planes 2 and 1) */
outsw(VGA_SEQ_INDEX, seq_set, sizeof(seq_set) /
sizeof(unsigned short));
outsw(VGA_GC_INDEX, gc_set, sizeof(gc_set) /
sizeof(unsigned short));
/* program the font */
src = font->bitmaps + font->first * font->height;
dst = font->first * 32;
for(temp = font->first; temp < font->last; temp++)
{
vmemwr(dst, src, font->height);
src += font->height;
dst += 32;
}
/* access text memory (planes 2 and 1) instead of font memory (plane 4) */
outsw(VGA_SEQ_INDEX, seq_reset, sizeof(seq_reset) /
sizeof(unsigned short));
outsw(VGA_GC_INDEX, gc_reset, sizeof(gc_reset) /
sizeof(unsigned short));
/* set font height in CRTC register 9 */
outportb(VGA_CRTC_INDEX, 9);
outportb(VGA_CRTC_DATA, (inportb(VGA_CRTC_DATA) & 0xE0) |
((font->height - 1) & 0x1F));
/* set top and bottom scanlines of cursor */
if(font->height == 16)
{
outportb(VGA_CRTC_INDEX, 10);
outportb(VGA_CRTC_DATA, 13);
outportb(VGA_CRTC_INDEX, 11);
outportb(VGA_CRTC_DATA, 14);
}
else if(font->height == 8)
{
outportb(VGA_CRTC_INDEX, 10);
outportb(VGA_CRTC_DATA, 7);
outportb(VGA_CRTC_INDEX, 11);
outportb(VGA_CRTC_DATA, 7);
}
}
/*****************************************************************************
*****************************************************************************/
#if defined(__DJGPP__)
/* make DJGPP code a little smaller */
void __crt0_load_environment_file(char *prog_name) { }
void __crt0_setup_arguments(void) { }
#endif
int main(void)
{
unsigned short temp;
#if HEIGHT==25
unsigned short char_ht = 16, csr_end = 14, csr_start = 13;
unsigned short screen_wd = 80, screen_ht = 25;
write_regs(_mode_80x25);
set_font(&_font_8x16);
#elif HEIGHT==50
unsigned short char_ht = 8, csr_end = 7, csr_start = 6;
unsigned short screen_wd = 80, screen_ht = 50;
write_regs(_mode_80x50);
set_font(&_font_8x8);
#elif HEIGHT==60
unsigned short char_ht = 8, csr_end = 7, csr_start = 6;
unsigned short screen_wd = 90, screen_ht = 60;
write_regs(_mode_90x60);
set_font(&_font_8x8);
#else
#error Must define HEIGHT as 25, 50, or 60.
#endif
/* set values in BIOS data area
MEM 0040h:004Ah - VIDEO - COLUMNS ON SCREEN */
poke40(0x004A, screen_wd);
/* MEM 0040h:004Ch - VIDEO - PAGE (REGEN BUFFER) SIZE IN BYTES */
poke40(0x004C, screen_wd * screen_ht * 2);
/* MEM 0040h:0050h - VIDEO - CURSOR POSITIONS */
for(temp = 0x0050; temp < 0x0060; temp += 2)
poke40(temp, 0);
/* MEM 0040h:0060h - VIDEO - CURSOR TYPE */
temp = csr_start;
temp <<= 8;
temp |= csr_end;
poke40(0x0060, temp);
/* MEM 0040h:0084h - VIDEO (EGA/MCGA/VGA) - ROWS ON SCREEN MINUS ONE */
pokeb40(0x0084, screen_ht - 1);
/* MEM 0040h:0085h - VIDEO (EGA/MCGA/VGA) - CHARACTER HEIGHT IN SCAN-LINES */
pokeb40(0x0085, char_ht);
return 0;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -