2 * Copyright © 1999 Keith Packard
4 * Permission to use, copy, modify, distribute, and sell this software and its
5 * documentation for any purpose is hereby granted without fee, provided that
6 * the above copyright notice appear in all copies and that both that
7 * copyright notice and this permission notice appear in supporting
8 * documentation, and that the name of Keith Packard not be used in
9 * advertising or publicity pertaining to distribution of the software without
10 * specific, written prior permission. Keith Packard makes no
11 * representations about the suitability of this software for any purpose. It
12 * is provided "as is" without express or implied warranty.
14 * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
15 * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
16 * EVENT SHALL KEITH PACKARD BE LIABLE FOR ANY SPECIAL, INDIRECT OR
17 * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
18 * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
19 * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
20 * PERFORMANCE OF THIS SOFTWARE.
24 #include <kdrive-config.h>
35 #define _VgaInb(r) inb(r)
36 #define _VgaOutb(v,r) outb(v,r)
42 #define _VgaByteAddr(a) ((VGAVOL8 *) (a))
43 #define _VgaBytePort(a) (a)
48 #define _VgaOutb(v,r) 0
50 #define _VgaByteAddr(a) ((VGAVOL8 *) ((VGA32) (a) ^ 3))
51 #define _VgaBytePort(a) 0
58 #undef VGA_DEBUG_REGISTERS
59 #ifdef VGA_DEBUG_REGISTERS
60 #define VGA_DEBUG(a) fprintf a
72 VgaOutb (VGA8 v
, VGA16 r
)
78 VgaReadMemb (VGA32 addr
)
80 return *_VgaByteAddr(addr
);
84 VgaWriteMemb (VGA8 v
, VGA32 addr
)
86 *_VgaByteAddr(addr
) = v
;
90 VgaFetch (VgaCard
*card
, VGA16 reg
)
95 (*card
->map
) (card
, reg
, &map
, VGAFALSE
);
98 value
= VgaReadMemb (map
.port
);
99 VGA_DEBUG ((stderr
, "%08x -> %2x\n", map
.port
, value
));
102 value
= _VgaInb (map
.port
);
103 VGA_DEBUG ((stderr
, "%4x -> %2x\n", map
.port
, value
));
105 case VgaAccessIndMem
:
106 VgaWriteMemb (map
.index
, map
.port
+ map
.addr
);
107 value
= VgaReadMemb (map
.port
+ map
.value
);
108 VGA_DEBUG ((stderr
, "%4x/%2x -> %2x\n", map
.port
, map
.index
, value
));
111 _VgaOutb (map
.index
, map
.port
+ map
.addr
);
112 value
= _VgaInb (map
.port
+ map
.value
);
113 VGA_DEBUG ((stderr
, "%4x/%2x -> %2x\n", map
.port
, map
.index
, value
));
117 VGA_DEBUG ((stderr
, "direct %4x -> %2x\n", reg
, value
));
124 VgaStore (VgaCard
*card
, VGA16 reg
, VGA8 value
)
129 (*card
->map
) (card
, reg
, &map
, VGATRUE
);
130 switch (map
.access
) {
132 VGA_DEBUG ((stderr
, "%8x <- %2x\n", map
.port
, value
));
133 VgaWriteMemb (map
.value
, map
.port
);
136 VGA_DEBUG ((stderr
, "%4x <- %2x\n", map
.port
, value
));
137 _VgaOutb (value
, map
.port
);
139 case VgaAccessIndMem
:
140 VgaWriteMemb (map
.index
, map
.port
+ map
.addr
);
141 VgaWriteMemb (value
, map
.port
+ map
.value
);
142 VGA_DEBUG ((stderr
, "%4x/%2x <- %2x\n", map
.port
, map
.index
, value
));
145 VGA_DEBUG ((stderr
, "%4x/%2x <- %2x\n", map
.port
, map
.index
, value
));
146 _VgaOutb (map
.index
, map
.port
+ map
.addr
);
147 _VgaOutb (value
, map
.port
+ map
.value
);
150 VGA_DEBUG ((stderr
, "direct %4x <- %2x\n", reg
, value
));
156 VgaPreserve (VgaCard
*card
)
161 for (s
= card
->saves
; s
->first
!= VGA_REG_NONE
; s
++)
163 for (id
= s
->first
; id
<= s
->last
; id
++)
165 card
->values
[id
].cur
= VgaFetch (card
, id
);
166 card
->values
[id
].save
= card
->values
[id
].cur
;
167 card
->values
[id
].flags
= VGA_VALUE_VALID
| VGA_VALUE_SAVED
;
173 VgaRestore (VgaCard
*card
)
178 for (s
= card
->saves
; s
->first
!= VGA_REG_NONE
; s
++)
180 for (id
= s
->first
; id
<= s
->last
; id
++)
182 if (card
->values
[id
].flags
& VGA_VALUE_SAVED
)
184 VgaStore (card
, id
, card
->values
[id
].save
);
185 card
->values
[id
].cur
= card
->values
[id
].save
;
192 VgaFinish (VgaCard
*card
)
196 for (id
= 0; id
< card
->max
; id
++)
197 card
->values
[id
].flags
= 0;
201 VgaInvalidate (VgaCard
*card
)
205 for (id
= 0; id
< card
->max
; id
++)
206 card
->values
[id
].flags
&= ~VGA_VALUE_VALID
;
211 _VgaSync (VgaCard
*card
, VGA16 id
)
213 if (!(card
->values
[id
].flags
& VGA_VALUE_VALID
))
215 card
->values
[id
].cur
= VgaFetch (card
, id
);
216 card
->values
[id
].flags
|= VGA_VALUE_VALID
;
221 VgaSet (VgaCard
*card
, VgaReg
*reg
, VGA32 value
)
227 if (reg
->id
!= VGA_REG_NONE
)
229 _VgaSync (card
, reg
->id
);
230 mask
= ((1 << reg
->len
) - 1);
234 v
= card
->values
[reg
->id
].cur
;
235 v
= (v
& ~mask
) | new;
236 card
->values
[reg
->id
].cur
= v
;
237 card
->values
[reg
->id
].flags
|= VGA_VALUE_MODIFIED
|VGA_VALUE_DIRTY
;
245 VgaFlushReg (VgaCard
*card
, VgaReg
*reg
)
249 if (reg
->id
!= VGA_REG_NONE
)
251 if (card
->values
[reg
->id
].flags
& VGA_VALUE_DIRTY
)
253 VgaStore (card
, reg
->id
, card
->values
[reg
->id
].cur
);
254 card
->values
[reg
->id
].flags
&= ~VGA_VALUE_DIRTY
;
263 VgaSetImm (VgaCard
*card
, VgaReg
*reg
, VGA32 value
)
265 VgaSet (card
, reg
, value
);
266 VgaFlushReg (card
, reg
);
270 VgaGet (VgaCard
*card
, VgaReg
*reg
)
272 VGA32 value
, offset
, v
;
279 if (reg
->id
!= VGA_REG_NONE
)
281 _VgaSync (card
, reg
->id
);
282 mask
= ((1 << reg
->len
) - 1);
283 v
= (card
->values
[reg
->id
].cur
>> reg
->base
) & mask
;
284 value
|= (v
<< offset
);
293 VgaGetImm (VgaCard
*card
, VgaReg
*reg
)
299 if (r
->id
!= VGA_REG_NONE
)
300 card
->values
[r
->id
].flags
&= ~VGA_VALUE_VALID
;
303 return VgaGet (card
, reg
);
307 VgaFlush (VgaCard
*card
)
311 for (id
= 0; id
< card
->max
; id
++)
313 if (card
->values
[id
].flags
& VGA_VALUE_DIRTY
)
315 VgaStore (card
, id
, card
->values
[id
].cur
);
316 card
->values
[id
].flags
&= ~VGA_VALUE_DIRTY
;
322 VgaFill (VgaCard
*card
, VGA16 low
, VGA16 high
)
326 for (id
= low
; id
< high
; id
++)