1/*	$NetBSD: pfour_subr.c,v 1.6 2008/04/28 20:23:58 martin Exp $ */
2
3/*-
4 * Copyright (c) 2000 The NetBSD Foundation, Inc.
5 * All rights reserved.
6 *
7 * This code is derived from software contributed to The NetBSD Foundation
8 * by Paul Kranenburg.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 *    notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 *    notice, this list of conditions and the following disclaimer in the
17 *    documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20 * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21 * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22 * PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23 * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29 * POSSIBILITY OF SUCH DAMAGE.
30 */
31
32/*
33 * Support routines for pfour framebuffers.
34 */
35
36
37#include <sys/cdefs.h>
38__KERNEL_RCSID(0, "$NetBSD: pfour_subr.c,v 1.6 2008/04/28 20:23:58 martin Exp $");
39
40#include <sys/param.h>
41#include <sys/systm.h>
42#include <sys/device.h>
43
44#include <dev/sun/pfourreg.h>
45#include <dev/sun/fbio.h>
46#include <dev/sun/fbvar.h>
47
48void
49fb_setsize_pfour(struct fbdevice *fb)
50{
51#if defined(SUN4)
52	volatile u_int32_t pfour;
53	int width, height;
54
55	/*
56	 * Some pfour framebuffers, e.g. the
57	 * cgsix, don't encode resolution the
58	 * same, so the driver handles that.
59	 * The driver can let us know that it
60	 * needs to do this by not mapping in
61	 * the pfour register by the time this
62	 * routine is called.
63	 */
64	if (fb->fb_pfour == NULL)
65		return;
66
67	pfour = *fb->fb_pfour;
68
69	/*
70	 * Use the pfour register to determine
71	 * the size.  Note that the cgsix and
72	 * cgeight don't use this size encoding.
73	 * In this case, we have to settle
74	 * for the defaults we were provided
75	 * with.
76	 */
77	if ((PFOUR_ID(pfour) == PFOUR_ID_COLOR24) ||
78	    (PFOUR_ID(pfour) == PFOUR_ID_FASTCOLOR))
79		return;
80
81	switch (PFOUR_SIZE(pfour)) {
82	case PFOUR_SIZE_1152X900:
83		width = 1152;
84		height = 900;
85		break;
86
87	case PFOUR_SIZE_1024X1024:
88		width = 1024;
89		height = 1024;
90		break;
91
92	case PFOUR_SIZE_1280X1024:
93		width = 1280;
94		height = 1024;
95		break;
96
97	case PFOUR_SIZE_1600X1280:
98		width = 1600;
99		height = 1280;
100		break;
101
102	case PFOUR_SIZE_1440X1440:
103		width = 1440;
104		height = 1440;
105		break;
106
107	case PFOUR_SIZE_640X480:
108		width = 640;
109		height = 480;
110		break;
111
112	default:
113
114		/*
115		 * Use the defaults already filled in by the generic fb code.
116		 */
117
118		return;
119	}
120
121	fb->fb_type.fb_width = width;
122	fb->fb_type.fb_height = height;
123#endif /* SUN4 */
124}
125
126
127/*
128 * Probe for a pfour framebuffer.  Return values:
129 *
130 *	PFOUR_NOTPFOUR: framebuffer is not a pfour framebuffer
131 *	otherwise returns pfour ID
132 */
133int
134fb_pfour_id(volatile void *va)
135{
136#if defined(SUN4)
137	volatile u_int32_t val, save, *pfour = va;
138
139	/* Read the pfour register. */
140	save = *pfour;
141
142	/*
143	 * Try to modify the type code.  If it changes, put the
144	 * original value back, and notify the caller that it's
145	 * not a pfour framebuffer.
146	 */
147	val = save & ~PFOUR_REG_RESET;
148	*pfour = (val ^ PFOUR_FBTYPE_MASK);
149	if ((*pfour ^ val) & PFOUR_FBTYPE_MASK) {
150		*pfour = save;
151		return (PFOUR_NOTPFOUR);
152	}
153
154	return (PFOUR_ID(val));
155#else
156	return (PFOUR_NOTPFOUR);
157#endif /* SUN4 */
158}
159
160/*
161 * Return the status of the video enable.
162 */
163int
164fb_pfour_get_video(struct fbdevice *fb)
165{
166
167	return ((*fb->fb_pfour & PFOUR_REG_VIDEO) != 0);
168}
169
170/*
171 * Enable or disable the framebuffer.
172 */
173void
174fb_pfour_set_video(struct fbdevice *fb, int enable)
175{
176	volatile u_int32_t pfour;
177
178	pfour = *fb->fb_pfour & ~(PFOUR_REG_INTCLR|PFOUR_REG_VIDEO);
179	*fb->fb_pfour = pfour | (enable ? PFOUR_REG_VIDEO : 0);
180}
181