ffb_rcache.h revision dbbd9e4b
1/*
2 * Acceleration for the Creator and Creator3D framebuffer - register caching.
3 *
4 * Copyright (C) 1999 David S. Miller (davem@redhat.com)
5 * Copyright (C) 1999 Jakub Jelinek (jakub@redhat.com)
6 *
7 * Permission is hereby granted, free of charge, to any person obtaining a copy
8 * of this software and associated documentation files (the "Software"), to deal
9 * in the Software without restriction, including without limitation the rights
10 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11 * copies of the Software, and to permit persons to whom the Software is
12 * furnished to do so, subject to the following conditions:
13 *
14 * The above copyright notice and this permission notice shall be included in
15 * all copies or substantial portions of the Software.
16 *
17 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
20 * JAKUB JELINEK OR DAVID MILLER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
22 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS
23 * IN THE SOFTWARE.
24 *
25 */
26/* $XFree86: xc/programs/Xserver/hw/xfree86/drivers/sunffb/ffb_rcache.h,v 1.1 2000/05/18 23:21:37 dawes Exp $ */
27
28#ifndef FFBRCACHE_H
29#define FFBRCACHE_H
30
31/* We only need to write the bits which actually change,
32 * writing unnessary bits causes the operation to go more
33 * slowly. -DaveM
34 *
35 * We used to have some hairy code here which tried to
36 * avoid writing attribute bits unnecessarily.  It has been
37 * removed because various two bit fields have different
38 * semantics.  For example, for some the higher bit is the
39 * edit bit, for others there are three state patterns
40 * and zero is a special "no edit" value.  Ho hum, it was
41 * a nice idea...
42 */
43#define FFB_WRITE_PPC(__fpriv, __ffb, __val, __chg_mask) \
44do {	unsigned int __oldval = (__fpriv)->ppc_cache; \
45	unsigned int __t; \
46	__t = (__oldval & (__chg_mask)) ^ (__val); \
47	if (__t) { \
48		unsigned int __newval = __oldval & ~(__chg_mask); \
49		__newval |= (__val); \
50		(__fpriv)->ppc_cache = __newval; \
51		FFBFifo((__fpriv), 1); \
52		(__ffb)->ppc = (__val); \
53	} \
54} while(0)
55
56#define FFB_WRITE_PMASK(__fpriv, __ffb, __val) \
57do {	if((__fpriv)->pmask_cache != (__val)) { \
58		(__fpriv)->pmask_cache = (__val); \
59		FFBFifo((__fpriv), 1); \
60		(__ffb)->pmask = (__val); \
61	} \
62} while(0)
63
64#define FFB_WRITE_ROP(__fpriv, __ffb, __val) \
65do {	if((__fpriv)->rop_cache != (__val)) { \
66		(__fpriv)->rop_cache = (__val); \
67		FFBFifo((__fpriv), 1); \
68		(__ffb)->rop = (__val); \
69	} \
70} while(0)
71
72#define FFB_WRITE_DRAWOP(__fpriv, __ffb, __val) \
73do {	if((__fpriv)->drawop_cache != (__val)) { \
74		(__fpriv)->drawop_cache = (__val); \
75		FFBFifo((__fpriv), 1); \
76		(__ffb)->drawop = (__val); \
77	} \
78} while(0)
79
80#define FFB_WRITE_FG(__fpriv, __ffb, __val) \
81do {	if((__fpriv)->fg_cache != (__val)) { \
82		(__fpriv)->fg_cache = (__val); \
83		FFBFifo((__fpriv), 1); \
84		(__ffb)->fg = (__val); \
85	} \
86} while(0)
87
88#define FFB_WRITE_BG(__fpriv, __ffb, __val) \
89do {	if((__fpriv)->bg_cache != (__val)) { \
90		(__fpriv)->bg_cache = (__val); \
91		FFBFifo((__fpriv), 1); \
92		(__ffb)->bg = (__val); \
93	} \
94} while(0)
95
96#define FFB_WRITE_FONTW(__fpriv, __ffb, __val) \
97do {	if((__fpriv)->fontw_cache != (__val)) { \
98		(__fpriv)->fontw_cache = (__val); \
99		FFBFifo((__fpriv), 1); \
100		(__ffb)->fontw = (__val); \
101	} \
102} while(0)
103
104#define FFB_WRITE_FONTINC(__fpriv, __ffb, __val) \
105do {	if((__fpriv)->fontinc_cache != (__val)) { \
106		(__fpriv)->fontinc_cache = (__val); \
107		FFBFifo((__fpriv), 1); \
108		(__ffb)->fontinc = (__val); \
109	} \
110} while(0)
111
112#define FFB_WRITE_FBC(__fpriv, __ffb, __val) \
113do {	if((__fpriv)->fbc_cache != (__val)) { \
114		(__fpriv)->fbc_cache = (__val); \
115		FFBFifo((__fpriv), 1); \
116		(__ffb)->fbc = (__val); \
117	} \
118} while(0)
119
120#define FFB_WRITE_WID(__fpriv, __ffb, __val) \
121do {	if((__fpriv)->wid_cache != (__val)) { \
122		(__fpriv)->wid_cache = (__val); \
123		FFBFifo((__fpriv), 1); \
124		(__ffb)->wid = (__val); \
125	} \
126} while(0)
127
128extern void __FFB_Attr_Raw(FFBPtr pFfb,
129			   unsigned int ppc,
130			   unsigned int ppc_mask,
131			   unsigned int pmask,
132			   unsigned int rop,
133			   int drawop, int fg,
134			   unsigned int fbc,
135			   unsigned int wid);
136
137#define FFB_ATTR_RAW(__fpriv, __ppc, __ppc_mask, __pmask, __rop, __drawop, __fg, __fbc, __wid) \
138	if((((__fpriv)->ppc_cache & (__ppc_mask)) != (__ppc))			|| \
139	   ((__fpriv)->pmask_cache != (__pmask))				|| \
140	   ((__fpriv)->rop_cache != (__rop))					|| \
141	   (((__drawop) != -1) && ((__fpriv)->drawop_cache != (__drawop)))	|| \
142	   ((__fpriv)->fg_cache != (__fg))					|| \
143	   ((__fpriv)->fbc_cache != (__fbc))					|| \
144	   ((__fpriv)->wid_cache != (__wid))) \
145		__FFB_Attr_Raw((__fpriv), (__ppc), (__ppc_mask), (__pmask), \
146			       (__rop), (__drawop), (__fg), (__fbc), (__wid))
147
148#define FFB_PPC_GCMASK	(FFB_PPC_APE_MASK | FFB_PPC_CS_MASK)
149
150#define FFB_PPC_WINMASK	(FFB_PPC_APE_MASK | FFB_PPC_CS_MASK | FFB_PPC_XS_MASK)
151
152/* We have to be careful when copying windows around.  For that
153 * case we will use either VIS copies or hw accelerated VSCROLL.
154 * All of the planes needs to be copied in the framebuffer from
155 * src to dst in order to handle child windows using different WIDs
156 * than the parent window being copied.
157 */
158
159/* Setup to access the smart frame buffer (SFB) directly where the
160 * pixel color comes from the cpu on writes.
161 */
162#define FFB_PPC_WINCOPY		(FFB_PPC_APE_DISABLE | FFB_PPC_XS_VAR | FFB_PPC_CS_VAR)
163#define FFB_PPC_WINCOPY_MASK	(FFB_PPC_APE_MASK | FFB_PPC_XS_MASK | FFB_PPC_CS_MASK)
164#define FFB_FBC_WINCOPY		(FFB_FBC_WB_A | FFB_FBC_WM_COMBINED | FFB_FBC_WE_FORCEON | \
165				 FFB_FBC_RB_A | FFB_FBC_SB_BOTH | FFB_FBC_XE_ON | \
166				 FFB_FBC_ZE_OFF | FFB_FBC_YE_OFF | FFB_FBC_RGBE_ON)
167
168#define FFB_ATTR_SFB_VAR_WINCOPY(__fpriv) \
169do {	unsigned int __ppc = FFB_PPC_WINCOPY; \
170	unsigned int __ppc_mask = FFB_PPC_WINCOPY_MASK; \
171	unsigned int __rop = FFB_ROP_NEW|(FFB_ROP_NEW<<8); \
172	unsigned int __fbc = FFB_FBC_WINCOPY; \
173	if((__fpriv)->has_double_buffer) { \
174		__fbc &= ~FFB_FBC_WB_MASK; \
175		__fbc |= FFB_FBC_WB_AB; \
176	} \
177	if (((__fpriv)->ppc_cache & __ppc_mask) != __ppc || \
178	    (__fpriv)->fbc_cache != __fbc || \
179	    (__fpriv)->rop_cache != __rop || \
180	    (__fpriv)->pmask_cache != 0xffffffff) { \
181		ffb_fbcPtr __ffb = (__fpriv)->regs; \
182		(__fpriv)->ppc_cache &= ~__ppc_mask; \
183		(__fpriv)->ppc_cache |= __ppc; \
184		(__fpriv)->fbc_cache = __fbc; \
185		(__fpriv)->rop_cache = __rop; \
186		(__fpriv)->pmask_cache = 0xffffffff; \
187		(__fpriv)->rp_active = 1; \
188		FFBFifo(__fpriv, 4); \
189		(__ffb)->ppc = __ppc; \
190		(__ffb)->fbc = __fbc; \
191		(__ffb)->rop = __rop; \
192		(__ffb)->pmask = 0xffffffff; \
193		(__fpriv)->rp_active = 1; \
194	} \
195} while(0)
196
197extern void __FFB_Attr_SFB_VAR(FFBPtr pFfb, unsigned int ppc, unsigned int ppc_mask, unsigned int fbc,
198			       unsigned int wid, unsigned int rop, unsigned int pmask);
199
200#define FFB_ATTR_SFB_VAR_WIN(__fpriv, __pmask, __alu, __pwin) \
201do {	unsigned int __ppc = FFB_PPC_APE_DISABLE | FFB_PPC_CS_VAR | FFB_PPC_XS_WID; \
202	unsigned int __ppc_mask = FFB_PPC_APE_MASK | FFB_PPC_CS_MASK | FFB_PPC_XS_MASK; \
203	unsigned int __rop = (FFB_ROP_EDIT_BIT | (__alu))|(FFB_ROP_NEW<<8); \
204	unsigned int __fbc = FFB_FBC_WIN(__pwin); \
205	if((__fpriv)->has_double_buffer) { \
206		__fbc &= ~FFB_FBC_WB_MASK; \
207		__fbc |= FFB_FBC_WB_AB; \
208	} \
209	if(((__fpriv)->ppc_cache & __ppc_mask) != __ppc || \
210	   (__fpriv)->fbc_cache != __fbc || \
211	   (__fpriv)->wid_cache != FFB_WID_WIN(__pwin) || \
212	   (__fpriv)->rop_cache != __rop || \
213	   (__fpriv)->pmask_cache != (__pmask)) \
214		__FFB_Attr_SFB_VAR(__fpriv, __ppc, __ppc_mask, __fbc, \
215				   FFB_WID_WIN(__pwin), __rop, (__pmask)); \
216} while(0)
217
218/* VSCROLL Attributes:
219 *
220 * PPC) VCE_DISABLE must be set, all other attributes are effectively
221 *      ignored since this drawop just copies pixels within the ram
222 *      chips and bypasses the pixel processor entirely.  So you
223 *	end up with a PPC color source behavior of {ZS,YS,XS,CS}_VAR.
224 * FBC) all options are allowed, but the SRC/DST buffers are determined
225 *      solely by the WB_* setting, that is, the RB_* setting is effectively
226 *      ignored since the pixels are copied directly through the write buffer
227 * ROP) must be FFB_ROP_OLD (even for the X plane!)
228 * PMASK) all options allowed
229 */
230#define FFB_ATTR_VSCROLL_WINCOPY(__fpriv) \
231do {	unsigned int __rop = (FFB_ROP_OLD | (FFB_ROP_OLD << 8)); \
232	unsigned int __fbc = FFB_FBC_WINCOPY; \
233	if((__fpriv)->has_double_buffer) { \
234		__fbc &= ~FFB_FBC_WB_MASK; \
235		__fbc |= FFB_FBC_WB_AB; \
236	} \
237	if((__fpriv)->fbc_cache != __fbc || \
238	   (__fpriv)->rop_cache != __rop || \
239	   (__fpriv)->pmask_cache != 0xffffffff || \
240	   (__fpriv)->drawop_cache != FFB_DRAWOP_VSCROLL) { \
241		ffb_fbcPtr __ffb = (__fpriv)->regs; \
242		(__fpriv)->fbc_cache = __fbc; \
243		(__fpriv)->rop_cache = __rop; \
244		(__fpriv)->pmask_cache = 0xffffffff; \
245		(__fpriv)->drawop_cache = FFB_DRAWOP_VSCROLL; \
246		(__fpriv)->rp_active = 1; \
247		FFBFifo(__fpriv, 4); \
248		(__ffb)->fbc = __fbc; \
249		(__ffb)->rop = __rop; \
250		(__ffb)->pmask = 0xffffffff; \
251		(__ffb)->drawop = FFB_DRAWOP_VSCROLL; \
252		(__fpriv)->rp_active = 1; \
253	} \
254} while(0)
255
256#define FFB_ATTR_VSCROLL_WIN(__fpriv, __pmask, __pwin) \
257do {	unsigned int __rop = (FFB_ROP_OLD | (FFB_ROP_OLD << 8)); \
258	unsigned int __fbc = FFB_FBC_WIN(__pwin); \
259	if((__fpriv)->has_double_buffer) { \
260		__fbc &= ~FFB_FBC_WB_MASK; \
261		__fbc |= FFB_FBC_WB_AB; \
262	} \
263	if((__fpriv)->fbc_cache != __fbc || \
264	   (__fpriv)->rop_cache != __rop || \
265	   (__fpriv)->pmask_cache != (__pmask) || \
266	   (__fpriv)->drawop_cache != FFB_DRAWOP_VSCROLL) { \
267		ffb_fbcPtr __ffb = (__fpriv)->regs; \
268		(__fpriv)->fbc_cache = __fbc; \
269		(__fpriv)->rop_cache = __rop; \
270		(__fpriv)->pmask_cache = (__pmask); \
271		(__fpriv)->drawop_cache = FFB_DRAWOP_VSCROLL; \
272		(__fpriv)->rp_active = 1; \
273		FFBFifo(__fpriv, 4); \
274		(__ffb)->fbc = __fbc; \
275		(__ffb)->rop = __rop; \
276		(__ffb)->pmask = (__pmask); \
277		(__ffb)->drawop = FFB_DRAWOP_VSCROLL; \
278	} \
279} while(0)
280
281#endif /* FFBRCACHE_H */
282