newport.c revision 1.5.4.4 1 1.5.4.4 skrll /* $NetBSD: newport.c,v 1.5.4.4 2004/09/21 13:21:13 skrll Exp $ */
2 1.5.4.2 skrll
3 1.5.4.2 skrll /*
4 1.5.4.2 skrll * Copyright (c) 2003 Ilpo Ruotsalainen
5 1.5.4.2 skrll * All rights reserved.
6 1.5.4.2 skrll *
7 1.5.4.2 skrll * Redistribution and use in source and binary forms, with or without
8 1.5.4.2 skrll * modification, are permitted provided that the following conditions
9 1.5.4.2 skrll * are met:
10 1.5.4.2 skrll * 1. Redistributions of source code must retain the above copyright
11 1.5.4.2 skrll * notice, this list of conditions and the following disclaimer.
12 1.5.4.2 skrll * 2. Redistributions in binary form must reproduce the above copyright
13 1.5.4.2 skrll * notice, this list of conditions and the following disclaimer in the
14 1.5.4.2 skrll * documentation and/or other materials provided with the distribution.
15 1.5.4.2 skrll * 3. The name of the author may not be used to endorse or promote products
16 1.5.4.2 skrll * derived from this software without specific prior written permission.
17 1.5.4.2 skrll *
18 1.5.4.2 skrll * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
19 1.5.4.2 skrll * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
20 1.5.4.2 skrll * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
21 1.5.4.2 skrll * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
22 1.5.4.2 skrll * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
23 1.5.4.2 skrll * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
24 1.5.4.2 skrll * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
25 1.5.4.2 skrll * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
26 1.5.4.2 skrll * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
27 1.5.4.2 skrll * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
28 1.5.4.2 skrll *
29 1.5.4.2 skrll * <<Id: LICENSE_GC,v 1.1 2001/10/01 23:24:05 cgd Exp>>
30 1.5.4.2 skrll */
31 1.5.4.2 skrll
32 1.5.4.2 skrll #include <sys/cdefs.h>
33 1.5.4.4 skrll __KERNEL_RCSID(0, "$NetBSD: newport.c,v 1.5.4.4 2004/09/21 13:21:13 skrll Exp $");
34 1.5.4.2 skrll
35 1.5.4.2 skrll #include <sys/param.h>
36 1.5.4.2 skrll #include <sys/systm.h>
37 1.5.4.2 skrll #include <sys/device.h>
38 1.5.4.2 skrll #include <sys/malloc.h>
39 1.5.4.2 skrll
40 1.5.4.2 skrll #include <dev/wscons/wsconsio.h>
41 1.5.4.2 skrll #include <dev/wscons/wsdisplayvar.h>
42 1.5.4.2 skrll #include <dev/wsfont/wsfont.h>
43 1.5.4.2 skrll
44 1.5.4.2 skrll #include <sgimips/gio/giovar.h>
45 1.5.4.2 skrll #include <sgimips/gio/newportvar.h>
46 1.5.4.2 skrll #include <sgimips/gio/newportreg.h>
47 1.5.4.2 skrll
48 1.5.4.2 skrll struct newport_softc {
49 1.5.4.2 skrll struct device sc_dev;
50 1.5.4.2 skrll
51 1.5.4.2 skrll struct newport_devconfig *sc_dc;
52 1.5.4.2 skrll };
53 1.5.4.2 skrll
54 1.5.4.2 skrll struct newport_devconfig {
55 1.5.4.2 skrll uint32_t dc_addr;
56 1.5.4.2 skrll
57 1.5.4.2 skrll bus_space_tag_t dc_st;
58 1.5.4.2 skrll bus_space_handle_t dc_sh;
59 1.5.4.2 skrll
60 1.5.4.2 skrll int dc_boardrev;
61 1.5.4.2 skrll int dc_vc2rev;
62 1.5.4.2 skrll int dc_cmaprev;
63 1.5.4.2 skrll int dc_xmaprev;
64 1.5.4.2 skrll int dc_rexrev;
65 1.5.4.2 skrll int dc_xres;
66 1.5.4.2 skrll int dc_yres;
67 1.5.4.2 skrll int dc_depth;
68 1.5.4.2 skrll
69 1.5.4.2 skrll int dc_font;
70 1.5.4.2 skrll struct wsdisplay_font *dc_fontdata;
71 1.5.4.2 skrll };
72 1.5.4.2 skrll
73 1.5.4.2 skrll static int newport_match(struct device *, struct cfdata *, void *);
74 1.5.4.2 skrll static void newport_attach(struct device *, struct device *, void *);
75 1.5.4.2 skrll
76 1.5.4.2 skrll CFATTACH_DECL(newport, sizeof(struct newport_softc),
77 1.5.4.2 skrll newport_match, newport_attach, NULL, NULL);
78 1.5.4.2 skrll
79 1.5.4.2 skrll /* textops */
80 1.5.4.2 skrll static void newport_cursor(void *, int, int, int);
81 1.5.4.2 skrll static int newport_mapchar(void *, int, unsigned int *);
82 1.5.4.2 skrll static void newport_putchar(void *, int, int, u_int, long);
83 1.5.4.2 skrll static void newport_copycols(void *, int, int, int, int);
84 1.5.4.2 skrll static void newport_erasecols(void *, int, int, int, long);
85 1.5.4.2 skrll static void newport_copyrows(void *, int, int, int);
86 1.5.4.2 skrll static void newport_eraserows(void *, int, int, long);
87 1.5.4.2 skrll static int newport_allocattr(void *, int, int, int, long *);
88 1.5.4.2 skrll
89 1.5.4.2 skrll /* accessops */
90 1.5.4.2 skrll static int newport_ioctl(void *, u_long, caddr_t, int, struct proc *);
91 1.5.4.2 skrll static paddr_t newport_mmap(void *, off_t, int);
92 1.5.4.2 skrll static int newport_alloc_screen(void *, const struct wsscreen_descr *,
93 1.5.4.2 skrll void **, int *, int *, long *);
94 1.5.4.2 skrll static void newport_free_screen(void *, void *);
95 1.5.4.2 skrll static int newport_show_screen(void *, void *, int,
96 1.5.4.2 skrll void (*)(void *, int, int), void *);
97 1.5.4.2 skrll
98 1.5.4.2 skrll static const struct wsdisplay_emulops newport_textops = {
99 1.5.4.2 skrll .cursor = newport_cursor,
100 1.5.4.2 skrll .mapchar = newport_mapchar,
101 1.5.4.2 skrll .putchar = newport_putchar,
102 1.5.4.2 skrll .copycols = newport_copycols,
103 1.5.4.2 skrll .erasecols = newport_erasecols,
104 1.5.4.2 skrll .copyrows = newport_copyrows,
105 1.5.4.2 skrll .eraserows = newport_eraserows,
106 1.5.4.2 skrll .allocattr = newport_allocattr
107 1.5.4.2 skrll };
108 1.5.4.2 skrll
109 1.5.4.2 skrll static const struct wsdisplay_accessops newport_accessops = {
110 1.5.4.2 skrll .ioctl = newport_ioctl,
111 1.5.4.2 skrll .mmap = newport_mmap,
112 1.5.4.2 skrll .alloc_screen = newport_alloc_screen,
113 1.5.4.2 skrll .free_screen = newport_free_screen,
114 1.5.4.2 skrll .show_screen = newport_show_screen,
115 1.5.4.2 skrll };
116 1.5.4.2 skrll
117 1.5.4.2 skrll static const struct wsscreen_descr newport_screen_1024x768 = {
118 1.5.4.2 skrll .name = "1024x768",
119 1.5.4.2 skrll .ncols = 128,
120 1.5.4.2 skrll .nrows = 48,
121 1.5.4.2 skrll .textops = &newport_textops,
122 1.5.4.2 skrll .fontwidth = 8,
123 1.5.4.2 skrll .fontheight = 16,
124 1.5.4.2 skrll .capabilities = WSSCREEN_WSCOLORS | WSSCREEN_HILIT | WSSCREEN_REVERSE
125 1.5.4.2 skrll };
126 1.5.4.2 skrll
127 1.5.4.2 skrll static const struct wsscreen_descr newport_screen_1280x1024 = {
128 1.5.4.2 skrll .name = "1280x1024",
129 1.5.4.2 skrll .ncols = 160,
130 1.5.4.2 skrll .nrows = 64,
131 1.5.4.2 skrll .textops = &newport_textops,
132 1.5.4.2 skrll .fontwidth = 8,
133 1.5.4.2 skrll .fontheight = 16,
134 1.5.4.2 skrll .capabilities = WSSCREEN_WSCOLORS | WSSCREEN_HILIT | WSSCREEN_REVERSE
135 1.5.4.2 skrll };
136 1.5.4.2 skrll
137 1.5.4.2 skrll static const struct wsscreen_descr *_newport_screenlist[] = {
138 1.5.4.2 skrll &newport_screen_1024x768,
139 1.5.4.2 skrll &newport_screen_1280x1024
140 1.5.4.2 skrll };
141 1.5.4.2 skrll
142 1.5.4.2 skrll static const struct wsscreen_list newport_screenlist = {
143 1.5.4.2 skrll sizeof(_newport_screenlist) / sizeof(struct wsscreen_descr *),
144 1.5.4.2 skrll _newport_screenlist
145 1.5.4.2 skrll };
146 1.5.4.2 skrll
147 1.5.4.2 skrll static struct newport_devconfig newport_console_dc;
148 1.5.4.2 skrll static int newport_is_console = 0;
149 1.5.4.2 skrll
150 1.5.4.2 skrll #define NEWPORT_ATTR_ENCODE(fg,bg) (((fg) << 8) | (bg))
151 1.5.4.2 skrll #define NEWPORT_ATTR_BG(a) ((a) & 0xff)
152 1.5.4.2 skrll #define NEWPORT_ATTR_FG(a) (((a) >> 8) & 0xff)
153 1.5.4.2 skrll
154 1.5.4.2 skrll static const uint16_t newport_cursor_data[128] = {
155 1.5.4.2 skrll /* Bit 0 */
156 1.5.4.2 skrll 0xff00, 0x0000,
157 1.5.4.2 skrll 0xff00, 0x0000,
158 1.5.4.2 skrll 0xff00, 0x0000,
159 1.5.4.2 skrll 0xff00, 0x0000,
160 1.5.4.2 skrll 0xff00, 0x0000,
161 1.5.4.2 skrll 0xff00, 0x0000,
162 1.5.4.2 skrll 0xff00, 0x0000,
163 1.5.4.2 skrll 0xff00, 0x0000,
164 1.5.4.2 skrll 0xff00, 0x0000,
165 1.5.4.2 skrll 0xff00, 0x0000,
166 1.5.4.2 skrll 0xff00, 0x0000,
167 1.5.4.2 skrll 0xff00, 0x0000,
168 1.5.4.2 skrll 0xff00, 0x0000,
169 1.5.4.2 skrll 0xff00, 0x0000,
170 1.5.4.2 skrll 0xff00, 0x0000,
171 1.5.4.2 skrll 0xff00, 0x0000,
172 1.5.4.2 skrll 0x0000, 0x0000,
173 1.5.4.2 skrll 0x0000, 0x0000,
174 1.5.4.2 skrll 0x0000, 0x0000,
175 1.5.4.2 skrll 0x0000, 0x0000,
176 1.5.4.2 skrll 0x0000, 0x0000,
177 1.5.4.2 skrll 0x0000, 0x0000,
178 1.5.4.2 skrll 0x0000, 0x0000,
179 1.5.4.2 skrll 0x0000, 0x0000,
180 1.5.4.2 skrll 0x0000, 0x0000,
181 1.5.4.2 skrll 0x0000, 0x0000,
182 1.5.4.2 skrll 0x0000, 0x0000,
183 1.5.4.2 skrll 0x0000, 0x0000,
184 1.5.4.2 skrll 0x0000, 0x0000,
185 1.5.4.2 skrll 0x0000, 0x0000,
186 1.5.4.2 skrll 0x0000, 0x0000,
187 1.5.4.2 skrll 0x0000, 0x0000,
188 1.5.4.2 skrll
189 1.5.4.2 skrll /* Bit 1 */
190 1.5.4.2 skrll 0x0000, 0x0000,
191 1.5.4.2 skrll 0x0000, 0x0000,
192 1.5.4.2 skrll 0x0000, 0x0000,
193 1.5.4.2 skrll 0x0000, 0x0000,
194 1.5.4.2 skrll 0x0000, 0x0000,
195 1.5.4.2 skrll 0x0000, 0x0000,
196 1.5.4.2 skrll 0x0000, 0x0000,
197 1.5.4.2 skrll 0x0000, 0x0000,
198 1.5.4.2 skrll 0x0000, 0x0000,
199 1.5.4.2 skrll 0x0000, 0x0000,
200 1.5.4.2 skrll 0x0000, 0x0000,
201 1.5.4.2 skrll 0x0000, 0x0000,
202 1.5.4.2 skrll 0x0000, 0x0000,
203 1.5.4.2 skrll 0x0000, 0x0000,
204 1.5.4.2 skrll 0x0000, 0x0000,
205 1.5.4.2 skrll 0x0000, 0x0000,
206 1.5.4.2 skrll 0x0000, 0x0000,
207 1.5.4.2 skrll 0x0000, 0x0000,
208 1.5.4.2 skrll 0x0000, 0x0000,
209 1.5.4.2 skrll 0x0000, 0x0000,
210 1.5.4.2 skrll 0x0000, 0x0000,
211 1.5.4.2 skrll 0x0000, 0x0000,
212 1.5.4.2 skrll 0x0000, 0x0000,
213 1.5.4.2 skrll 0x0000, 0x0000,
214 1.5.4.2 skrll 0x0000, 0x0000,
215 1.5.4.2 skrll 0x0000, 0x0000,
216 1.5.4.2 skrll 0x0000, 0x0000,
217 1.5.4.2 skrll 0x0000, 0x0000,
218 1.5.4.2 skrll 0x0000, 0x0000,
219 1.5.4.2 skrll 0x0000, 0x0000,
220 1.5.4.2 skrll 0x0000, 0x0000,
221 1.5.4.2 skrll 0x0000, 0x0000,
222 1.5.4.2 skrll };
223 1.5.4.2 skrll
224 1.5.4.2 skrll static const uint8_t newport_defcmap[16*3] = {
225 1.5.4.2 skrll /* Normal colors */
226 1.5.4.2 skrll 0x00, 0x00, 0x00, /* black */
227 1.5.4.2 skrll 0x7f, 0x00, 0x00, /* red */
228 1.5.4.2 skrll 0x00, 0x7f, 0x00, /* green */
229 1.5.4.2 skrll 0x7f, 0x7f, 0x00, /* brown */
230 1.5.4.2 skrll 0x00, 0x00, 0x7f, /* blue */
231 1.5.4.2 skrll 0x7f, 0x00, 0x7f, /* magenta */
232 1.5.4.2 skrll 0x00, 0x7f, 0x7f, /* cyan */
233 1.5.4.2 skrll 0xc7, 0xc7, 0xc7, /* white - XXX too dim? */
234 1.5.4.2 skrll
235 1.5.4.2 skrll /* Hilite colors */
236 1.5.4.2 skrll 0x7f, 0x7f, 0x7f, /* black */
237 1.5.4.2 skrll 0xff, 0x00, 0x00, /* red */
238 1.5.4.2 skrll 0x00, 0xff, 0x00, /* green */
239 1.5.4.2 skrll 0xff, 0xff, 0x00, /* brown */
240 1.5.4.2 skrll 0x00, 0x00, 0xff, /* blue */
241 1.5.4.2 skrll 0xff, 0x00, 0xff, /* magenta */
242 1.5.4.2 skrll 0x00, 0xff, 0xff, /* cyan */
243 1.5.4.2 skrll 0xff, 0xff, 0xff, /* white */
244 1.5.4.2 skrll };
245 1.5.4.2 skrll
246 1.5.4.2 skrll /**** Low-level hardware register groveling functions ****/
247 1.5.4.2 skrll static void
248 1.5.4.2 skrll rex3_write(struct newport_devconfig *dc, bus_size_t rexreg, uint32_t val)
249 1.5.4.2 skrll {
250 1.5.4.2 skrll bus_space_write_4(dc->dc_st, dc->dc_sh, NEWPORT_REX3_OFFSET + rexreg,
251 1.5.4.2 skrll val);
252 1.5.4.2 skrll }
253 1.5.4.2 skrll
254 1.5.4.2 skrll static void
255 1.5.4.2 skrll rex3_write_go(struct newport_devconfig *dc, bus_size_t rexreg, uint32_t val)
256 1.5.4.2 skrll {
257 1.5.4.2 skrll rex3_write(dc, rexreg + REX3_REG_GO, val);
258 1.5.4.2 skrll }
259 1.5.4.2 skrll
260 1.5.4.2 skrll static uint32_t
261 1.5.4.2 skrll rex3_read(struct newport_devconfig *dc, bus_size_t rexreg)
262 1.5.4.2 skrll {
263 1.5.4.2 skrll return bus_space_read_4(dc->dc_st, dc->dc_sh, NEWPORT_REX3_OFFSET +
264 1.5.4.2 skrll rexreg);
265 1.5.4.2 skrll }
266 1.5.4.2 skrll
267 1.5.4.2 skrll static void
268 1.5.4.2 skrll rex3_wait_gfifo(struct newport_devconfig *dc)
269 1.5.4.2 skrll {
270 1.5.4.2 skrll while (rex3_read(dc, REX3_REG_STATUS) & REX3_STATUS_GFXBUSY)
271 1.5.4.2 skrll ;
272 1.5.4.2 skrll }
273 1.5.4.2 skrll
274 1.5.4.2 skrll static void
275 1.5.4.2 skrll vc2_write_ireg(struct newport_devconfig *dc, uint8_t ireg, uint16_t val)
276 1.5.4.2 skrll {
277 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
278 1.5.4.2 skrll REX3_DCBMODE_DW_3 |
279 1.5.4.2 skrll REX3_DCBMODE_ENCRSINC |
280 1.5.4.2 skrll (NEWPORT_DCBADDR_VC2 << REX3_DCBMODE_DCBADDR_SHIFT) |
281 1.5.4.2 skrll (VC2_DCBCRS_INDEX << REX3_DCBMODE_DCBCRS_SHIFT) |
282 1.5.4.2 skrll REX3_DCBMODE_ENASYNCACK |
283 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
284 1.5.4.2 skrll
285 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, (ireg << 24) | (val << 8));
286 1.5.4.2 skrll }
287 1.5.4.2 skrll
288 1.5.4.2 skrll static uint16_t
289 1.5.4.2 skrll vc2_read_ireg(struct newport_devconfig *dc, uint8_t ireg)
290 1.5.4.2 skrll {
291 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
292 1.5.4.2 skrll REX3_DCBMODE_DW_1 |
293 1.5.4.2 skrll REX3_DCBMODE_ENCRSINC |
294 1.5.4.2 skrll (NEWPORT_DCBADDR_VC2 << REX3_DCBMODE_DCBADDR_SHIFT) |
295 1.5.4.2 skrll (VC2_DCBCRS_INDEX << REX3_DCBMODE_DCBCRS_SHIFT) |
296 1.5.4.2 skrll REX3_DCBMODE_ENASYNCACK |
297 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
298 1.5.4.2 skrll
299 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, ireg << 24);
300 1.5.4.2 skrll
301 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
302 1.5.4.2 skrll REX3_DCBMODE_DW_2 |
303 1.5.4.2 skrll REX3_DCBMODE_ENCRSINC |
304 1.5.4.2 skrll (NEWPORT_DCBADDR_VC2 << REX3_DCBMODE_DCBADDR_SHIFT) |
305 1.5.4.2 skrll (VC2_DCBCRS_IREG << REX3_DCBMODE_DCBCRS_SHIFT) |
306 1.5.4.2 skrll REX3_DCBMODE_ENASYNCACK |
307 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
308 1.5.4.2 skrll
309 1.5.4.2 skrll return (uint16_t)(rex3_read(dc, REX3_REG_DCBDATA0) >> 16);
310 1.5.4.2 skrll }
311 1.5.4.2 skrll
312 1.5.4.2 skrll static uint16_t
313 1.5.4.2 skrll vc2_read_ram(struct newport_devconfig *dc, uint16_t addr)
314 1.5.4.2 skrll {
315 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_RAM_ADDRESS, addr);
316 1.5.4.2 skrll
317 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
318 1.5.4.2 skrll REX3_DCBMODE_DW_2 |
319 1.5.4.2 skrll (NEWPORT_DCBADDR_VC2 << REX3_DCBMODE_DCBADDR_SHIFT) |
320 1.5.4.2 skrll (VC2_DCBCRS_RAM << REX3_DCBMODE_DCBCRS_SHIFT) |
321 1.5.4.2 skrll REX3_DCBMODE_ENASYNCACK |
322 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
323 1.5.4.2 skrll
324 1.5.4.2 skrll return (uint16_t)(rex3_read(dc, REX3_REG_DCBDATA0) >> 16);
325 1.5.4.2 skrll }
326 1.5.4.2 skrll
327 1.5.4.2 skrll static void
328 1.5.4.2 skrll vc2_write_ram(struct newport_devconfig *dc, uint16_t addr, uint16_t val)
329 1.5.4.2 skrll {
330 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_RAM_ADDRESS, addr);
331 1.5.4.2 skrll
332 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
333 1.5.4.2 skrll REX3_DCBMODE_DW_2 |
334 1.5.4.2 skrll (NEWPORT_DCBADDR_VC2 << REX3_DCBMODE_DCBADDR_SHIFT) |
335 1.5.4.2 skrll (VC2_DCBCRS_RAM << REX3_DCBMODE_DCBCRS_SHIFT) |
336 1.5.4.2 skrll REX3_DCBMODE_ENASYNCACK |
337 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
338 1.5.4.2 skrll
339 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, val << 16);
340 1.5.4.2 skrll }
341 1.5.4.2 skrll
342 1.5.4.2 skrll static u_int32_t
343 1.5.4.2 skrll xmap9_read(struct newport_devconfig *dc, int crs)
344 1.5.4.2 skrll {
345 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
346 1.5.4.2 skrll REX3_DCBMODE_DW_1 |
347 1.5.4.2 skrll (NEWPORT_DCBADDR_XMAP_0 << REX3_DCBMODE_DCBADDR_SHIFT) |
348 1.5.4.2 skrll (crs << REX3_DCBMODE_DCBCRS_SHIFT) |
349 1.5.4.2 skrll (3 << REX3_DCBMODE_CSWIDTH_SHIFT) |
350 1.5.4.2 skrll (2 << REX3_DCBMODE_CSHOLD_SHIFT) |
351 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
352 1.5.4.2 skrll return rex3_read(dc, REX3_REG_DCBDATA0);
353 1.5.4.2 skrll }
354 1.5.4.2 skrll
355 1.5.4.2 skrll static void
356 1.5.4.2 skrll xmap9_write(struct newport_devconfig *dc, int crs, uint8_t val)
357 1.5.4.2 skrll {
358 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
359 1.5.4.2 skrll REX3_DCBMODE_DW_1 |
360 1.5.4.2 skrll (NEWPORT_DCBADDR_XMAP_BOTH << REX3_DCBMODE_DCBADDR_SHIFT) |
361 1.5.4.2 skrll (crs << REX3_DCBMODE_DCBCRS_SHIFT) |
362 1.5.4.2 skrll (3 << REX3_DCBMODE_CSWIDTH_SHIFT) |
363 1.5.4.2 skrll (2 << REX3_DCBMODE_CSHOLD_SHIFT) |
364 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
365 1.5.4.2 skrll
366 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, val << 24);
367 1.5.4.2 skrll }
368 1.5.4.2 skrll
369 1.5.4.2 skrll static void
370 1.5.4.2 skrll xmap9_write_mode(struct newport_devconfig *dc, uint8_t index, uint32_t mode)
371 1.5.4.2 skrll {
372 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
373 1.5.4.2 skrll REX3_DCBMODE_DW_4 |
374 1.5.4.2 skrll (NEWPORT_DCBADDR_XMAP_BOTH << REX3_DCBMODE_DCBADDR_SHIFT) |
375 1.5.4.2 skrll (XMAP9_DCBCRS_MODE_SETUP << REX3_DCBMODE_DCBCRS_SHIFT) |
376 1.5.4.2 skrll (3 << REX3_DCBMODE_CSWIDTH_SHIFT) |
377 1.5.4.2 skrll (2 << REX3_DCBMODE_CSHOLD_SHIFT) |
378 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
379 1.5.4.2 skrll
380 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, (index << 24) | mode);
381 1.5.4.2 skrll }
382 1.5.4.2 skrll
383 1.5.4.2 skrll /**** Helper functions ****/
384 1.5.4.2 skrll static void
385 1.5.4.2 skrll newport_fill_rectangle(struct newport_devconfig *dc, int x1, int y1, int x2,
386 1.5.4.2 skrll int y2, uint8_t color)
387 1.5.4.2 skrll {
388 1.5.4.2 skrll rex3_wait_gfifo(dc);
389 1.5.4.2 skrll
390 1.5.4.2 skrll rex3_write(dc, REX3_REG_DRAWMODE0, REX3_DRAWMODE0_OPCODE_DRAW |
391 1.5.4.2 skrll REX3_DRAWMODE0_ADRMODE_BLOCK | REX3_DRAWMODE0_DOSETUP |
392 1.5.4.2 skrll REX3_DRAWMODE0_STOPONX | REX3_DRAWMODE0_STOPONY);
393 1.5.4.2 skrll rex3_write(dc, REX3_REG_WRMASK, 0xffffffff);
394 1.5.4.2 skrll rex3_write(dc, REX3_REG_COLORI, color);
395 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYSTARTI, (x1 << REX3_XYSTARTI_XSHIFT) | y1);
396 1.5.4.2 skrll
397 1.5.4.2 skrll rex3_write_go(dc, REX3_REG_XYENDI, (x2 << REX3_XYENDI_XSHIFT) | y2);
398 1.5.4.2 skrll }
399 1.5.4.2 skrll
400 1.5.4.2 skrll static void
401 1.5.4.2 skrll newport_copy_rectangle(struct newport_devconfig *dc, int x1, int y1, int x2,
402 1.5.4.2 skrll int y2, int dx, int dy)
403 1.5.4.2 skrll {
404 1.5.4.2 skrll uint32_t tmp;
405 1.5.4.2 skrll
406 1.5.4.2 skrll rex3_wait_gfifo(dc);
407 1.5.4.2 skrll
408 1.5.4.2 skrll rex3_write(dc, REX3_REG_DRAWMODE0, REX3_DRAWMODE0_OPCODE_SCR2SCR |
409 1.5.4.2 skrll REX3_DRAWMODE0_ADRMODE_BLOCK | REX3_DRAWMODE0_DOSETUP |
410 1.5.4.2 skrll REX3_DRAWMODE0_STOPONX | REX3_DRAWMODE0_STOPONY);
411 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYSTARTI, (x1 << REX3_XYSTARTI_XSHIFT) | y1);
412 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYENDI, (x2 << REX3_XYENDI_XSHIFT) | y2);
413 1.5.4.2 skrll
414 1.5.4.2 skrll tmp = (dy - y1) & 0xffff;
415 1.5.4.2 skrll tmp |= (dx - x1) << REX3_XYMOVE_XSHIFT;
416 1.5.4.2 skrll
417 1.5.4.2 skrll rex3_write_go(dc, REX3_REG_XYMOVE, tmp);
418 1.5.4.2 skrll }
419 1.5.4.2 skrll
420 1.5.4.2 skrll static void
421 1.5.4.2 skrll newport_cmap_setrgb(struct newport_devconfig *dc, int index, uint8_t r,
422 1.5.4.2 skrll uint8_t g, uint8_t b)
423 1.5.4.2 skrll {
424 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
425 1.5.4.2 skrll REX3_DCBMODE_DW_2 |
426 1.5.4.2 skrll REX3_DCBMODE_ENCRSINC |
427 1.5.4.2 skrll (NEWPORT_DCBADDR_CMAP_BOTH << REX3_DCBMODE_DCBADDR_SHIFT) |
428 1.5.4.2 skrll (CMAP_DCBCRS_ADDRESS_LOW << REX3_DCBMODE_DCBCRS_SHIFT) |
429 1.5.4.2 skrll (1 << REX3_DCBMODE_CSWIDTH_SHIFT) |
430 1.5.4.2 skrll (1 << REX3_DCBMODE_CSHOLD_SHIFT) |
431 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT) |
432 1.5.4.2 skrll REX3_DCBMODE_SWAPENDIAN);
433 1.5.4.2 skrll
434 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, index << 16);
435 1.5.4.2 skrll
436 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
437 1.5.4.2 skrll REX3_DCBMODE_DW_3 |
438 1.5.4.2 skrll (NEWPORT_DCBADDR_CMAP_BOTH << REX3_DCBMODE_DCBADDR_SHIFT) |
439 1.5.4.2 skrll (CMAP_DCBCRS_PALETTE << REX3_DCBMODE_DCBCRS_SHIFT) |
440 1.5.4.2 skrll (1 << REX3_DCBMODE_CSWIDTH_SHIFT) |
441 1.5.4.2 skrll (1 << REX3_DCBMODE_CSHOLD_SHIFT) |
442 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
443 1.5.4.2 skrll
444 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBDATA0, (r << 24) + (g << 16) + (b << 8));
445 1.5.4.2 skrll }
446 1.5.4.2 skrll
447 1.5.4.2 skrll static void
448 1.5.4.2 skrll newport_get_resolution(struct newport_devconfig *dc)
449 1.5.4.2 skrll {
450 1.5.4.2 skrll uint16_t vep,lines;
451 1.5.4.2 skrll uint16_t linep,cols;
452 1.5.4.2 skrll uint16_t data;
453 1.5.4.2 skrll
454 1.5.4.2 skrll vep = vc2_read_ireg(dc, VC2_IREG_VIDEO_ENTRY);
455 1.5.4.2 skrll
456 1.5.4.2 skrll dc->dc_xres = 0;
457 1.5.4.2 skrll dc->dc_yres = 0;
458 1.5.4.2 skrll
459 1.5.4.2 skrll for (;;) {
460 1.5.4.2 skrll /* Iterate over runs in video timing table */
461 1.5.4.2 skrll
462 1.5.4.2 skrll cols = 0;
463 1.5.4.2 skrll
464 1.5.4.2 skrll linep = vc2_read_ram(dc, vep++);
465 1.5.4.2 skrll lines = vc2_read_ram(dc, vep++);
466 1.5.4.2 skrll
467 1.5.4.2 skrll if (lines == 0)
468 1.5.4.2 skrll break;
469 1.5.4.2 skrll
470 1.5.4.2 skrll do {
471 1.5.4.2 skrll /* Iterate over state runs in line sequence table */
472 1.5.4.2 skrll
473 1.5.4.2 skrll data = vc2_read_ram(dc, linep++);
474 1.5.4.2 skrll
475 1.5.4.2 skrll if ((data & 0x0001) == 0)
476 1.5.4.2 skrll cols += (data >> 7) & 0xfe;
477 1.5.4.2 skrll
478 1.5.4.2 skrll if ((data & 0x0080) == 0)
479 1.5.4.2 skrll data = vc2_read_ram(dc, linep++);
480 1.5.4.2 skrll } while ((data & 0x8000) == 0);
481 1.5.4.2 skrll
482 1.5.4.2 skrll if (cols != 0) {
483 1.5.4.2 skrll if (cols > dc->dc_xres)
484 1.5.4.2 skrll dc->dc_xres = cols;
485 1.5.4.2 skrll
486 1.5.4.2 skrll dc->dc_yres += lines;
487 1.5.4.2 skrll }
488 1.5.4.2 skrll }
489 1.5.4.2 skrll }
490 1.5.4.2 skrll
491 1.5.4.2 skrll static void
492 1.5.4.2 skrll newport_setup_hw(struct newport_devconfig *dc)
493 1.5.4.2 skrll {
494 1.5.4.2 skrll uint16_t curp,tmp;
495 1.5.4.2 skrll int i;
496 1.5.4.2 skrll uint32_t scratch;
497 1.5.4.2 skrll
498 1.5.4.2 skrll /* Get various revisions */
499 1.5.4.2 skrll rex3_write(dc, REX3_REG_DCBMODE,
500 1.5.4.2 skrll REX3_DCBMODE_DW_1 |
501 1.5.4.2 skrll (NEWPORT_DCBADDR_CMAP_0 << REX3_DCBMODE_DCBADDR_SHIFT) |
502 1.5.4.2 skrll (CMAP_DCBCRS_REVISION << REX3_DCBMODE_DCBCRS_SHIFT) |
503 1.5.4.2 skrll (1 << REX3_DCBMODE_CSWIDTH_SHIFT) |
504 1.5.4.2 skrll (1 << REX3_DCBMODE_CSHOLD_SHIFT) |
505 1.5.4.2 skrll (1 << REX3_DCBMODE_CSSETUP_SHIFT));
506 1.5.4.2 skrll
507 1.5.4.2 skrll scratch = vc2_read_ireg(dc, VC2_IREG_CONFIG);
508 1.5.4.2 skrll dc->dc_vc2rev = (scratch & VC2_IREG_CONFIG_REVISION) >> 5;
509 1.5.4.2 skrll
510 1.5.4.2 skrll scratch = rex3_read(dc, REX3_REG_DCBDATA0);
511 1.5.4.2 skrll
512 1.5.4.2 skrll dc->dc_boardrev = (scratch >> 28) & 0x07;
513 1.5.4.2 skrll dc->dc_cmaprev = scratch & 0x07;
514 1.5.4.2 skrll dc->dc_xmaprev = xmap9_read(dc, XMAP9_DCBCRS_REVISION) & 0x07;
515 1.5.4.2 skrll dc->dc_depth = ( (dc->dc_boardrev > 1) && (scratch & 0x80)) ? 8 : 24;
516 1.5.4.2 skrll
517 1.5.4.2 skrll /* Setup cursor glyph */
518 1.5.4.2 skrll curp = vc2_read_ireg(dc, VC2_IREG_CURSOR_ENTRY);
519 1.5.4.2 skrll
520 1.5.4.2 skrll for (i=0; i<128; i++)
521 1.5.4.2 skrll vc2_write_ram(dc, curp + i, newport_cursor_data[i]);
522 1.5.4.2 skrll
523 1.5.4.2 skrll /* Setup VC2 to a known state */
524 1.5.4.2 skrll tmp = vc2_read_ireg(dc, VC2_IREG_CONTROL) & VC2_CONTROL_INTERLACE;
525 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_CONTROL, tmp |
526 1.5.4.2 skrll VC2_CONTROL_DISPLAY_ENABLE |
527 1.5.4.2 skrll VC2_CONTROL_VTIMING_ENABLE |
528 1.5.4.2 skrll VC2_CONTROL_DID_ENABLE |
529 1.5.4.2 skrll VC2_CONTROL_CURSORFUNC_ENABLE |
530 1.5.4.2 skrll VC2_CONTROL_CURSOR_ENABLE);
531 1.5.4.2 skrll
532 1.5.4.2 skrll /* Setup XMAP9s */
533 1.5.4.2 skrll xmap9_write(dc, XMAP9_DCBCRS_CONFIG,
534 1.5.4.2 skrll XMAP9_CONFIG_8BIT_SYSTEM | XMAP9_CONFIG_RGBMAP_CI);
535 1.5.4.2 skrll
536 1.5.4.2 skrll xmap9_write(dc, XMAP9_DCBCRS_CURSOR_CMAP, 0);
537 1.5.4.2 skrll
538 1.5.4.2 skrll xmap9_write_mode(dc, 0,
539 1.5.4.2 skrll XMAP9_MODE_GAMMA_BYPASS |
540 1.5.4.2 skrll XMAP9_MODE_PIXSIZE_8BPP);
541 1.5.4.2 skrll xmap9_write(dc, XMAP9_DCBCRS_MODE_SELECT, 0);
542 1.5.4.2 skrll
543 1.5.4.2 skrll /* Setup REX3 */
544 1.5.4.2 skrll rex3_write(dc, REX3_REG_DRAWMODE1,
545 1.5.4.2 skrll REX3_DRAWMODE1_PLANES_CI |
546 1.5.4.2 skrll REX3_DRAWMODE1_DD_DD8 |
547 1.5.4.2 skrll REX3_DRAWMODE1_RWPACKED |
548 1.5.4.2 skrll REX3_DRAWMODE1_HD_HD8 |
549 1.5.4.2 skrll REX3_DRAWMODE1_COMPARE_LT |
550 1.5.4.2 skrll REX3_DRAWMODE1_COMPARE_EQ |
551 1.5.4.2 skrll REX3_DRAWMODE1_COMPARE_GT |
552 1.5.4.2 skrll REX3_DRAWMODE1_LO_SRC);
553 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYWIN, (4096 << 16) | 4096);
554 1.5.4.2 skrll rex3_write(dc, REX3_REG_TOPSCAN, 0x3ff); /* XXX Why? XXX */
555 1.5.4.2 skrll
556 1.5.4.2 skrll /* Setup CMAP */
557 1.5.4.2 skrll for (i=0; i<16; i++)
558 1.5.4.2 skrll newport_cmap_setrgb(dc, i, newport_defcmap[i*3],
559 1.5.4.2 skrll newport_defcmap[i*3 + 1], newport_defcmap[i*3 + 2]);
560 1.5.4.2 skrll }
561 1.5.4.2 skrll
562 1.5.4.2 skrll /**** Attach routines ****/
563 1.5.4.2 skrll static int
564 1.5.4.2 skrll newport_match(struct device *parent, struct cfdata *self, void *aux)
565 1.5.4.2 skrll {
566 1.5.4.2 skrll struct gio_attach_args *ga = aux;
567 1.5.4.2 skrll
568 1.5.4.2 skrll /* newport doesn't decode all addresses */
569 1.5.4.2 skrll if (ga->ga_addr != 0x1f000000 && ga->ga_addr != 0x1f400000 &&
570 1.5.4.2 skrll ga->ga_addr != 0x1f800000 && ga->ga_addr != 0x1fc00000)
571 1.5.4.2 skrll return 0;
572 1.5.4.2 skrll
573 1.5.4.2 skrll /* newport doesn't respond with correct product id, empirically
574 1.5.4.2 skrll * both empty slots and newports seem to yield this result */
575 1.5.4.2 skrll if (ga->ga_product != 0x04)
576 1.5.4.2 skrll return 0;
577 1.5.4.2 skrll
578 1.5.4.2 skrll /* Don't do the destructive probe if we're already attached */
579 1.5.4.2 skrll if (newport_is_console && ga->ga_addr == newport_console_dc.dc_addr)
580 1.5.4.2 skrll return 1;
581 1.5.4.2 skrll
582 1.5.4.2 skrll /* Ugly, this probe is destructive, blame SGI... */
583 1.5.4.2 skrll /* XXX Should be bus_space_peek/bus_space_poke XXX */
584 1.5.4.2 skrll bus_space_write_4(ga->ga_iot, ga->ga_ioh,
585 1.5.4.2 skrll NEWPORT_REX3_OFFSET + REX3_REG_XSTARTI, 0x12345678);
586 1.5.4.2 skrll if (bus_space_read_4(ga->ga_iot, ga->ga_ioh,
587 1.5.4.2 skrll NEWPORT_REX3_OFFSET + REX3_REG_XSTART)
588 1.5.4.2 skrll != ((0x12345678 & 0xffff) << 11))
589 1.5.4.2 skrll return 0;
590 1.5.4.2 skrll
591 1.5.4.2 skrll return 1;
592 1.5.4.2 skrll }
593 1.5.4.2 skrll
594 1.5.4.2 skrll static void
595 1.5.4.2 skrll newport_attach_common(struct newport_devconfig *dc, struct gio_attach_args *ga)
596 1.5.4.2 skrll {
597 1.5.4.2 skrll dc->dc_addr = ga->ga_addr;
598 1.5.4.2 skrll
599 1.5.4.2 skrll dc->dc_st = ga->ga_iot;
600 1.5.4.2 skrll dc->dc_sh = ga->ga_ioh;
601 1.5.4.2 skrll
602 1.5.4.2 skrll wsfont_init();
603 1.5.4.2 skrll
604 1.5.4.2 skrll dc->dc_font = wsfont_find(NULL, 8, 16, 0, WSDISPLAY_FONTORDER_L2R,
605 1.5.4.2 skrll WSDISPLAY_FONTORDER_L2R);
606 1.5.4.2 skrll if (dc->dc_font < 0)
607 1.5.4.2 skrll panic("newport_attach_common: no suitable fonts");
608 1.5.4.2 skrll
609 1.5.4.2 skrll if (wsfont_lock(dc->dc_font, &dc->dc_fontdata))
610 1.5.4.2 skrll panic("newport_attach_common: unable to lock font data");
611 1.5.4.2 skrll
612 1.5.4.2 skrll newport_setup_hw(dc);
613 1.5.4.2 skrll
614 1.5.4.2 skrll newport_get_resolution(dc);
615 1.5.4.2 skrll
616 1.5.4.2 skrll newport_fill_rectangle(dc, 0, 0, dc->dc_xres, dc->dc_yres, 0);
617 1.5.4.2 skrll }
618 1.5.4.2 skrll
619 1.5.4.2 skrll static void
620 1.5.4.2 skrll newport_attach(struct device *parent, struct device *self, void *aux)
621 1.5.4.2 skrll {
622 1.5.4.2 skrll struct gio_attach_args *ga = aux;
623 1.5.4.2 skrll struct newport_softc *sc = (void *)self;
624 1.5.4.2 skrll struct wsemuldisplaydev_attach_args wa;
625 1.5.4.2 skrll
626 1.5.4.2 skrll if (newport_is_console && ga->ga_addr == newport_console_dc.dc_addr) {
627 1.5.4.2 skrll wa.console = 1;
628 1.5.4.2 skrll sc->sc_dc = &newport_console_dc;
629 1.5.4.2 skrll } else {
630 1.5.4.2 skrll wa.console = 0;
631 1.5.4.2 skrll sc->sc_dc = malloc(sizeof(struct newport_devconfig),
632 1.5.4.2 skrll M_DEVBUF, M_WAITOK | M_ZERO);
633 1.5.4.2 skrll if (sc->sc_dc == NULL)
634 1.5.4.2 skrll panic("newport_attach: out of memory");
635 1.5.4.2 skrll
636 1.5.4.2 skrll newport_attach_common(sc->sc_dc, ga);
637 1.5.4.2 skrll }
638 1.5.4.2 skrll
639 1.5.4.2 skrll aprint_naive(": Display adapter\n");
640 1.5.4.2 skrll
641 1.5.4.2 skrll aprint_normal(": SGI NG1 (board revision %d, cmap revision %d, xmap revision %d, vc2 revision %d), depth %d\n",
642 1.5.4.2 skrll sc->sc_dc->dc_boardrev, sc->sc_dc->dc_cmaprev,
643 1.5.4.2 skrll sc->sc_dc->dc_xmaprev, sc->sc_dc->dc_vc2rev, sc->sc_dc->dc_depth);
644 1.5.4.2 skrll
645 1.5.4.2 skrll wa.scrdata = &newport_screenlist;
646 1.5.4.2 skrll wa.accessops = &newport_accessops;
647 1.5.4.2 skrll wa.accesscookie = sc->sc_dc;
648 1.5.4.2 skrll
649 1.5.4.2 skrll config_found(&sc->sc_dev, &wa, wsemuldisplaydevprint);
650 1.5.4.2 skrll }
651 1.5.4.2 skrll
652 1.5.4.2 skrll int
653 1.5.4.2 skrll newport_cnattach(struct gio_attach_args *ga)
654 1.5.4.2 skrll {
655 1.5.4.2 skrll long defattr = NEWPORT_ATTR_ENCODE(WSCOL_WHITE, WSCOL_BLACK);
656 1.5.4.2 skrll const struct wsscreen_descr *screen;
657 1.5.4.2 skrll
658 1.5.4.2 skrll if (!newport_match(NULL, NULL, ga)) {
659 1.5.4.2 skrll return ENXIO;
660 1.5.4.2 skrll }
661 1.5.4.2 skrll
662 1.5.4.2 skrll newport_attach_common(&newport_console_dc, ga);
663 1.5.4.2 skrll
664 1.5.4.2 skrll if (newport_console_dc.dc_xres >= 1280 &&
665 1.5.4.2 skrll newport_console_dc.dc_yres >= 1024)
666 1.5.4.2 skrll screen = &newport_screen_1280x1024;
667 1.5.4.2 skrll else
668 1.5.4.2 skrll screen = &newport_screen_1024x768;
669 1.5.4.2 skrll
670 1.5.4.2 skrll wsdisplay_cnattach(screen, &newport_console_dc, 0, 0, defattr);
671 1.5.4.2 skrll
672 1.5.4.2 skrll newport_is_console = 1;
673 1.5.4.2 skrll
674 1.5.4.2 skrll return 0;
675 1.5.4.2 skrll }
676 1.5.4.2 skrll
677 1.5.4.2 skrll /**** wsdisplay textops ****/
678 1.5.4.2 skrll static void
679 1.5.4.2 skrll newport_cursor(void *c, int on, int row, int col)
680 1.5.4.2 skrll {
681 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
682 1.5.4.2 skrll uint16_t control;
683 1.5.4.2 skrll int x_offset;
684 1.5.4.2 skrll
685 1.5.4.2 skrll control = vc2_read_ireg(dc, VC2_IREG_CONTROL);
686 1.5.4.2 skrll
687 1.5.4.2 skrll if (!on) {
688 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_CONTROL,
689 1.5.4.2 skrll control & ~VC2_CONTROL_CURSOR_ENABLE);
690 1.5.4.2 skrll } else {
691 1.5.4.2 skrll /* Work around bug in some board revisions */
692 1.5.4.2 skrll if (dc->dc_boardrev < 6)
693 1.5.4.2 skrll x_offset = 21;
694 1.5.4.2 skrll else if (dc->dc_vc2rev == 0)
695 1.5.4.2 skrll x_offset = 29;
696 1.5.4.2 skrll else
697 1.5.4.2 skrll x_offset = 31;
698 1.5.4.2 skrll
699 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_CURSOR_X,
700 1.5.4.2 skrll col * dc->dc_fontdata->fontwidth + x_offset);
701 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_CURSOR_Y,
702 1.5.4.2 skrll row * dc->dc_fontdata->fontheight + 31);
703 1.5.4.2 skrll
704 1.5.4.2 skrll vc2_write_ireg(dc, VC2_IREG_CONTROL,
705 1.5.4.2 skrll control | VC2_CONTROL_CURSOR_ENABLE);
706 1.5.4.2 skrll }
707 1.5.4.2 skrll }
708 1.5.4.2 skrll
709 1.5.4.2 skrll static int
710 1.5.4.2 skrll newport_mapchar(void *c, int ch, unsigned int *cp)
711 1.5.4.2 skrll {
712 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
713 1.5.4.2 skrll
714 1.5.4.2 skrll if (dc->dc_fontdata->encoding != WSDISPLAY_FONTENC_ISO) {
715 1.5.4.2 skrll ch = wsfont_map_unichar(dc->dc_fontdata, ch);
716 1.5.4.2 skrll
717 1.5.4.2 skrll if (ch < 0)
718 1.5.4.2 skrll goto fail;
719 1.5.4.2 skrll }
720 1.5.4.2 skrll
721 1.5.4.2 skrll if (ch < dc->dc_fontdata->firstchar ||
722 1.5.4.2 skrll ch >= dc->dc_fontdata->firstchar + dc->dc_fontdata->numchars)
723 1.5.4.2 skrll goto fail;
724 1.5.4.2 skrll
725 1.5.4.2 skrll *cp = ch;
726 1.5.4.2 skrll return 5;
727 1.5.4.2 skrll
728 1.5.4.2 skrll fail:
729 1.5.4.2 skrll *cp = ' ';
730 1.5.4.2 skrll return 0;
731 1.5.4.2 skrll }
732 1.5.4.2 skrll
733 1.5.4.2 skrll static void
734 1.5.4.2 skrll newport_putchar(void *c, int row, int col, u_int ch, long attr)
735 1.5.4.2 skrll {
736 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
737 1.5.4.2 skrll struct wsdisplay_font *font = dc->dc_fontdata;
738 1.5.4.2 skrll uint8_t *bitmap = (u_int8_t *)font->data + (ch - font->firstchar) *
739 1.5.4.2 skrll font->fontheight * font->stride;
740 1.5.4.2 skrll uint32_t pattern;
741 1.5.4.2 skrll int i;
742 1.5.4.2 skrll int x = col * font->fontwidth;
743 1.5.4.2 skrll int y = row * font->fontheight;
744 1.5.4.2 skrll
745 1.5.4.2 skrll rex3_wait_gfifo(dc);
746 1.5.4.2 skrll
747 1.5.4.2 skrll rex3_write(dc, REX3_REG_DRAWMODE0, REX3_DRAWMODE0_OPCODE_DRAW |
748 1.5.4.2 skrll REX3_DRAWMODE0_ADRMODE_BLOCK | REX3_DRAWMODE0_STOPONX |
749 1.5.4.2 skrll REX3_DRAWMODE0_ENZPATTERN | REX3_DRAWMODE0_ZPOPAQUE);
750 1.5.4.2 skrll
751 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYSTARTI, (x << REX3_XYSTARTI_XSHIFT) | y);
752 1.5.4.2 skrll rex3_write(dc, REX3_REG_XYENDI,
753 1.5.4.2 skrll (x + font->fontwidth - 1) << REX3_XYENDI_XSHIFT);
754 1.5.4.2 skrll
755 1.5.4.2 skrll rex3_write(dc, REX3_REG_COLORI, NEWPORT_ATTR_FG(attr));
756 1.5.4.2 skrll rex3_write(dc, REX3_REG_COLORBACK, NEWPORT_ATTR_BG(attr));
757 1.5.4.2 skrll
758 1.5.4.2 skrll rex3_write(dc, REX3_REG_WRMASK, 0xffffffff);
759 1.5.4.2 skrll
760 1.5.4.2 skrll for (i=0; i<font->fontheight; i++) {
761 1.5.4.2 skrll /* XXX Works only with font->fontwidth == 8 XXX */
762 1.5.4.2 skrll pattern = *bitmap << 24;
763 1.5.4.2 skrll
764 1.5.4.2 skrll rex3_write_go(dc, REX3_REG_ZPATTERN, pattern);
765 1.5.4.2 skrll
766 1.5.4.2 skrll bitmap += font->stride;
767 1.5.4.2 skrll }
768 1.5.4.2 skrll }
769 1.5.4.2 skrll
770 1.5.4.2 skrll static void
771 1.5.4.2 skrll newport_copycols(void *c, int row, int srccol, int dstcol, int ncols)
772 1.5.4.2 skrll {
773 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
774 1.5.4.2 skrll struct wsdisplay_font *font = dc->dc_fontdata;
775 1.5.4.2 skrll
776 1.5.4.2 skrll newport_copy_rectangle(dc,
777 1.5.4.2 skrll srccol * font->fontwidth, /* x1 */
778 1.5.4.2 skrll row * font->fontheight, /* y1 */
779 1.5.4.2 skrll (srccol + ncols + 1) * font->fontwidth - 1, /* x2 */
780 1.5.4.2 skrll (row + 1) * font->fontheight - 1, /* y2 */
781 1.5.4.2 skrll dstcol * font->fontheight, /* dx */
782 1.5.4.2 skrll row * font->fontheight); /* dy */
783 1.5.4.2 skrll }
784 1.5.4.2 skrll
785 1.5.4.2 skrll static void
786 1.5.4.2 skrll newport_erasecols(void *c, int row, int startcol, int ncols,
787 1.5.4.2 skrll long attr)
788 1.5.4.2 skrll {
789 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
790 1.5.4.2 skrll struct wsdisplay_font *font = dc->dc_fontdata;
791 1.5.4.2 skrll
792 1.5.4.2 skrll newport_fill_rectangle(dc,
793 1.5.4.2 skrll startcol * font->fontwidth, /* x1 */
794 1.5.4.2 skrll row * font->fontheight, /* y1 */
795 1.5.4.2 skrll (startcol + ncols + 1) * font->fontwidth - 1, /* x2 */
796 1.5.4.2 skrll (row + 1) * font->fontheight - 1, /* y2 */
797 1.5.4.2 skrll NEWPORT_ATTR_BG(attr));
798 1.5.4.2 skrll }
799 1.5.4.2 skrll
800 1.5.4.2 skrll static void
801 1.5.4.2 skrll newport_copyrows(void *c, int srcrow, int dstrow, int nrows)
802 1.5.4.2 skrll {
803 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
804 1.5.4.2 skrll struct wsdisplay_font *font = dc->dc_fontdata;
805 1.5.4.2 skrll
806 1.5.4.2 skrll newport_copy_rectangle(dc,
807 1.5.4.2 skrll 0, /* x1 */
808 1.5.4.2 skrll srcrow * font->fontheight, /* y1 */
809 1.5.4.2 skrll dc->dc_xres, /* x2 */
810 1.5.4.2 skrll (srcrow + nrows + 1) * font->fontheight - 1, /* y2 */
811 1.5.4.2 skrll 0, /* dx */
812 1.5.4.2 skrll dstrow * font->fontheight); /* dy */
813 1.5.4.2 skrll }
814 1.5.4.2 skrll
815 1.5.4.2 skrll static void
816 1.5.4.2 skrll newport_eraserows(void *c, int startrow, int nrows, long attr)
817 1.5.4.2 skrll {
818 1.5.4.2 skrll struct newport_devconfig *dc = (void *)c;
819 1.5.4.2 skrll struct wsdisplay_font *font = dc->dc_fontdata;
820 1.5.4.2 skrll
821 1.5.4.2 skrll newport_fill_rectangle(dc,
822 1.5.4.2 skrll 0, /* x1 */
823 1.5.4.2 skrll startrow * font->fontheight, /* y1 */
824 1.5.4.2 skrll dc->dc_xres, /* x2 */
825 1.5.4.2 skrll (startrow + nrows + 1) * font->fontheight - 1, /* y2 */
826 1.5.4.2 skrll NEWPORT_ATTR_BG(attr));
827 1.5.4.2 skrll }
828 1.5.4.2 skrll
829 1.5.4.2 skrll static int
830 1.5.4.2 skrll newport_allocattr(void *c, int fg, int bg, int flags, long *attr)
831 1.5.4.2 skrll {
832 1.5.4.2 skrll if (flags & WSATTR_BLINK)
833 1.5.4.2 skrll return EINVAL;
834 1.5.4.2 skrll
835 1.5.4.2 skrll if ((flags & WSATTR_WSCOLORS) == 0) {
836 1.5.4.2 skrll fg = WSCOL_WHITE;
837 1.5.4.2 skrll bg = WSCOL_BLACK;
838 1.5.4.2 skrll }
839 1.5.4.2 skrll
840 1.5.4.2 skrll if (flags & WSATTR_HILIT)
841 1.5.4.2 skrll fg += 8;
842 1.5.4.2 skrll
843 1.5.4.2 skrll if (flags & WSATTR_REVERSE) {
844 1.5.4.2 skrll int tmp = fg;
845 1.5.4.2 skrll fg = bg;
846 1.5.4.2 skrll bg = tmp;
847 1.5.4.2 skrll }
848 1.5.4.2 skrll
849 1.5.4.2 skrll *attr = NEWPORT_ATTR_ENCODE(fg, bg);
850 1.5.4.2 skrll
851 1.5.4.2 skrll return 0;
852 1.5.4.2 skrll }
853 1.5.4.2 skrll
854 1.5.4.2 skrll /**** wsdisplay accessops ****/
855 1.5.4.2 skrll
856 1.5.4.2 skrll static int
857 1.5.4.2 skrll newport_ioctl(void *c, u_long cmd, caddr_t data, int flag, struct proc *p)
858 1.5.4.2 skrll {
859 1.5.4.2 skrll struct newport_softc *sc = c;
860 1.5.4.2 skrll
861 1.5.4.2 skrll #define FBINFO (*(struct wsdisplay_fbinfo*)data)
862 1.5.4.2 skrll
863 1.5.4.2 skrll switch (cmd) {
864 1.5.4.2 skrll case WSDISPLAYIO_GINFO:
865 1.5.4.2 skrll FBINFO.width = sc->sc_dc->dc_xres;
866 1.5.4.2 skrll FBINFO.height = sc->sc_dc->dc_yres;
867 1.5.4.2 skrll FBINFO.depth = sc->sc_dc->dc_depth;
868 1.5.4.2 skrll FBINFO.cmsize = 1 << FBINFO.depth;
869 1.5.4.2 skrll return 0;
870 1.5.4.2 skrll case WSDISPLAYIO_GTYPE:
871 1.5.4.2 skrll *(u_int *)data = WSDISPLAY_TYPE_NEWPORT;
872 1.5.4.2 skrll return 0;
873 1.5.4.2 skrll }
874 1.5.4.2 skrll return EPASSTHROUGH;
875 1.5.4.2 skrll }
876 1.5.4.2 skrll
877 1.5.4.2 skrll static paddr_t
878 1.5.4.2 skrll newport_mmap(void *c, off_t offset, int prot)
879 1.5.4.2 skrll {
880 1.5.4.2 skrll struct newport_devconfig *dc = c;
881 1.5.4.2 skrll
882 1.5.4.2 skrll if ( offset >= 0xfffff)
883 1.5.4.2 skrll return -1;
884 1.5.4.2 skrll
885 1.5.4.2 skrll return mips_btop(dc->dc_addr + offset);
886 1.5.4.2 skrll }
887 1.5.4.2 skrll
888 1.5.4.2 skrll static int
889 1.5.4.2 skrll newport_alloc_screen(void *c, const struct wsscreen_descr *type, void **cookiep,
890 1.5.4.2 skrll int *cursxp, int *cursyp, long *attrp)
891 1.5.4.2 skrll {
892 1.5.4.2 skrll /* This won't get called for console screen and we don't support
893 1.5.4.2 skrll * virtual screens */
894 1.5.4.2 skrll
895 1.5.4.2 skrll return ENOMEM;
896 1.5.4.2 skrll }
897 1.5.4.2 skrll
898 1.5.4.2 skrll static void
899 1.5.4.2 skrll newport_free_screen(void *c, void *cookie)
900 1.5.4.2 skrll {
901 1.5.4.2 skrll panic("newport_free_screen");
902 1.5.4.2 skrll }
903 1.5.4.2 skrll static int
904 1.5.4.2 skrll newport_show_screen(void *c, void *cookie, int waitok,
905 1.5.4.2 skrll void (*cb)(void *, int, int), void *cbarg)
906 1.5.4.2 skrll {
907 1.5.4.2 skrll return 0;
908 1.5.4.2 skrll }
909