grf_nubus.c revision 1.16 1 /* $NetBSD: grf_nubus.c,v 1.16 1997/02/20 00:23:28 scottr Exp $ */
2
3 /*
4 * Copyright (c) 1995 Allen Briggs. All rights reserved.
5 *
6 * Redistribution and use in source and binary forms, with or without
7 * modification, are permitted provided that the following conditions
8 * are met:
9 * 1. Redistributions of source code must retain the above copyright
10 * notice, this list of conditions and the following disclaimer.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * 3. All advertising materials mentioning features or use of this software
15 * must display the following acknowledgement:
16 * This product includes software developed by Allen Briggs.
17 * 4. The name of the author may not be used to endorse or promote products
18 * derived from this software without specific prior written permission.
19 *
20 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
21 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
22 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
23 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
24 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
25 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
26 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
27 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
28 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
29 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
30 */
31 /*
32 * Device-specific routines for handling Nubus-based video cards.
33 */
34
35 #include <sys/param.h>
36
37 #include <sys/device.h>
38 #include <sys/ioctl.h>
39 #include <sys/file.h>
40 #include <sys/malloc.h>
41 #include <sys/mman.h>
42 #include <sys/proc.h>
43 #include <sys/systm.h>
44
45 #include <machine/bus.h>
46 #include <machine/cpu.h>
47 #include <machine/grfioctl.h>
48 #include <machine/viareg.h>
49
50 #include "nubus.h"
51 #include "grfvar.h"
52
53 static void load_image_data __P((caddr_t data, struct image_data *image));
54 static void grfmv_intr __P((void *vsc, int slot));
55
56 static char zero = 0;
57
58 static int grfmv_mode __P((struct grf_softc *gp, int cmd, void *arg));
59 static caddr_t grfmv_phys __P((struct grf_softc *gp, vm_offset_t addr));
60 static int grfmv_match __P((struct device *, struct cfdata *, void *));
61 static void grfmv_attach __P((struct device *, struct device *, void *));
62
63 struct cfdriver macvid_cd = {
64 NULL, "macvid", DV_DULL
65 };
66
67 struct cfattach macvid_ca = {
68 sizeof(struct grfbus_softc), grfmv_match, grfmv_attach
69 };
70
71 static void
72 load_image_data(data, image)
73 caddr_t data;
74 struct image_data *image;
75 {
76 bcopy(data , &image->size, 4);
77 bcopy(data + 4, &image->offset, 4);
78 bcopy(data + 8, &image->rowbytes, 2);
79 bcopy(data + 10, &image->top, 2);
80 bcopy(data + 12, &image->left, 2);
81 bcopy(data + 14, &image->bottom, 2);
82 bcopy(data + 16, &image->right, 2);
83 bcopy(data + 18, &image->version, 2);
84 bcopy(data + 20, &image->packType, 2);
85 bcopy(data + 22, &image->packSize, 4);
86 bcopy(data + 26, &image->hRes, 4);
87 bcopy(data + 30, &image->vRes, 4);
88 bcopy(data + 34, &image->pixelType, 2);
89 bcopy(data + 36, &image->pixelSize, 2);
90 bcopy(data + 38, &image->cmpCount, 2);
91 bcopy(data + 40, &image->cmpSize, 2);
92 bcopy(data + 42, &image->planeBytes, 4);
93 }
94
95 /*ARGSUSED*/
96 static void
97 grfmv_intr(vsc, slot)
98 void *vsc;
99 int slot;
100 {
101 caddr_t slotbase;
102 struct grfbus_softc *sc;
103
104 sc = (struct grfbus_softc *) vsc;
105 slotbase = (caddr_t) sc->sc_slot.virtual_base;
106 slotbase[0xa0000] = zero;
107 }
108
109 static int
110 grfmv_match(parent, cf, aux)
111 struct device *parent;
112 struct cfdata *cf;
113 void *aux;
114 {
115 struct nubus_attach_args *na = (struct nubus_attach_args *) aux;
116
117 if (na->category != NUBUS_CATEGORY_DISPLAY)
118 return 0;
119
120 if (na->type != NUBUS_TYPE_VIDEO)
121 return 0;
122
123 if (na->drsw != NUBUS_DRSW_APPLE)
124 return 0;
125
126 /*
127 * If we've gotten this far, then we're dealing with a real-live
128 * Apple QuickDraw-compatible display card resource. Now, how to
129 * determine that this is an active resource??? Dunno. But we'll
130 * proceed like it is.
131 */
132
133 return 1;
134 }
135
136 static void
137 grfmv_attach(parent, self, aux)
138 struct device *parent, *self;
139 void *aux;
140 {
141 struct grfbus_softc *sc = (struct grfbus_softc *) self;
142 struct nubus_attach_args *na = (struct nubus_attach_args *) aux;
143 struct image_data image_store, image;
144 struct grfmode *gm;
145 char cardname[CARD_NAME_LEN];
146 nubus_dirent dirent;
147 nubus_dir dir, mode_dir;
148 int mode;
149
150 sc->card_id = na->drhw;
151
152 bcopy(na->fmt, &sc->sc_slot, sizeof(nubus_slot));
153
154 nubus_get_main_dir(&sc->sc_slot, &dir);
155
156 if (nubus_find_rsrc(&sc->sc_slot, &dir, na->rsrcid, &dirent) <= 0)
157 return;
158
159 nubus_get_dir_from_rsrc(&sc->sc_slot, &dirent, &sc->board_dir);
160
161 if (nubus_find_rsrc(&sc->sc_slot, &sc->board_dir,
162 NUBUS_RSRC_TYPE, &dirent) <= 0)
163 if ((na->rsrcid != 128) ||
164 (nubus_find_rsrc(&sc->sc_slot, &dir, 129, &dirent) <= 0))
165 return;
166
167 mode = NUBUS_RSRC_FIRSTMODE;
168 if (nubus_find_rsrc(&sc->sc_slot, &sc->board_dir, mode, &dirent) <= 0) {
169 printf("\n%s: probe failed to get board rsrc.\n",
170 sc->sc_dev.dv_xname);
171 return;
172 }
173
174 nubus_get_dir_from_rsrc(&sc->sc_slot, &dirent, &mode_dir);
175
176 if (nubus_find_rsrc(&sc->sc_slot, &mode_dir, VID_PARAMS, &dirent)
177 <= 0) {
178 printf("\n%s: probe failed to get mode dir.\n",
179 sc->sc_dev.dv_xname);
180 return;
181 }
182
183 if (nubus_get_ind_data(&sc->sc_slot, &dirent, (caddr_t) &image_store,
184 sizeof(struct image_data)) <= 0) {
185 printf("\n%s: probe failed to get indirect mode data.\n",
186 sc->sc_dev.dv_xname);
187 return;
188 }
189
190 /* Need to load display info (and driver?), etc... (?) */
191
192 load_image_data((caddr_t) &image_store, &image);
193
194 gm = &sc->curr_mode;
195 gm->mode_id = mode;
196 gm->fbbase = (caddr_t) (sc->sc_slot.virtual_base + image.offset);
197 gm->fboff = image.offset;
198 gm->rowbytes = image.rowbytes;
199 gm->width = image.right - image.left;
200 gm->height = image.bottom - image.top;
201 gm->fbsize = sc->curr_mode.height * sc->curr_mode.rowbytes;
202 gm->hres = image.hRes;
203 gm->vres = image.vRes;
204 gm->ptype = image.pixelType;
205 gm->psize = image.pixelSize;
206
207 strncpy(cardname, nubus_get_card_name(&sc->sc_slot),
208 CARD_NAME_LEN);
209 cardname[CARD_NAME_LEN-1] = '\0';
210
211 printf(": %s\n", cardname);
212
213 add_nubus_intr(sc->sc_slot.slot, grfmv_intr, sc);
214
215 /* Perform common video attachment. */
216 grf_establish(sc, &sc->sc_slot, grfmv_mode, grfmv_phys);
217 }
218
219 static int
220 grfmv_mode(gp, cmd, arg)
221 struct grf_softc *gp;
222 int cmd;
223 void *arg;
224 {
225 switch (cmd) {
226 case GM_GRFON:
227 case GM_GRFOFF:
228 return 0;
229 case GM_CURRMODE:
230 break;
231 case GM_NEWMODE:
232 break;
233 case GM_LISTMODES:
234 break;
235 }
236 return EINVAL;
237 }
238
239 static caddr_t
240 grfmv_phys(gp, addr)
241 struct grf_softc *gp;
242 vm_offset_t addr;
243 {
244 return (caddr_t) (NUBUS_SLOT_TO_PADDR(gp->sc_slot->slot) +
245 (addr - gp->sc_slot->virtual_base));
246 }
247