1 /*
2 * Copyright (c) 1988 University of Utah.
3 * Copyright (c) 1990, 1993
4 * The Regents of the University of California. All rights reserved.
5 *
6 * This code is derived from software contributed to Berkeley by
7 * the Systems Programming Group of the University of Utah Computer
8 * Science Department.
9 *
10 * %sccs.include.redist.c%
11 *
12 * from: Utah $Hdr: grf_rb.c 1.15 93/08/13$
13 *
14 * @(#)grf_rb.c 8.4 (Berkeley) 01/12/94
15 */
16
17 #include "grf.h"
18 #if NGRF > 0
19
20 /*
21 * Graphics routines for the Renaissance, HP98720 Graphics system.
22 */
23 #include <sys/param.h>
24 #include <sys/errno.h>
25
26 #include <hp/dev/grfioctl.h>
27 #include <hp/dev/grfvar.h>
28 #include <hp300/dev/grf_rbreg.h>
29
30 #include <machine/cpu.h>
31
32 /*
33 * Initialize hardware.
34 * Must point g_display at a grfinfo structure describing the hardware.
35 * Returns 0 if hardware not present, non-zero ow.
36 */
37 rb_init(gp, addr)
38 struct grf_softc *gp;
39 caddr_t addr;
40 {
41 register struct rboxfb *rbp;
42 struct grfinfo *gi = &gp->g_display;
43 int fboff;
44 extern caddr_t sctopa(), iomap();
45
46 rbp = (struct rboxfb *) addr;
47 if (ISIIOVA(addr))
48 gi->gd_regaddr = (caddr_t) IIOP(addr);
49 else
50 gi->gd_regaddr = sctopa(vatosc(addr));
51 gi->gd_regsize = 0x20000;
52 gi->gd_fbwidth = (rbp->fbwmsb << 8) | rbp->fbwlsb;
53 gi->gd_fbheight = (rbp->fbhmsb << 8) | rbp->fbhlsb;
54 gi->gd_fbsize = gi->gd_fbwidth * gi->gd_fbheight;
55 fboff = (rbp->fbomsb << 8) | rbp->fbolsb;
56 gi->gd_fbaddr = (caddr_t) (*((u_char *)addr + fboff) << 16);
57 if (gi->gd_regaddr >= (caddr_t)DIOIIBASE) {
58 /*
59 * For DIO II space the fbaddr just computed is the offset
60 * from the select code base (regaddr) of the framebuffer.
61 * Hence it is also implicitly the size of the register set.
62 */
63 gi->gd_regsize = (int) gi->gd_fbaddr;
64 gi->gd_fbaddr += (int) gi->gd_regaddr;
65 gp->g_regkva = addr;
66 gp->g_fbkva = addr + gi->gd_regsize;
67 } else {
68 /*
69 * For DIO space we need to map the seperate framebuffer.
70 */
71 gp->g_regkva = addr;
72 gp->g_fbkva = iomap(gi->gd_fbaddr, gi->gd_fbsize);
73 }
74 gi->gd_dwidth = (rbp->dwmsb << 8) | rbp->dwlsb;
75 gi->gd_dheight = (rbp->dwmsb << 8) | rbp->dwlsb;
76 gi->gd_planes = 0; /* ?? */
77 gi->gd_colors = 256;
78 return(1);
79 }
80
81 /*
82 * Change the mode of the display.
83 * Right now all we can do is grfon/grfoff.
84 * Return a UNIX error number or 0 for success.
85 */
rb_mode(gp,cmd,data)86 rb_mode(gp, cmd, data)
87 register struct grf_softc *gp;
88 int cmd;
89 caddr_t data;
90 {
91 register struct rboxfb *rbp;
92 int error = 0;
93
94 rbp = (struct rboxfb *) gp->g_regkva;
95 switch (cmd) {
96 /*
97 * The minimal register info here is from the Renaissance X driver.
98 */
99 case GM_GRFON:
100 case GM_GRFOFF:
101 break;
102
103 case GM_GRFOVON:
104 rbp->write_enable = 0;
105 rbp->opwen = 0xF;
106 rbp->drive = 0x10;
107 break;
108
109 case GM_GRFOVOFF:
110 rbp->opwen = 0;
111 rbp->write_enable = 0xffffffff;
112 rbp->drive = 0x01;
113 break;
114
115 /*
116 * Remember UVA of mapping for GCDESCRIBE.
117 * XXX this should be per-process.
118 */
119 case GM_MAP:
120 gp->g_data = data;
121 break;
122
123 case GM_UNMAP:
124 gp->g_data = 0;
125 break;
126
127 #ifdef HPUXCOMPAT
128 case GM_DESCRIBE:
129 {
130 struct grf_fbinfo *fi = (struct grf_fbinfo *)data;
131 struct grfinfo *gi = &gp->g_display;
132 int i;
133
134 /* feed it what HP-UX expects */
135 fi->id = gi->gd_id;
136 fi->mapsize = gi->gd_fbsize;
137 fi->dwidth = gi->gd_dwidth;
138 fi->dlength = gi->gd_dheight;
139 fi->width = gi->gd_fbwidth;
140 fi->length = gi->gd_fbheight;
141 fi->bpp = NBBY;
142 fi->xlen = (fi->width * fi->bpp) / NBBY;
143 fi->npl = gi->gd_planes;
144 fi->bppu = fi->npl;
145 fi->nplbytes = fi->xlen * ((fi->length * fi->bpp) / NBBY);
146 bcopy("HP98720", fi->name, 8);
147 fi->attr = 2; /* HW block mover */
148 /*
149 * If mapped, return the UVA where mapped.
150 */
151 if (gp->g_data) {
152 fi->regbase = gp->g_data;
153 fi->fbbase = fi->regbase + gp->g_display.gd_regsize;
154 } else {
155 fi->fbbase = 0;
156 fi->regbase = 0;
157 }
158 for (i = 0; i < 6; i++)
159 fi->regions[i] = 0;
160 break;
161 }
162 #endif
163
164 default:
165 error = EINVAL;
166 break;
167 }
168 return(error);
169 }
170
171 #endif
172