2 #include "../port/lib.h"
7 #include "../port/error.h"
16 setet4000page(int page)
30 et4000page(VGAscr *scr, int page)
34 unlock(&scr->devlock);
38 et4000disable(VGAscr*)
43 imaF7 = inb(0x217B) & ~0x80;
48 et4000enable(VGAscr *scr)
55 * Configure CRTCB for Sprite, 64x64,
62 * Cursor goes in the top left corner
63 * of the Sprite area, so the horizontal and
64 * vertical presets are 0.
77 * Find a place for the cursor data in display memory.
78 * Must be on a "doubleword" boundary, but put it on a
79 * 1024-byte boundary so that there's no danger of it
82 scr->storage = (scr->gscreen->width*sizeof(ulong)*scr->gscreen->r.max.y+1023)/1024;
83 scr->storage *= 1024/4;
85 outb(0x217B, scr->storage & 0xFF);
87 outb(0x217B, (scr->storage>>8) & 0xFF);
89 outb(0x217B, (scr->storage>>16) & 0x0F);
93 * Row offset in "quadwords". Must be 2 for Sprite.
94 * Bag the pixel-panning.
95 * Colour depth, must be 2 for Sprite.
106 // if(vgascreen.ldepth == 3)
109 // outb(0x217B, 0x00);
112 * Enable the CRTCB/Sprite.
116 outb(0x217B, 0x80|imaF7);
120 et4000load(VGAscr *scr, Cursor *c)
125 uchar clr[2*16], set[2*16];
128 * Lock the display memory so we can update the
129 * cursor bitmap if necessary.
134 * Disable the cursor.
135 * Set the display page (do we need to restore
136 * the current contents when done?) and the
137 * pointer to the two planes. What if this crosses
142 setet4000page(scr->storage>>16);
143 mem = (uchar*)scr->vaddr + (scr->storage & 0xFFFF);
146 * Initialise the 64x64 cursor RAM array. There are 2 planes,
147 * p0 and p1. Data is written 4 pixels per byte, with p1 the
148 * MS bit of each pixel.
149 * The cursor mode gives the following truth table:
151 * 0 0 Sprite Colour 0 (defined as 0x00)
152 * 0 1 Sprite Colour 1 (defined as 0xFF)
153 * 1 0 Transparent (allow CRTC pixel pass through)
154 * 1 1 Invert (allow CRTC pixel invert through)
155 * Put the cursor into the top-left of the 64x64 array.
157 * This is almost certainly wrong, since it has not
158 * been updated for the 3rd edition color values.
160 memmove(clr, c->clr, sizeof(clr));
161 // pixreverse(clr, sizeof(clr), 0);
162 memmove(set, c->set, sizeof(set));
163 // pixreverse(set, sizeof(set), 0);
164 for(y = 0; y < 64; y++){
165 for(x = 0; x < 64/8; x++){
166 if(x < 16/8 && y < 16){
171 for(i = 0; i < 8; i++){
175 else if(p0 & (1<<(7-i)))
181 *mem++ = (p>>8) & 0xFF;
194 p = inb(0x217B)|0x80;
197 unlock(&scr->devlock);
201 et4000move(VGAscr *scr, Point p)
205 if(canlock(&scr->devlock) == 0)
209 * Mustn't position the cursor offscreen even partially,
210 * or it disappears. Therefore, if x or y is -ve, adjust the
211 * cursor presets instead.
213 if((x = p.x+scr->offset.x) < 0){
219 if((y = p.y+scr->offset.y) < 0){
227 * The cursor image is jerky if we don't do this.
228 * The cursor information is probably fetched from
229 * display memory during the horizontal blank active
230 * time and it doesn't like it if the coordinates
231 * are changed underneath.
233 while((vgai(Status1) & 0x08) == 0)
243 outb(0x217B, (x>>8) & 0xFF);
245 outb(0x217B, x & 0xFF);
247 outb(0x217B, (y>>8) & 0xFF);
249 outb(0x217B, y & 0xFF);
251 unlock(&scr->devlock);
255 VGAcur vgaet4000cur = {
264 VGAdev vgaet4000dev = {