1 /* $NetBSD: bw2.c,v 1.33 2008/06/08 17:30:08 tsutsui Exp $ */
4 * Copyright (c) 1992, 1993
5 * The Regents of the University of California. All rights reserved.
7 * This software was developed by the Computer Systems Engineering group
8 * at Lawrence Berkeley Laboratory under DARPA contract BG 91-66 and
9 * contributed to Berkeley.
11 * All advertising materials mentioning features or use of this software
12 * must display the following acknowledgement:
13 * This product includes software developed by the University of
14 * California, Lawrence Berkeley Laboratory.
16 * Redistribution and use in source and binary forms, with or without
17 * modification, are permitted provided that the following conditions
19 * 1. Redistributions of source code must retain the above copyright
20 * notice, this list of conditions and the following disclaimer.
21 * 2. Redistributions in binary form must reproduce the above copyright
22 * notice, this list of conditions and the following disclaimer in the
23 * documentation and/or other materials provided with the distribution.
24 * 3. Neither the name of the University nor the names of its contributors
25 * may be used to endorse or promote products derived from this software
26 * without specific prior written permission.
28 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
29 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
30 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
31 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
32 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
33 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
34 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
35 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
36 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
37 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
40 * @(#)bwtwo.c 8.1 (Berkeley) 6/11/93
44 * black&white display (bw2) driver.
46 * Does not handle interrupts, even though they can occur.
49 #include <sys/cdefs.h>
50 __KERNEL_RCSID(0, "$NetBSD: bw2.c,v 1.33 2008/06/08 17:30:08 tsutsui Exp $");
52 #include <sys/param.h>
53 #include <sys/systm.h>
55 #include <sys/device.h>
56 #include <sys/ioctl.h>
57 #include <sys/malloc.h>
62 #include <uvm/uvm_extern.h>
64 #include <machine/autoconf.h>
65 #include <machine/cpu.h>
66 #include <dev/sun/fbio.h>
67 #include <machine/idprom.h>
68 #include <machine/pmap.h>
70 #include <sun3/dev/fbvar.h>
71 #include <sun3/dev/bw2reg.h>
72 #include <sun3/dev/p4reg.h>
76 /* per-display variables */
78 device_t sc_dev
; /* base device */
79 struct fbdevice sc_fb
; /* frame buffer device */
80 int sc_phys
; /* display RAM (phys addr) */
81 /* If using overlay plane of something, it is... */
82 int sc_ovtype
; /* ... this type. */
86 /* autoconfiguration driver */
87 static int bw2match(device_t
, cfdata_t
, void *);
88 static void bw2attach(device_t
, device_t
, void *);
90 CFATTACH_DECL_NEW(bwtwo
, sizeof(struct bw2_softc
),
91 bw2match
, bw2attach
, NULL
, NULL
);
93 dev_type_open(bw2open
);
94 dev_type_ioctl(bw2ioctl
);
95 dev_type_mmap(bw2mmap
);
97 const struct cdevsw bwtwo_cdevsw
= {
98 bw2open
, nullclose
, noread
, nowrite
, bw2ioctl
,
99 nostop
, notty
, nopoll
, bw2mmap
, nokqfilter
,
102 /* XXX we do not handle frame buffer interrupts */
104 static int bw2gvideo(struct fbdevice
*, void *);
105 static int bw2svideo(struct fbdevice
*, void *);
107 static struct fbdriver bw2fbdriver
= {
108 bw2open
, nullclose
, bw2mmap
, nokqfilter
,
110 bw2gvideo
, bw2svideo
,
111 fb_noioctl
, fb_noioctl
, };
114 bw2match(device_t parent
, cfdata_t cf
, void *args
)
116 struct confargs
*ca
= args
;
117 int mid
, p4id
, peekval
;
120 /* No default address support. */
121 if (ca
->ca_paddr
== -1)
125 * Slight hack here: The low four bits of the
126 * config flags, if set, restrict the match to
127 * that machine "implementation" only.
129 mid
= cf
->cf_flags
& IDM_IMPL_MASK
;
130 if (mid
!= 0 && (mid
!= (cpu_machine_id
& IDM_IMPL_MASK
)))
134 * Make sure something is there, and if so,
135 * see if it looks like a P4 register.
137 p4reg
= bus_tmapin(ca
->ca_bustype
, ca
->ca_paddr
);
138 peekval
= peek_long(p4reg
);
139 p4id
= (peekval
== -1) ? P4_NOTFOUND
: fb_pfour_id(p4reg
);
145 * The config flag 0x40 if set means we should match
146 * only on a CG? overlay plane. We can use only the
147 * CG4 and CG8, which both have a P4 register.
149 if (cf
->cf_flags
& 0x40) {
161 * OK, we are expecting a plain old BW2, and
162 * there may or may not be a P4 register.
170 aprint_debug("bwtwo at 0x%lx match p4id=0x%x fails\n",
171 ca
->ca_paddr
, p4id
& 0xFF);
180 * Attach a display. We need to notice if it is the console, too.
183 bw2attach(device_t parent
, device_t self
, void *args
)
185 struct bw2_softc
*sc
= device_private(self
);
186 struct fbdevice
*fb
= &sc
->sc_fb
;
187 struct confargs
*ca
= args
;
191 int pixeloffset
; /* offset to framebuffer */
195 fbt
= &fb
->fb_fbtype
;
196 fbt
->fb_type
= FBTYPE_SUN2BW
;
197 fbt
->fb_width
= 1152; /* default - see below */
198 fbt
->fb_height
= 900; /* default - see below */
201 fbt
->fb_size
= BW2_FBSIZE
; /* default - see below */
202 fb
->fb_driver
= &bw2fbdriver
;
204 fb
->fb_name
= device_xname(self
);
205 fb
->fb_flags
= device_cfdata(self
)->cf_flags
;
207 /* Set up default pixel offset. May be changed below. */
210 /* Does it have a P4 register? */
211 p4reg
= bus_mapin(ca
->ca_bustype
, ca
->ca_paddr
, 4);
212 p4id
= fb_pfour_id(p4reg
);
213 if (p4id
!= P4_NOTFOUND
)
214 fb
->fb_pfour
= p4reg
;
216 bus_mapout(p4reg
, 4);
224 pixeloffset
= P4_BW_OFF
;
228 aprint_error("%s: bad p4id=0x%x\n", fb
->fb_name
, p4id
);
229 /* Must be some kinda color... */
233 sc
->sc_ovtype
= p4id
;
234 pixeloffset
= P4_COLOR_OFF_OVERLAY
;
237 sc
->sc_phys
= ca
->ca_paddr
+ pixeloffset
;
240 * Determine width and height as follows:
241 * If it has a P4 register, use that;
242 * else if unit==0, use the EEPROM size,
243 * else make our best guess.
246 fb_pfour_setsize(fb
);
247 /* XXX device_unit() abuse */
248 else if (device_unit(self
) == 0)
249 fb_eeprom_setsize(fb
);
251 /* Guess based on machine ID. */
252 switch (cpu_machine_id
) {
256 * Only the model 60 can have hi-res.
257 * Look at the "resolution" jumper.
259 tmp
= bus_peek(BUS_OBMEM
, BW2_CR_PADDR
, 1);
260 if ((tmp
!= -1) && (tmp
& 0x80) == 0)
265 /* The Sun3/260 is ALWAYS high-resolution! */
268 fbt
->fb_width
= 1600;
269 fbt
->fb_height
= 1280;
270 fbt
->fb_size
= BW2_FBSIZE_HIRES
;
275 /* Leave the defaults set above. */
279 aprint_normal(" (%dx%d)\n", fbt
->fb_width
, fbt
->fb_height
);
281 /* Make sure video is on. */
285 /* Let /dev/fb know we are here. */
290 bw2open(dev_t dev
, int flags
, int mode
, struct lwp
*l
)
292 struct bw2_softc
*sc
;
293 int unit
= minor(dev
);
295 sc
= device_lookup_private(&bwtwo_cd
, unit
);
302 bw2ioctl(dev_t dev
, u_long cmd
, void *data
, int flags
, struct lwp
*l
)
304 struct bw2_softc
*sc
= device_lookup_private(&bwtwo_cd
, minor(dev
));
306 return fbioctlfb(&sc
->sc_fb
, cmd
, data
);
310 * Return the address that would map the given device at the given
311 * offset, allowing for the given protection, or return -1 for error.
314 bw2mmap(dev_t dev
, off_t off
, int prot
)
316 struct bw2_softc
*sc
= device_lookup_private(&bwtwo_cd
, minor(dev
));
317 int size
= sc
->sc_fb
.fb_fbtype
.fb_size
;
320 panic("%s: bad offset", __func__
);
322 if ((off
< 0) || (off
>= size
))
326 * I turned on PMAP_NC here to disable the cache as I was
327 * getting horribly broken behaviour without it.
329 return (sc
->sc_phys
+ off
) | PMAP_NC
;
334 bw2gvideo(struct fbdevice
*fb
, void *data
)
336 struct bw2_softc
*sc
= fb
->fb_private
;
339 *on
= sc
->sc_video_on
;
345 bw2svideo(struct fbdevice
*fb
, void *data
)
347 struct bw2_softc
*sc
= fb
->fb_private
;
350 if (sc
->sc_video_on
== *on
)
352 sc
->sc_video_on
= *on
;
355 fb_pfour_set_video(fb
, sc
->sc_video_on
);
357 enable_video(sc
->sc_video_on
);