1 /**
2  ** ega4.c ---- the 16 color EGA frame driver
3  **
4  ** Copyright (c) 1995 Csaba Biegl, 820 Stirrup Dr, Nashville, TN 37221
5  ** [e-mail: csaba@vuse.vanderbilt.edu].
6  **
7  ** This file is part of the GRX graphics library.
8  **
9  ** The GRX graphics library is free software; you can redistribute it
10  ** and/or modify it under some conditions; see the "copying.grx" file
11  ** for details.
12  **
13  ** This library is distributed in the hope that it will be useful,
14  ** but WITHOUT ANY WARRANTY; without even the implied warranty of
15  ** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
16  **
17  **/
18 
19 #include "libgrx.h"
20 #include "grdriver.h"
21 #include "arith.h"
22 #include "mempeek.h"
23 #include "memcopy.h"
24 #include "memfill.h"
25 #include "vgaregs.h"
26 #include "ioport.h"
27 
28 /* frame offset address calculation */
29 #define FOFS(x,y,lo) umuladd32((y),(lo),((x) >> 3))
30 
31 static GrColor lastcolor;
32 static int  writeops[] = {
33     (VGA_FUNC_SET << 8) + VGA_ROT_FN_SEL_REG,      /* C_SET */
34     (VGA_FUNC_XOR << 8) + VGA_ROT_FN_SEL_REG,      /* C_XOR */
35     (VGA_FUNC_OR  << 8) + VGA_ROT_FN_SEL_REG,      /* C_OR  */
36     (VGA_FUNC_AND << 8) + VGA_ROT_FN_SEL_REG       /* C_AND */
37 };
38 
init(GrVideoMode * mp)39 static int init(GrVideoMode *mp)
40 {
41 	GRX_ENTER();
42 	/* set write mode 0 */
43 	outport_w(VGA_GR_CTRL_PORT,((0 << 8) | VGA_MODE_REG));
44 	/* don't care register to 0 */
45 	outport_w(VGA_GR_CTRL_PORT,((0 << 8) | VGA_COLOR_DONTC_REG));
46 	/* enable all 4 planes for writing */
47 	outport_w(VGA_SEQUENCER_PORT,((0x0f << 8) | VGA_WRT_PLANE_ENB_REG));
48 	/* enable all 4 planes for set/reset */
49 	outport_w(VGA_GR_CTRL_PORT,((0x0f << 8) | VGA_SET_RESET_ENB_REG));
50 	lastcolor = (-1L);
51 	GRX_RETURN(TRUE);
52 }
53 
54 
55 static INLINE
readpixel(GrFrame * c,int x,int y)56 GrColor readpixel(GrFrame *c,int x,int y)
57 {
58 	char far *ptr;
59 	unsigned mask, pixval;
60 	GRX_ENTER();
61 	ptr = &SCRN->gc_baseaddr[0][FOFS(x,y,SCRN->gc_lineoffset)];
62 	mask= 0x80U >> (x &= 7);
63 	setup_far_selector(SCRN->gc_selector);
64 	outport_w(VGA_GR_CTRL_PORT,((3 << 8) | VGA_RD_PLANE_SEL_REG));
65 	pixval = (peek_b_f(ptr) & mask);
66 	outport_b(VGA_GR_CTRL_DATA,2);
67 	pixval = (peek_b_f(ptr) & mask) | (pixval << 1);
68 	outport_b(VGA_GR_CTRL_DATA,1);
69 	pixval = (peek_b_f(ptr) & mask) | (pixval << 1);
70 	outport_b(VGA_GR_CTRL_DATA,0);
71 	pixval = (peek_b_f(ptr) & mask) | (pixval << 1);
72 	lastcolor = (-1L);
73 	GRX_RETURN((GrColor)(pixval >> (7 - x)));
74 }
75 
76 static INLINE
drawpixel(int x,int y,GrColor color)77 void drawpixel(int x,int y,GrColor color)
78 {
79 	char far *ptr;
80 	GRX_ENTER();
81 	ptr = &CURC->gc_baseaddr[0][FOFS(x,y,SCRN->gc_lineoffset)];
82 	setup_far_selector(CURC->gc_selector);
83 	if(lastcolor != color) {
84 	    outport_w(VGA_GR_CTRL_PORT,writeops[C_OPER(color) & 3]);
85 	    outport_w(VGA_GR_CTRL_PORT,((((int)color & 0x0f) << 8) | VGA_SET_RESET_REG));
86 	    lastcolor = color;
87 	}
88 	outport_w(VGA_GR_CTRL_PORT,((0x8000U >> (x & 7)) | VGA_BIT_MASK_REG));
89 	poke_b_f_or(ptr,0);
90 	GRX_LEAVE();
91 }
92 
93 static
94 #include "fdrivers/generic/hline.c"
95 
96 static
97 #include "fdrivers/generic/vline.c"
98 
99 static
100 #include "fdrivers/generic/block.c"
101 
102 static
103 #include "fdrivers/generic/line.c"
104 
105 static
106 #include "fdrivers/generic/bitmap.c"
107 
108 static
109 #include "fdrivers/generic/pattern.c"
110 
111 static
112 #include "fdrivers/generic/bitblt.c"
113 
114 GrFrameDriver _GrFrameDriverEGA4 = {
115     GR_frameEGA4,               /* frame mode */
116     GR_frameRAM4,               /* compatible RAM frame mode */
117     TRUE,                       /* onscreen */
118     4,                          /* scan line width alignment */
119     4,                          /* number of planes */
120     4,                          /* bits per pixel */
121     64*1024L,                   /* max plane size the code can handle */
122     init,
123     readpixel,
124     drawpixel,
125     drawline,
126     drawhline,
127     drawvline,
128     drawblock,
129     drawbitmap,
130     drawpattern,
131     bitblt,
132     _GrFrDrvGenericBitBlt,
133     _GrFrDrvGenericBitBlt,
134     _GrFrDrvGenericGetIndexedScanline,
135     _GrFrDrvGenericPutScanline
136 };
137