vreset.c revision 1.4 1 1.4 garbled /* $NetBSD: vreset.c,v 1.4 2006/04/10 18:40:06 garbled Exp $ */
2 1.1 nonaka
3 1.1 nonaka /*
4 1.1 nonaka * Copyright (C) 1995-1997 Gary Thomas (gdt (at) linuxppc.org)
5 1.1 nonaka * All rights reserved.
6 1.1 nonaka *
7 1.1 nonaka * Initialize the VGA control registers to 80x25 text mode.
8 1.1 nonaka *
9 1.1 nonaka * Adapted from a program by:
10 1.1 nonaka * Steve Sellgren
11 1.1 nonaka * San Francisco Indigo Company
12 1.1 nonaka * sfindigo!sellgren (at) uunet.uu.net
13 1.1 nonaka * Adapted for Moto boxes by:
14 1.1 nonaka * Pat Kane & Mark Scott, 1996
15 1.1 nonaka * Fixed for IBM/PowerStack II Pat Kane 1997
16 1.1 nonaka *
17 1.1 nonaka * Redistribution and use in source and binary forms, with or without
18 1.1 nonaka * modification, are permitted provided that the following conditions
19 1.1 nonaka * are met:
20 1.1 nonaka * 1. Redistributions of source code must retain the above copyright
21 1.1 nonaka * notice, this list of conditions and the following disclaimer.
22 1.1 nonaka * 2. Redistributions in binary form must reproduce the above copyright
23 1.1 nonaka * notice, this list of conditions and the following disclaimer in the
24 1.1 nonaka * documentation and/or other materials provided with the distribution.
25 1.1 nonaka * 3. All advertising materials mentioning features or use of this software
26 1.1 nonaka * must display the following acknowledgement:
27 1.1 nonaka * This product includes software developed by Gary Thomas.
28 1.1 nonaka * 4. The name of the author may not be used to endorse or promote products
29 1.1 nonaka * derived from this software without specific prior written permission.
30 1.1 nonaka *
31 1.1 nonaka * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
32 1.1 nonaka * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
33 1.1 nonaka * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
34 1.1 nonaka * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
35 1.1 nonaka * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
36 1.1 nonaka * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
37 1.1 nonaka * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
38 1.1 nonaka * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
39 1.1 nonaka * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
40 1.1 nonaka * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
41 1.1 nonaka */
42 1.1 nonaka
43 1.1 nonaka #ifdef CONS_VGA
44 1.1 nonaka #include <lib/libsa/stand.h>
45 1.3 dsl #include <sys/bswap.h>
46 1.1 nonaka #include "boot.h"
47 1.1 nonaka #include "iso_font.h"
48 1.1 nonaka
49 1.4 garbled static inline void outw(int, u_short);
50 1.4 garbled void writeAttr(u_char, u_char, u_char);
51 1.1 nonaka
52 1.1 nonaka
53 1.1 nonaka #if 0
54 1.1 nonaka static char rcsid[] = "vreset.c 2.0 1997 kane PEK'97 Exp $";
55 1.1 nonaka #endif
56 1.1 nonaka
57 1.1 nonaka /*
58 1.1 nonaka * VGA Register
59 1.1 nonaka */
60 1.1 nonaka struct VgaRegs
61 1.1 nonaka {
62 1.1 nonaka u_short io_port;
63 1.1 nonaka u_char io_index;
64 1.1 nonaka u_char io_value;
65 1.1 nonaka };
66 1.1 nonaka
67 1.1 nonaka /*
68 1.1 nonaka * Default console text mode registers used to reset
69 1.1 nonaka * graphics adapter.
70 1.1 nonaka */
71 1.1 nonaka #define NREGS 54
72 1.1 nonaka #define ENDMK 0xFFFF /* End marker */
73 1.1 nonaka
74 1.1 nonaka #define S3Vendor 0x5333
75 1.1 nonaka #define CirrusVendor 0x1013
76 1.1 nonaka #define DiamondVendor 0x100E
77 1.1 nonaka #define MatroxVendor 0x102B
78 1.1 nonaka
79 1.1 nonaka struct VgaRegs GenVgaTextRegs[NREGS+1] = {
80 1.1 nonaka /* port index value */
81 1.1 nonaka /* SR Regs */
82 1.1 nonaka { 0x3c4, 0x1, 0x0 },
83 1.1 nonaka { 0x3c4, 0x2, 0x3 },
84 1.1 nonaka { 0x3c4, 0x3, 0x0 },
85 1.1 nonaka { 0x3c4, 0x4, 0x2 },
86 1.1 nonaka /* CR Regs */
87 1.1 nonaka { 0x3d4, 0x0, 0x5f },
88 1.1 nonaka { 0x3d4, 0x1, 0x4f },
89 1.1 nonaka { 0x3d4, 0x2, 0x50 },
90 1.1 nonaka { 0x3d4, 0x3, 0x82 },
91 1.1 nonaka { 0x3d4, 0x4, 0x55 },
92 1.1 nonaka { 0x3d4, 0x5, 0x81 },
93 1.1 nonaka { 0x3d4, 0x6, 0xbf },
94 1.1 nonaka { 0x3d4, 0x7, 0x1f },
95 1.1 nonaka { 0x3d4, 0x8, 0x00 },
96 1.1 nonaka { 0x3d4, 0x9, 0x4f },
97 1.1 nonaka { 0x3d4, 0xa, 0x0d },
98 1.1 nonaka { 0x3d4, 0xb, 0x0e },
99 1.1 nonaka { 0x3d4, 0xc, 0x00 },
100 1.1 nonaka { 0x3d4, 0xd, 0x00 },
101 1.1 nonaka { 0x3d4, 0xe, 0x00 },
102 1.1 nonaka { 0x3d4, 0xf, 0x00 },
103 1.1 nonaka { 0x3d4, 0x10, 0x9c },
104 1.1 nonaka { 0x3d4, 0x11, 0x8e },
105 1.1 nonaka { 0x3d4, 0x12, 0x8f },
106 1.1 nonaka { 0x3d4, 0x13, 0x28 },
107 1.1 nonaka { 0x3d4, 0x14, 0x1f },
108 1.1 nonaka { 0x3d4, 0x15, 0x96 },
109 1.1 nonaka { 0x3d4, 0x16, 0xb9 },
110 1.1 nonaka { 0x3d4, 0x17, 0xa3 },
111 1.1 nonaka /* GR Regs */
112 1.1 nonaka { 0x3ce, 0x0, 0x0 },
113 1.1 nonaka { 0x3ce, 0x1, 0x0 },
114 1.1 nonaka { 0x3ce, 0x2, 0x0 },
115 1.1 nonaka { 0x3ce, 0x3, 0x0 },
116 1.1 nonaka { 0x3ce, 0x4, 0x0 },
117 1.1 nonaka { 0x3ce, 0x5, 0x10 },
118 1.1 nonaka { 0x3ce, 0x6, 0xe },
119 1.1 nonaka { 0x3ce, 0x7, 0x0 },
120 1.1 nonaka { 0x3ce, 0x8, 0xff },
121 1.1 nonaka { ENDMK },
122 1.1 nonaka };
123 1.1 nonaka
124 1.1 nonaka struct VgaRegs S3TextRegs[NREGS+1] = {
125 1.1 nonaka /* port index value */
126 1.1 nonaka /* SR Regs */
127 1.1 nonaka { 0x3c4, 0x1, 0x0 },
128 1.1 nonaka { 0x3c4, 0x2, 0x3 },
129 1.1 nonaka { 0x3c4, 0x3, 0x0 },
130 1.1 nonaka { 0x3c4, 0x4, 0x2 },
131 1.1 nonaka /* CR Regs */
132 1.1 nonaka { 0x3d4, 0x0, 0x5f },
133 1.1 nonaka { 0x3d4, 0x1, 0x4f },
134 1.1 nonaka { 0x3d4, 0x2, 0x50 },
135 1.1 nonaka { 0x3d4, 0x3, 0x82 },
136 1.1 nonaka { 0x3d4, 0x4, 0x55 },
137 1.1 nonaka { 0x3d4, 0x5, 0x81 },
138 1.1 nonaka { 0x3d4, 0x6, 0xbf },
139 1.1 nonaka { 0x3d4, 0x7, 0x1f },
140 1.1 nonaka { 0x3d4, 0x8, 0x00 },
141 1.1 nonaka { 0x3d4, 0x9, 0x4f },
142 1.1 nonaka { 0x3d4, 0xa, 0x0d },
143 1.1 nonaka { 0x3d4, 0xb, 0x0e },
144 1.1 nonaka { 0x3d4, 0xc, 0x00 },
145 1.1 nonaka { 0x3d4, 0xd, 0x00 },
146 1.1 nonaka { 0x3d4, 0xe, 0x00 },
147 1.1 nonaka { 0x3d4, 0xf, 0x00 },
148 1.1 nonaka { 0x3d4, 0x10, 0x9c },
149 1.1 nonaka { 0x3d4, 0x11, 0x8e },
150 1.1 nonaka { 0x3d4, 0x12, 0x8f },
151 1.1 nonaka { 0x3d4, 0x13, 0x28 },
152 1.1 nonaka { 0x3d4, 0x14, 0x1f },
153 1.1 nonaka { 0x3d4, 0x15, 0x96 },
154 1.1 nonaka { 0x3d4, 0x16, 0xb9 },
155 1.1 nonaka { 0x3d4, 0x17, 0xa3 },
156 1.1 nonaka /* GR Regs */
157 1.1 nonaka { 0x3ce, 0x0, 0x0 },
158 1.1 nonaka { 0x3ce, 0x1, 0x0 },
159 1.1 nonaka { 0x3ce, 0x2, 0x0 },
160 1.1 nonaka { 0x3ce, 0x3, 0x0 },
161 1.1 nonaka { 0x3ce, 0x4, 0x0 },
162 1.1 nonaka { 0x3ce, 0x5, 0x10 },
163 1.1 nonaka { 0x3ce, 0x6, 0xe },
164 1.1 nonaka { 0x3ce, 0x7, 0x0 },
165 1.1 nonaka { 0x3ce, 0x8, 0xff },
166 1.1 nonaka { ENDMK }
167 1.1 nonaka };
168 1.1 nonaka
169 1.1 nonaka struct RGBColors
170 1.1 nonaka {
171 1.1 nonaka u_char r, g, b;
172 1.1 nonaka };
173 1.1 nonaka
174 1.1 nonaka /*
175 1.1 nonaka * Default console text mode color table.
176 1.1 nonaka * These values were obtained by booting Linux with
177 1.1 nonaka * text mode firmware & then dumping the registers.
178 1.1 nonaka */
179 1.1 nonaka struct RGBColors TextCLUT[256] =
180 1.1 nonaka {
181 1.1 nonaka /* red green blue */
182 1.1 nonaka { 0x0, 0x0, 0x0 },
183 1.1 nonaka { 0x0, 0x0, 0x2a },
184 1.1 nonaka { 0x0, 0x2a, 0x0 },
185 1.1 nonaka { 0x0, 0x2a, 0x2a },
186 1.1 nonaka { 0x2a, 0x0, 0x0 },
187 1.1 nonaka { 0x2a, 0x0, 0x2a },
188 1.1 nonaka { 0x2a, 0x2a, 0x0 },
189 1.1 nonaka { 0x2a, 0x2a, 0x2a },
190 1.1 nonaka { 0x0, 0x0, 0x15 },
191 1.1 nonaka { 0x0, 0x0, 0x3f },
192 1.1 nonaka { 0x0, 0x2a, 0x15 },
193 1.1 nonaka { 0x0, 0x2a, 0x3f },
194 1.1 nonaka { 0x2a, 0x0, 0x15 },
195 1.1 nonaka { 0x2a, 0x0, 0x3f },
196 1.1 nonaka { 0x2a, 0x2a, 0x15 },
197 1.1 nonaka { 0x2a, 0x2a, 0x3f },
198 1.1 nonaka { 0x0, 0x15, 0x0 },
199 1.1 nonaka { 0x0, 0x15, 0x2a },
200 1.1 nonaka { 0x0, 0x3f, 0x0 },
201 1.1 nonaka { 0x0, 0x3f, 0x2a },
202 1.1 nonaka { 0x2a, 0x15, 0x0 },
203 1.1 nonaka { 0x2a, 0x15, 0x2a },
204 1.1 nonaka { 0x2a, 0x3f, 0x0 },
205 1.1 nonaka { 0x2a, 0x3f, 0x2a },
206 1.1 nonaka { 0x0, 0x15, 0x15 },
207 1.1 nonaka { 0x0, 0x15, 0x3f },
208 1.1 nonaka { 0x0, 0x3f, 0x15 },
209 1.1 nonaka { 0x0, 0x3f, 0x3f },
210 1.1 nonaka { 0x2a, 0x15, 0x15 },
211 1.1 nonaka { 0x2a, 0x15, 0x3f },
212 1.1 nonaka { 0x2a, 0x3f, 0x15 },
213 1.1 nonaka { 0x2a, 0x3f, 0x3f },
214 1.1 nonaka { 0x15, 0x0, 0x0 },
215 1.1 nonaka { 0x15, 0x0, 0x2a },
216 1.1 nonaka { 0x15, 0x2a, 0x0 },
217 1.1 nonaka { 0x15, 0x2a, 0x2a },
218 1.1 nonaka { 0x3f, 0x0, 0x0 },
219 1.1 nonaka { 0x3f, 0x0, 0x2a },
220 1.1 nonaka { 0x3f, 0x2a, 0x0 },
221 1.1 nonaka { 0x3f, 0x2a, 0x2a },
222 1.1 nonaka { 0x15, 0x0, 0x15 },
223 1.1 nonaka { 0x15, 0x0, 0x3f },
224 1.1 nonaka { 0x15, 0x2a, 0x15 },
225 1.1 nonaka { 0x15, 0x2a, 0x3f },
226 1.1 nonaka { 0x3f, 0x0, 0x15 },
227 1.1 nonaka { 0x3f, 0x0, 0x3f },
228 1.1 nonaka { 0x3f, 0x2a, 0x15 },
229 1.1 nonaka { 0x3f, 0x2a, 0x3f },
230 1.1 nonaka { 0x15, 0x15, 0x0 },
231 1.1 nonaka { 0x15, 0x15, 0x2a },
232 1.1 nonaka { 0x15, 0x3f, 0x0 },
233 1.1 nonaka { 0x15, 0x3f, 0x2a },
234 1.1 nonaka { 0x3f, 0x15, 0x0 },
235 1.1 nonaka { 0x3f, 0x15, 0x2a },
236 1.1 nonaka { 0x3f, 0x3f, 0x0 },
237 1.1 nonaka { 0x3f, 0x3f, 0x2a },
238 1.1 nonaka { 0x15, 0x15, 0x15 },
239 1.1 nonaka { 0x15, 0x15, 0x3f },
240 1.1 nonaka { 0x15, 0x3f, 0x15 },
241 1.1 nonaka { 0x15, 0x3f, 0x3f },
242 1.1 nonaka { 0x3f, 0x15, 0x15 },
243 1.1 nonaka { 0x3f, 0x15, 0x3f },
244 1.1 nonaka { 0x3f, 0x3f, 0x15 },
245 1.1 nonaka { 0x3f, 0x3f, 0x3f },
246 1.1 nonaka { 0x39, 0xc, 0x5 },
247 1.1 nonaka { 0x15, 0x2c, 0xf },
248 1.1 nonaka { 0x26, 0x10, 0x3d },
249 1.1 nonaka { 0x29, 0x29, 0x38 },
250 1.1 nonaka { 0x4, 0x1a, 0xe },
251 1.1 nonaka { 0x2, 0x1e, 0x3a },
252 1.1 nonaka { 0x3c, 0x25, 0x33 },
253 1.1 nonaka { 0x3c, 0xc, 0x2c },
254 1.1 nonaka { 0x3f, 0x3, 0x2b },
255 1.1 nonaka { 0x1c, 0x9, 0x13 },
256 1.1 nonaka { 0x25, 0x2a, 0x35 },
257 1.1 nonaka { 0x1e, 0xa, 0x38 },
258 1.1 nonaka { 0x24, 0x8, 0x3 },
259 1.1 nonaka { 0x3, 0xe, 0x36 },
260 1.1 nonaka { 0xc, 0x6, 0x2a },
261 1.1 nonaka { 0x26, 0x3, 0x32 },
262 1.1 nonaka { 0x5, 0x2f, 0x33 },
263 1.1 nonaka { 0x3c, 0x35, 0x2f },
264 1.1 nonaka { 0x2d, 0x26, 0x3e },
265 1.1 nonaka { 0xd, 0xa, 0x10 },
266 1.1 nonaka { 0x25, 0x3c, 0x11 },
267 1.1 nonaka { 0xd, 0x4, 0x2e },
268 1.1 nonaka { 0x5, 0x19, 0x3e },
269 1.1 nonaka { 0xc, 0x13, 0x34 },
270 1.1 nonaka { 0x2b, 0x6, 0x24 },
271 1.1 nonaka { 0x4, 0x3, 0xd },
272 1.1 nonaka { 0x2f, 0x3c, 0xc },
273 1.1 nonaka { 0x2a, 0x37, 0x1f },
274 1.1 nonaka { 0xf, 0x12, 0x38 },
275 1.1 nonaka { 0x38, 0xe, 0x2a },
276 1.1 nonaka { 0x12, 0x2f, 0x19 },
277 1.1 nonaka { 0x29, 0x2e, 0x31 },
278 1.1 nonaka { 0x25, 0x13, 0x3e },
279 1.1 nonaka { 0x33, 0x3e, 0x33 },
280 1.1 nonaka { 0x1d, 0x2c, 0x25 },
281 1.1 nonaka { 0x15, 0x15, 0x5 },
282 1.1 nonaka { 0x32, 0x25, 0x39 },
283 1.1 nonaka { 0x1a, 0x7, 0x1f },
284 1.1 nonaka { 0x13, 0xe, 0x1d },
285 1.1 nonaka { 0x36, 0x17, 0x34 },
286 1.1 nonaka { 0xf, 0x15, 0x23 },
287 1.1 nonaka { 0x2, 0x35, 0xd },
288 1.1 nonaka { 0x15, 0x3f, 0xc },
289 1.1 nonaka { 0x14, 0x2f, 0xf },
290 1.1 nonaka { 0x19, 0x21, 0x3e },
291 1.1 nonaka { 0x27, 0x11, 0x2f },
292 1.1 nonaka { 0x38, 0x3f, 0x3c },
293 1.1 nonaka { 0x36, 0x2d, 0x15 },
294 1.1 nonaka { 0x16, 0x17, 0x2 },
295 1.1 nonaka { 0x1, 0xa, 0x3d },
296 1.1 nonaka { 0x1b, 0x11, 0x3f },
297 1.1 nonaka { 0x21, 0x3c, 0xd },
298 1.1 nonaka { 0x1a, 0x39, 0x3d },
299 1.1 nonaka { 0x8, 0xe, 0xe },
300 1.1 nonaka { 0x22, 0x21, 0x23 },
301 1.1 nonaka { 0x1e, 0x30, 0x5 },
302 1.1 nonaka { 0x1f, 0x22, 0x3d },
303 1.1 nonaka { 0x1e, 0x2f, 0xa },
304 1.1 nonaka { 0x0, 0x1c, 0xe },
305 1.1 nonaka { 0x0, 0x1c, 0x15 },
306 1.1 nonaka { 0x0, 0x1c, 0x1c },
307 1.1 nonaka { 0x0, 0x15, 0x1c },
308 1.1 nonaka { 0x0, 0xe, 0x1c },
309 1.1 nonaka { 0x0, 0x7, 0x1c },
310 1.1 nonaka { 0xe, 0xe, 0x1c },
311 1.1 nonaka { 0x11, 0xe, 0x1c },
312 1.1 nonaka { 0x15, 0xe, 0x1c },
313 1.1 nonaka { 0x18, 0xe, 0x1c },
314 1.1 nonaka { 0x1c, 0xe, 0x1c },
315 1.1 nonaka { 0x1c, 0xe, 0x18 },
316 1.1 nonaka { 0x1c, 0xe, 0x15 },
317 1.1 nonaka { 0x1c, 0xe, 0x11 },
318 1.1 nonaka { 0x1c, 0xe, 0xe },
319 1.1 nonaka { 0x1c, 0x11, 0xe },
320 1.1 nonaka { 0x1c, 0x15, 0xe },
321 1.1 nonaka { 0x1c, 0x18, 0xe },
322 1.1 nonaka { 0x1c, 0x1c, 0xe },
323 1.1 nonaka { 0x18, 0x1c, 0xe },
324 1.1 nonaka { 0x15, 0x1c, 0xe },
325 1.1 nonaka { 0x11, 0x1c, 0xe },
326 1.1 nonaka { 0xe, 0x1c, 0xe },
327 1.1 nonaka { 0xe, 0x1c, 0x11 },
328 1.1 nonaka { 0xe, 0x1c, 0x15 },
329 1.1 nonaka { 0xe, 0x1c, 0x18 },
330 1.1 nonaka { 0xe, 0x1c, 0x1c },
331 1.1 nonaka { 0xe, 0x18, 0x1c },
332 1.1 nonaka { 0xe, 0x15, 0x1c },
333 1.1 nonaka { 0xe, 0x11, 0x1c },
334 1.1 nonaka { 0x14, 0x14, 0x1c },
335 1.1 nonaka { 0x16, 0x14, 0x1c },
336 1.1 nonaka { 0x18, 0x14, 0x1c },
337 1.1 nonaka { 0x1a, 0x14, 0x1c },
338 1.1 nonaka { 0x1c, 0x14, 0x1c },
339 1.1 nonaka { 0x1c, 0x14, 0x1a },
340 1.1 nonaka { 0x1c, 0x14, 0x18 },
341 1.1 nonaka { 0x1c, 0x14, 0x16 },
342 1.1 nonaka { 0x1c, 0x14, 0x14 },
343 1.1 nonaka { 0x1c, 0x16, 0x14 },
344 1.1 nonaka { 0x1c, 0x18, 0x14 },
345 1.1 nonaka { 0x1c, 0x1a, 0x14 },
346 1.1 nonaka { 0x1c, 0x1c, 0x14 },
347 1.1 nonaka { 0x1a, 0x1c, 0x14 },
348 1.1 nonaka { 0x18, 0x1c, 0x14 },
349 1.1 nonaka { 0x16, 0x1c, 0x14 },
350 1.1 nonaka { 0x14, 0x1c, 0x14 },
351 1.1 nonaka { 0x14, 0x1c, 0x16 },
352 1.1 nonaka { 0x14, 0x1c, 0x18 },
353 1.1 nonaka { 0x14, 0x1c, 0x1a },
354 1.1 nonaka { 0x14, 0x1c, 0x1c },
355 1.1 nonaka { 0x14, 0x1a, 0x1c },
356 1.1 nonaka { 0x14, 0x18, 0x1c },
357 1.1 nonaka { 0x14, 0x16, 0x1c },
358 1.1 nonaka { 0x0, 0x0, 0x10 },
359 1.1 nonaka { 0x4, 0x0, 0x10 },
360 1.1 nonaka { 0x8, 0x0, 0x10 },
361 1.1 nonaka { 0xc, 0x0, 0x10 },
362 1.1 nonaka { 0x10, 0x0, 0x10 },
363 1.1 nonaka { 0x10, 0x0, 0xc },
364 1.1 nonaka { 0x10, 0x0, 0x8 },
365 1.1 nonaka { 0x10, 0x0, 0x4 },
366 1.1 nonaka { 0x10, 0x0, 0x0 },
367 1.1 nonaka { 0x10, 0x4, 0x0 },
368 1.1 nonaka { 0x10, 0x8, 0x0 },
369 1.1 nonaka { 0x10, 0xc, 0x0 },
370 1.1 nonaka { 0x10, 0x10, 0x0 },
371 1.1 nonaka { 0xc, 0x10, 0x0 },
372 1.1 nonaka { 0x8, 0x10, 0x0 },
373 1.1 nonaka { 0x4, 0x10, 0x0 },
374 1.1 nonaka { 0x0, 0x10, 0x0 },
375 1.1 nonaka { 0x0, 0x10, 0x4 },
376 1.1 nonaka { 0x0, 0x10, 0x8 },
377 1.1 nonaka { 0x0, 0x10, 0xc },
378 1.1 nonaka { 0x0, 0x10, 0x10 },
379 1.1 nonaka { 0x0, 0xc, 0x10 },
380 1.1 nonaka { 0x0, 0x8, 0x10 },
381 1.1 nonaka { 0x0, 0x4, 0x10 },
382 1.1 nonaka { 0x8, 0x8, 0x10 },
383 1.1 nonaka { 0xa, 0x8, 0x10 },
384 1.1 nonaka { 0xc, 0x8, 0x10 },
385 1.1 nonaka { 0xe, 0x8, 0x10 },
386 1.1 nonaka { 0x10, 0x8, 0x10 },
387 1.1 nonaka { 0x10, 0x8, 0xe },
388 1.1 nonaka { 0x10, 0x8, 0xc },
389 1.1 nonaka { 0x10, 0x8, 0xa },
390 1.1 nonaka { 0x10, 0x8, 0x8 },
391 1.1 nonaka { 0x10, 0xa, 0x8 },
392 1.1 nonaka { 0x10, 0xc, 0x8 },
393 1.1 nonaka { 0x10, 0xe, 0x8 },
394 1.1 nonaka { 0x10, 0x10, 0x8 },
395 1.1 nonaka { 0xe, 0x10, 0x8 },
396 1.1 nonaka { 0xc, 0x10, 0x8 },
397 1.1 nonaka { 0xa, 0x10, 0x8 },
398 1.1 nonaka { 0x8, 0x10, 0x8 },
399 1.1 nonaka { 0x8, 0x10, 0xa },
400 1.1 nonaka { 0x8, 0x10, 0xc },
401 1.1 nonaka { 0x8, 0x10, 0xe },
402 1.1 nonaka { 0x8, 0x10, 0x10 },
403 1.1 nonaka { 0x8, 0xe, 0x10 },
404 1.1 nonaka { 0x8, 0xc, 0x10 },
405 1.1 nonaka { 0x8, 0xa, 0x10 },
406 1.1 nonaka { 0xb, 0xb, 0x10 },
407 1.1 nonaka { 0xc, 0xb, 0x10 },
408 1.1 nonaka { 0xd, 0xb, 0x10 },
409 1.1 nonaka { 0xf, 0xb, 0x10 },
410 1.1 nonaka { 0x10, 0xb, 0x10 },
411 1.1 nonaka { 0x10, 0xb, 0xf },
412 1.1 nonaka { 0x10, 0xb, 0xd },
413 1.1 nonaka { 0x10, 0xb, 0xc },
414 1.1 nonaka { 0x10, 0xb, 0xb },
415 1.1 nonaka { 0x10, 0xc, 0xb },
416 1.1 nonaka { 0x10, 0xd, 0xb },
417 1.1 nonaka { 0x10, 0xf, 0xb },
418 1.1 nonaka { 0x10, 0x10, 0xb },
419 1.1 nonaka { 0xf, 0x10, 0xb },
420 1.1 nonaka { 0xd, 0x10, 0xb },
421 1.1 nonaka { 0xc, 0x10, 0xb },
422 1.1 nonaka { 0xb, 0x10, 0xb },
423 1.1 nonaka { 0xb, 0x10, 0xc },
424 1.1 nonaka { 0xb, 0x10, 0xd },
425 1.1 nonaka { 0xb, 0x10, 0xf },
426 1.1 nonaka { 0xb, 0x10, 0x10 },
427 1.1 nonaka { 0xb, 0xf, 0x10 },
428 1.1 nonaka { 0xb, 0xd, 0x10 },
429 1.1 nonaka { 0xb, 0xc, 0x10 },
430 1.1 nonaka { 0x0, 0x0, 0x0 },
431 1.1 nonaka { 0x0, 0x0, 0x0 },
432 1.1 nonaka { 0x0, 0x0, 0x0 },
433 1.1 nonaka { 0x0, 0x0, 0x0 },
434 1.1 nonaka { 0x0, 0x0, 0x0 },
435 1.1 nonaka { 0x0, 0x0, 0x0 },
436 1.1 nonaka { 0x0, 0x0, 0x0 },
437 1.1 nonaka };
438 1.1 nonaka
439 1.1 nonaka u_char AC[21] = {
440 1.1 nonaka 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x14, 0x07,
441 1.1 nonaka 0x38, 0x39, 0x3A, 0x3B, 0x3C, 0x3D, 0x3E, 0x3F,
442 1.1 nonaka 0x0C, 0x00, 0x0F, 0x08, 0x00
443 1.1 nonaka };
444 1.1 nonaka
445 1.4 garbled void enablePCIvideo(int);
446 1.4 garbled static int scanPCI(void);
447 1.4 garbled static int PCIVendor(int);
448 1.4 garbled int delayLoop(int);
449 1.4 garbled void setTextRegs(struct VgaRegs *);
450 1.4 garbled void setTextCLUT(void);
451 1.4 garbled void loadFont(u_char *);
452 1.4 garbled void unlockS3(void);
453 1.1 nonaka #ifdef DEBUG
454 1.4 garbled static void printslots(void);
455 1.1 nonaka #endif
456 1.1 nonaka
457 1.1 nonaka static inline void
458 1.4 garbled outw(int port, u_short val)
459 1.1 nonaka {
460 1.1 nonaka outb(port, val >> 8);
461 1.1 nonaka outb(port+1, val);
462 1.1 nonaka }
463 1.1 nonaka
464 1.1 nonaka void
465 1.4 garbled vga_reset(u_char *ISA_mem)
466 1.1 nonaka {
467 1.1 nonaka int slot;
468 1.1 nonaka struct VgaRegs *VgaTextRegs;
469 1.1 nonaka
470 1.1 nonaka /* See if VGA already in TEXT mode - exit if so! */
471 1.1 nonaka outb(0x3CE, 0x06);
472 1.1 nonaka if ((inb(0x3CF) & 0x01) == 0) return;
473 1.1 nonaka
474 1.1 nonaka /* If no VGA responding in text mode, then we have some work to do... */
475 1.1 nonaka slot = scanPCI(); /* find video card in use */
476 1.1 nonaka enablePCIvideo(slot); /* enable I/O to card */
477 1.1 nonaka
478 1.1 nonaka /*
479 1.1 nonaka * Note: the PCI scanning code does not yet work correctly
480 1.1 nonaka * for non-Moto boxes, so the switch below only
481 1.1 nonaka * defaults to using an S3 card if it does not
482 1.1 nonaka * find a Cirrus card.
483 1.1 nonaka *
484 1.1 nonaka * The only reason we need to scan the bus looking for
485 1.1 nonaka * a graphics card is so we could do the "enablePCIvideo(slot)"
486 1.1 nonaka * call above; it is needed because Moto's OpenFirmware
487 1.1 nonaka * disables I/O to the graphics adapter before it gives
488 1.1 nonaka * us control. PEK'97
489 1.1 nonaka */
490 1.1 nonaka
491 1.1 nonaka switch (PCIVendor(slot)) {
492 1.1 nonaka default: /* Assume S3 */
493 1.1 nonaka /* case(S3Vendor): */
494 1.1 nonaka unlockS3();
495 1.1 nonaka VgaTextRegs = S3TextRegs;
496 1.1 nonaka outw(0x3C4, 0x0120); /* disable video */
497 1.1 nonaka setTextRegs(VgaTextRegs); /* initial register setup */
498 1.1 nonaka setTextCLUT(); /* load color lookup table */
499 1.1 nonaka loadFont(ISA_mem); /* load font */
500 1.1 nonaka setTextRegs(VgaTextRegs); /* reload registers */
501 1.1 nonaka outw(0x3C4, 0x0100); /* re-enable video */
502 1.1 nonaka outb(0x3c2, 0x63); /* MISC */
503 1.1 nonaka outb(0x3c2, 0x67); /* MISC */
504 1.1 nonaka break;
505 1.1 nonaka
506 1.1 nonaka case(CirrusVendor):
507 1.1 nonaka VgaTextRegs = GenVgaTextRegs;
508 1.1 nonaka outw(0x3C4, 0x0612); /* unlock ext regs */
509 1.1 nonaka outw(0x3C4, 0x0700); /* reset ext sequence mode */
510 1.1 nonaka outw(0x3C4, 0x0120); /* disable video */
511 1.1 nonaka setTextRegs(VgaTextRegs); /* initial register setup */
512 1.1 nonaka setTextCLUT(); /* load color lookup table */
513 1.1 nonaka loadFont(ISA_mem); /* load font */
514 1.1 nonaka setTextRegs(VgaTextRegs); /* reload registers */
515 1.1 nonaka outw(0x3C4, 0x0100); /* re-enable video */
516 1.1 nonaka outb(0x3c2, 0x63); /* MISC */
517 1.1 nonaka break;
518 1.1 nonaka
519 1.1 nonaka case (DiamondVendor):
520 1.1 nonaka case (MatroxVendor):
521 1.1 nonaka /*
522 1.1 nonaka * The following code is almost enuf to get the Matrox
523 1.1 nonaka * working (on a Moto box) but the video is not stable.
524 1.1 nonaka * We probably need to tweak the TVP3026 Video PLL regs. PEK'97
525 1.1 nonaka */
526 1.1 nonaka VgaTextRegs = GenVgaTextRegs;
527 1.1 nonaka outw(0x3C4, 0x0120); /* disable video */
528 1.1 nonaka setTextRegs(VgaTextRegs); /* initial register setup */
529 1.1 nonaka setTextCLUT(); /* load color lookup table */
530 1.1 nonaka loadFont(ISA_mem); /* load font */
531 1.1 nonaka setTextRegs(VgaTextRegs); /* reload registers */
532 1.1 nonaka outw(0x3C4, 0x0100); /* re-enable video */
533 1.1 nonaka outb(0x3c2, 0x63); /* MISC */
534 1.1 nonaka printf("VGA Chip Vendor ID: 0x%08x\n", PCIVendor(slot));
535 1.1 nonaka delayLoop(1);
536 1.1 nonaka break;
537 1.1 nonaka };
538 1.1 nonaka
539 1.1 nonaka
540 1.1 nonaka #ifdef DEBUG
541 1.1 nonaka printslots();
542 1.1 nonaka delayLoop(5);
543 1.1 nonaka #endif
544 1.1 nonaka
545 1.1 nonaka delayLoop(2); /* give time for the video monitor to come up */
546 1.1 nonaka }
547 1.1 nonaka
548 1.1 nonaka /*
549 1.1 nonaka * Write to VGA Attribute registers.
550 1.1 nonaka */
551 1.1 nonaka void
552 1.4 garbled writeAttr(u_char index, u_char data, u_char videoOn)
553 1.1 nonaka {
554 1.1 nonaka u_char v;
555 1.1 nonaka v = inb(0x3da); /* reset attr. address toggle */
556 1.1 nonaka if (videoOn)
557 1.1 nonaka outb(0x3c0, (index & 0x1F) | 0x20);
558 1.1 nonaka else
559 1.1 nonaka outb(0x3c0, (index & 0x1F));
560 1.1 nonaka outb(0x3c0, data);
561 1.1 nonaka }
562 1.1 nonaka
563 1.1 nonaka void
564 1.4 garbled setTextRegs(struct VgaRegs *svp)
565 1.1 nonaka {
566 1.1 nonaka int i;
567 1.1 nonaka
568 1.1 nonaka /*
569 1.1 nonaka * saved settings
570 1.1 nonaka */
571 1.1 nonaka while (svp->io_port != ENDMK) {
572 1.1 nonaka outb(svp->io_port, svp->io_index);
573 1.1 nonaka outb(svp->io_port+1, svp->io_value);
574 1.1 nonaka svp++;
575 1.1 nonaka }
576 1.1 nonaka
577 1.1 nonaka outb(0x3c2, 0x67); /* MISC */
578 1.1 nonaka outb(0x3c6, 0xff); /* MASK */
579 1.1 nonaka
580 1.1 nonaka for (i = 0; i < 0x10; i++)
581 1.1 nonaka writeAttr(i, AC[i], 0); /* pallete */
582 1.1 nonaka writeAttr(0x10, 0x0c, 0); /* text mode */
583 1.1 nonaka writeAttr(0x11, 0x00, 0); /* overscan color (border) */
584 1.1 nonaka writeAttr(0x12, 0x0f, 0); /* plane enable */
585 1.1 nonaka writeAttr(0x13, 0x08, 0); /* pixel panning */
586 1.1 nonaka writeAttr(0x14, 0x00, 1); /* color select; video on */
587 1.1 nonaka }
588 1.1 nonaka
589 1.1 nonaka void
590 1.4 garbled setTextCLUT(void)
591 1.1 nonaka {
592 1.1 nonaka int i;
593 1.1 nonaka
594 1.1 nonaka outb(0x3C6, 0xFF);
595 1.1 nonaka i = inb(0x3C7);
596 1.1 nonaka outb(0x3C8, 0);
597 1.1 nonaka i = inb(0x3C7);
598 1.1 nonaka
599 1.1 nonaka for (i = 0; i < 256; i++) {
600 1.1 nonaka outb(0x3C9, TextCLUT[i].r);
601 1.1 nonaka outb(0x3C9, TextCLUT[i].g);
602 1.1 nonaka outb(0x3C9, TextCLUT[i].b);
603 1.1 nonaka }
604 1.1 nonaka }
605 1.1 nonaka
606 1.1 nonaka void
607 1.4 garbled loadFont(u_char *ISA_mem)
608 1.1 nonaka {
609 1.1 nonaka int i, j;
610 1.1 nonaka u_char *font_page = (u_char *)&ISA_mem[0xA0000];
611 1.1 nonaka
612 1.1 nonaka outb(0x3C2, 0x67);
613 1.1 nonaka /*
614 1.1 nonaka * Load font
615 1.1 nonaka */
616 1.1 nonaka i = inb(0x3DA); /* Reset Attr toggle */
617 1.1 nonaka
618 1.1 nonaka outb(0x3C0,0x30);
619 1.1 nonaka outb(0x3C0, 0x01); /* graphics mode */
620 1.1 nonaka
621 1.1 nonaka outw(0x3C4, 0x0001); /* reset sequencer */
622 1.1 nonaka outw(0x3C4, 0x0204); /* write to plane 2 */
623 1.1 nonaka outw(0x3C4, 0x0406); /* enable plane graphics */
624 1.1 nonaka outw(0x3C4, 0x0003); /* reset sequencer */
625 1.1 nonaka outw(0x3CE, 0x0402); /* read plane 2 */
626 1.1 nonaka outw(0x3CE, 0x0500); /* write mode 0, read mode 0 */
627 1.1 nonaka outw(0x3CE, 0x0605); /* set graphics mode */
628 1.1 nonaka
629 1.1 nonaka for (i = 0; i < sizeof(font); i += 16) {
630 1.1 nonaka for (j = 0; j < 16; j++) {
631 1.2 perry __asm volatile("eieio");
632 1.1 nonaka font_page[(2*i)+j] = font[i+j];
633 1.1 nonaka }
634 1.1 nonaka }
635 1.1 nonaka }
636 1.1 nonaka
637 1.1 nonaka void
638 1.4 garbled unlockS3(void)
639 1.1 nonaka {
640 1.1 nonaka /* From the S3 manual */
641 1.1 nonaka outb(0x46E8, 0x10); /* Put into setup mode */
642 1.1 nonaka outb(0x3C3, 0x10);
643 1.1 nonaka outb(0x102, 0x01); /* Enable registers */
644 1.1 nonaka outb(0x46E8, 0x08); /* Enable video */
645 1.1 nonaka outb(0x3C3, 0x08);
646 1.1 nonaka outb(0x4AE8, 0x00);
647 1.1 nonaka
648 1.1 nonaka outb(0x42E8, 0x80); /* Reset graphics engine? */
649 1.1 nonaka
650 1.1 nonaka outb(0x3D4, 0x38); /* Unlock all registers */
651 1.1 nonaka outb(0x3D5, 0x48);
652 1.1 nonaka outb(0x3D4, 0x39);
653 1.1 nonaka outb(0x3D5, 0xA5);
654 1.1 nonaka outb(0x3D4, 0x40);
655 1.1 nonaka outb(0x3D5, inb(0x3D5)|0x01);
656 1.1 nonaka outb(0x3D4, 0x33);
657 1.1 nonaka outb(0x3D5, inb(0x3D5)&~0x52);
658 1.1 nonaka outb(0x3D4, 0x35);
659 1.1 nonaka outb(0x3D5, inb(0x3D5)&~0x30);
660 1.1 nonaka outb(0x3D4, 0x3A);
661 1.1 nonaka outb(0x3D5, 0x00);
662 1.1 nonaka outb(0x3D4, 0x53);
663 1.1 nonaka outb(0x3D5, 0x00);
664 1.1 nonaka outb(0x3D4, 0x31);
665 1.1 nonaka outb(0x3D5, inb(0x3D5)&~0x4B);
666 1.1 nonaka outb(0x3D4, 0x58);
667 1.1 nonaka
668 1.1 nonaka outb(0x3D5, 0);
669 1.1 nonaka
670 1.1 nonaka outb(0x3D4, 0x54);
671 1.1 nonaka outb(0x3D5, 0x38);
672 1.1 nonaka outb(0x3D4, 0x60);
673 1.1 nonaka outb(0x3D5, 0x07);
674 1.1 nonaka outb(0x3D4, 0x61);
675 1.1 nonaka outb(0x3D5, 0x80);
676 1.1 nonaka outb(0x3D4, 0x62);
677 1.1 nonaka outb(0x3D5, 0xA1);
678 1.1 nonaka outb(0x3D4, 0x69); /* High order bits for cursor address */
679 1.1 nonaka outb(0x3D5, 0);
680 1.1 nonaka
681 1.1 nonaka outb(0x3D4, 0x32);
682 1.1 nonaka outb(0x3D5, inb(0x3D5)&~0x10);
683 1.1 nonaka }
684 1.1 nonaka
685 1.1 nonaka /* ============ */
686 1.1 nonaka
687 1.1 nonaka
688 1.1 nonaka #define NSLOTS 8
689 1.1 nonaka #define NPCIREGS 5
690 1.1 nonaka
691 1.1 nonaka /*
692 1.1 nonaka * should use devfunc number/indirect method to be totally safe on
693 1.1 nonaka * all machines, this works for now on 3 slot Moto boxes
694 1.1 nonaka */
695 1.1 nonaka
696 1.1 nonaka struct PCI_ConfigInfo {
697 1.1 nonaka u_long * config_addr;
698 1.1 nonaka u_long regs[NPCIREGS];
699 1.1 nonaka } PCI_slots [NSLOTS] = {
700 1.1 nonaka { (u_long *)0x80808000, { 0xDE, 0xAD, 0xBE, 0xEF } },
701 1.1 nonaka { (u_long *)0x80800800, { 0xDE, 0xAD, 0xBE, 0xEF } },
702 1.1 nonaka { (u_long *)0x80801000, { 0xDE, 0xAD, 0xBE, 0xEF } },
703 1.1 nonaka { (u_long *)0x80802000, { 0xDE, 0xAD, 0xBE, 0xEF } },
704 1.1 nonaka { (u_long *)0x80804000, { 0xDE, 0xAD, 0xBE, 0xEF } },
705 1.1 nonaka { (u_long *)0x80810000, { 0xDE, 0xAD, 0xBE, 0xEF } },
706 1.1 nonaka { (u_long *)0x80820000, { 0xDE, 0xAD, 0xBE, 0xEF } },
707 1.1 nonaka { (u_long *)0x80840000, { 0xDE, 0xAD, 0xBE, 0xEF } }
708 1.1 nonaka };
709 1.1 nonaka
710 1.1 nonaka
711 1.1 nonaka /*
712 1.1 nonaka * The following code modifies the PCI Command register
713 1.1 nonaka * to enable memory and I/O accesses.
714 1.1 nonaka */
715 1.1 nonaka void
716 1.4 garbled enablePCIvideo(int slot)
717 1.1 nonaka {
718 1.4 garbled volatile u_char * ppci;
719 1.1 nonaka
720 1.4 garbled ppci = (u_char *)PCI_slots[slot].config_addr;
721 1.1 nonaka ppci[4] = 0x0003; /* enable memory and I/O accesses */
722 1.2 perry __asm volatile("eieio");
723 1.1 nonaka
724 1.1 nonaka outb(0x3d4, 0x11);
725 1.1 nonaka outb(0x3d5, 0x0e); /* unlock CR0-CR7 */
726 1.1 nonaka }
727 1.1 nonaka
728 1.1 nonaka #define DEVID 0
729 1.1 nonaka #define CMD 1
730 1.1 nonaka #define CLASS 2
731 1.1 nonaka #define MEMBASE 4
732 1.1 nonaka
733 1.1 nonaka int
734 1.4 garbled scanPCI(void)
735 1.1 nonaka {
736 1.1 nonaka int slt, r;
737 1.1 nonaka struct PCI_ConfigInfo *pslot;
738 1.1 nonaka int theSlot = -1;
739 1.1 nonaka int highVgaSlot = -1;
740 1.1 nonaka
741 1.1 nonaka for (slt = 0; slt < NSLOTS; slt++) {
742 1.1 nonaka pslot = &PCI_slots[slt];
743 1.1 nonaka for (r = 0; r < NPCIREGS; r++) {
744 1.1 nonaka pslot->regs[r] = bswap32(pslot->config_addr[r]);
745 1.1 nonaka }
746 1.1 nonaka
747 1.1 nonaka if (pslot->regs[DEVID] != 0xFFFFFFFF) { /* card in slot ? */
748 1.1 nonaka if ((pslot->regs[CLASS] & 0xFFFFFF00) == 0x03000000) { /* VGA ? */
749 1.1 nonaka highVgaSlot = slt;
750 1.1 nonaka if ((pslot->regs[CMD] & 0x03)) { /* did firmware enable it ? */
751 1.1 nonaka theSlot = slt;
752 1.1 nonaka }
753 1.1 nonaka }
754 1.1 nonaka }
755 1.1 nonaka }
756 1.1 nonaka
757 1.1 nonaka if (theSlot == -1)
758 1.1 nonaka theSlot = highVgaSlot;
759 1.1 nonaka
760 1.1 nonaka return (theSlot);
761 1.1 nonaka }
762 1.1 nonaka
763 1.1 nonaka int
764 1.4 garbled delayLoop(int k)
765 1.1 nonaka {
766 1.1 nonaka volatile int a, b;
767 1.1 nonaka volatile int i, j;
768 1.1 nonaka a = 0;
769 1.1 nonaka do {
770 1.1 nonaka for (i = 0; i < 500; i++) {
771 1.1 nonaka b = i;
772 1.1 nonaka for (j = 0; j < 200; j++) {
773 1.1 nonaka a = b+j;
774 1.1 nonaka }
775 1.1 nonaka }
776 1.1 nonaka } while (k--);
777 1.1 nonaka return(a);
778 1.1 nonaka }
779 1.1 nonaka
780 1.1 nonaka /* return Vendor ID of card in the slot */
781 1.1 nonaka static
782 1.4 garbled int PCIVendor(int slotnum)
783 1.1 nonaka {
784 1.1 nonaka struct PCI_ConfigInfo *pslot;
785 1.1 nonaka
786 1.1 nonaka pslot = &PCI_slots[slotnum];
787 1.1 nonaka
788 1.1 nonaka return (pslot->regs[DEVID] & 0xFFFF);
789 1.1 nonaka }
790 1.1 nonaka
791 1.1 nonaka #ifdef DEBUG
792 1.1 nonaka static
793 1.1 nonaka void
794 1.4 garbled printslots(void)
795 1.1 nonaka {
796 1.1 nonaka int i;
797 1.1 nonaka for (i = 0; i < NSLOTS; i++) {
798 1.1 nonaka
799 1.1 nonaka printf("PCI Slot number: %d", i);
800 1.1 nonaka printf(" Vendor ID: 0x%08x\n", PCIVendor(i));
801 1.1 nonaka }
802 1.1 nonaka }
803 1.1 nonaka #endif /* DEBUG */
804 1.1 nonaka #endif /* CONS_VGA */
805