VirtualBox

source: vbox/trunk/src/VBox/Additions/x11/x11include/7.0/xorg/cfbmskbits.h@ 17240

Last change on this file since 17240 was 17236, checked in by vboxsync, 16 years ago

Additions/x11/x11include: blast! Reverted r43555 and r43556

  • Property svn:eol-style set to native
File size: 27.2 KB
Line 
1/* $XFree86: xc/programs/Xserver/cfb/cfbmskbits.h,v 3.13tsi Exp $ */
2/************************************************************
3Copyright 1987 by Sun Microsystems, Inc. Mountain View, CA.
4
5 All Rights Reserved
6
7Permission to use, copy, modify, and distribute this
8software and its documentation for any purpose and without
9fee is hereby granted, provided that the above copyright no-
10tice appear in all copies and that both that copyright no-
11tice and this permission notice appear in supporting docu-
12mentation, and that the names of Sun or The Open Group
13not be used in advertising or publicity pertaining to
14distribution of the software without specific prior
15written permission. Sun and The Open Group make no
16representations about the suitability of this software for
17any purpose. It is provided "as is" without any express or
18implied warranty.
19
20SUN DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
21INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
22NESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SUN BE LI-
23ABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
24ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
25PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
26OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH
27THE USE OR PERFORMANCE OF THIS SOFTWARE.
28
29********************************************************/
30
31/* $Xorg: cfbmskbits.h,v 1.3 2000/08/17 19:48:14 cpqbld Exp $ */
32/* Optimizations for PSZ == 32 added by Kyle Marvin ([email protected]) */
33
34#include <X11/X.h>
35#include <X11/Xmd.h>
36#include "servermd.h"
37#if defined(XFREE86) || ( defined(__OpenBSD__) && defined(__alpha__) ) \
38 || (defined(__bsdi__))
39#include "xf86_ansic.h"
40#include "compiler.h"
41#endif
42
43/*
44 * ==========================================================================
45 * Converted from mfb to support memory-mapped color framebuffer by smarks@sun,
46 * April-May 1987.
47 *
48 * The way I did the conversion was to consider each longword as an
49 * array of four bytes instead of an array of 32 one-bit pixels. So
50 * getbits() and putbits() retain much the same calling sequence, but
51 * they move bytes around instead of bits. Of course, this entails the
52 * removal of all of the one-bit-pixel dependencies from the other
53 * files, but the major bit-hacking stuff should be covered here.
54 *
55 * I've created some new macros that make it easier to understand what's
56 * going on in the pixel calculations, and that make it easier to change the
57 * pixel size.
58 *
59 * name explanation
60 * ---- -----------
61 * PSZ pixel size (in bits)
62 * PGSZ pixel group size (in bits)
63 * PGSZB pixel group size (in bytes)
64 * PGSZBMSK mask with lowest PGSZB bits set to 1
65 * PPW pixels per word (pixels per pixel group)
66 * PPWMSK mask with lowest PPW bits set to 1
67 * PLST index of last pixel in a word (should be PPW-1)
68 * PIM pixel index mask (index within a pixel group)
69 * PWSH pixel-to-word shift (should be log2(PPW))
70 * PMSK mask with lowest PSZ bits set to 1
71 *
72 *
73 * Here are some sample values. In the notation cfbA,B: A is PSZ, and
74 * B is PGSZB. All the other values are derived from these
75 * two. This table does not show all combinations!
76 *
77 * name cfb8,4 cfb24,4 cfb32,4 cfb8,8 cfb24,8 cfb32,8
78 * ---- ------ ------- ------ ------ ------ -------
79 * PSZ 8 24 32 8 24 32
80 * PGSZ 32 32 32 64 64 64
81 * PGSZB 4 4 4 8 8 8
82 * PGSZBMSK 0xF 0xF? 0xF 0xFF 0xFF 0xFF
83 * PPW 4 1 1 8 2 2
84 * PPWMSK 0xF 0x1 0x1 0xFF 0x3? 0x3
85 * PLST 3 0 0 7 1 1
86 * PIM 0x3 0x0 0x0 0x7 0x1? 0x1
87 * PWSH 2 0 0 3 1 1
88 * PMSK 0xFF 0xFFFFFF 0xFFFFFFFF 0xFF 0xFFFFFF 0xFFFFFFFF
89 *
90 *
91 * I have also added a new macro, PFILL, that takes one pixel and
92 * replicates it throughout a word. This macro definition is dependent
93 * upon pixel and word size; it doesn't use macros like PPW and so
94 * forth. Examples: for monochrome, PFILL(1) => 0xffffffff, PFILL(0) =>
95 * 0x00000000. For 8-bit color, PFILL(0x5d) => 0x5d5d5d5d. This macro
96 * is used primarily for replicating a plane mask into a word.
97 *
98 * Color framebuffers operations also support the notion of a plane
99 * mask. This mask determines which planes of the framebuffer can be
100 * altered; the others are left unchanged. I have added another
101 * parameter to the putbits and putbitsrop macros that is the plane
102 * mask.
103 * ==========================================================================
104 *
105 * Keith Packard ([email protected])
106 * 64bit code is no longer supported; it requires DIX support
107 * for repadding images which significantly impacts performance
108 */
109
110/*
111 * PSZ needs to be defined before we get here. Usually it comes from a
112 * -DPSZ=foo on the compilation command line.
113 */
114
115#ifndef PSZ
116#define PSZ 8
117#endif
118
119/*
120 * PixelGroup is the data type used to operate on groups of pixels.
121 * We typedef it here to CARD32 with the assumption that you
122 * want to manipulate 32 bits worth of pixels at a time as you can. If CARD32
123 * is not appropriate for your server, define it to something else
124 * before including this file. In this case you will also have to define
125 * PGSZB to the size in bytes of PixelGroup.
126 */
127#ifndef PixelGroup
128#define PixelGroup CARD32
129#define PGSZB 4
130#endif /* PixelGroup */
131
132#ifndef CfbBits
133#define CfbBits CARD32
134#endif
135
136#define PGSZ (PGSZB << 3)
137#define PPW (PGSZ/PSZ)
138#define PLST (PPW-1)
139#define PIM PLST
140#define PMSK (((PixelGroup)1 << PSZ) - 1)
141#define PPWMSK (((PixelGroup)1 << PPW) - 1) /* instead of BITMSK */
142#define PGSZBMSK (((PixelGroup)1 << PGSZB) - 1)
143
144/* set PWSH = log2(PPW) using brute force */
145
146#if PPW == 1
147#define PWSH 0
148#else
149#if PPW == 2
150#define PWSH 1
151#else
152#if PPW == 4
153#define PWSH 2
154#else
155#if PPW == 8
156#define PWSH 3
157#else
158#if PPW == 16
159#define PWSH 4
160#endif /* PPW == 16 */
161#endif /* PPW == 8 */
162#endif /* PPW == 4 */
163#endif /* PPW == 2 */
164#endif /* PPW == 1 */
165
166/* Defining PIXEL_ADDR means that individual pixels are addressable by this
167 * machine (as type PixelType). A possible CFB architecture which supported
168 * 8-bits-per-pixel on a non byte-addressable machine would not have this
169 * defined.
170 *
171 * Defining FOUR_BIT_CODE means that cfb knows how to stipple on this machine;
172 * eventually, stippling code for 16 and 32 bit devices should be written
173 * which would allow them to also use FOUR_BIT_CODE. There isn't that
174 * much to do in those cases, but it would make them quite a bit faster.
175 */
176
177#if PSZ == 8
178#define PIXEL_ADDR
179typedef CARD8 PixelType;
180#define FOUR_BIT_CODE
181#endif
182
183#if PSZ == 16
184#define PIXEL_ADDR
185typedef CARD16 PixelType;
186#endif
187
188#if PSZ == 24
189#undef PMSK
190#define PMSK 0xFFFFFF
191/*#undef PIM
192#define PIM 3*/
193#define PIXEL_ADDR
194typedef CARD32 PixelType;
195#endif
196
197#if PSZ == 32
198#undef PMSK
199#define PMSK 0xFFFFFFFF
200#define PIXEL_ADDR
201typedef CARD32 PixelType;
202#endif
203
204
205/* the following notes use the following conventions:
206SCREEN LEFT SCREEN RIGHT
207in this file and maskbits.c, left and right refer to screen coordinates,
208NOT bit numbering in registers.
209
210cfbstarttab[n]
211 pixels[0,n-1] = 0's pixels[n,PPW-1] = 1's
212cfbendtab[n] =
213 pixels[0,n-1] = 1's pixels[n,PPW-1] = 0's
214
215cfbstartpartial[], cfbendpartial[]
216 these are used as accelerators for doing putbits and masking out
217bits that are all contained between longword boudaries. the extra
218256 bytes of data seems a small price to pay -- code is smaller,
219and narrow things (e.g. window borders) go faster.
220
221the names may seem misleading; they are derived not from which end
222of the word the bits are turned on, but at which end of a scanline
223the table tends to be used.
224
225look at the tables and macros to understand boundary conditions.
226(careful readers will note that starttab[n] = ~endtab[n] for n != 0)
227
228-----------------------------------------------------------------------
229these two macros depend on the screen's bit ordering.
230in both of them x is a screen position. they are used to
231combine bits collected from multiple longwords into a
232single destination longword, and to unpack a single
233source longword into multiple destinations.
234
235SCRLEFT(dst, x)
236 takes dst[x, PPW] and moves them to dst[0, PPW-x]
237 the contents of the rest of dst are 0 ONLY IF
238 dst is UNSIGNED.
239 is cast as an unsigned.
240 this is a right shift on the VAX, left shift on
241 Sun and pc-rt.
242
243SCRRIGHT(dst, x)
244 takes dst[0,x] and moves them to dst[PPW-x, PPW]
245 the contents of the rest of dst are 0 ONLY IF
246 dst is UNSIGNED.
247 this is a left shift on the VAX, right shift on
248 Sun and pc-rt.
249
250
251the remaining macros are cpu-independent; all bit order dependencies
252are built into the tables and the two macros above.
253
254maskbits(x, w, startmask, endmask, nlw)
255 for a span of width w starting at position x, returns
256a mask for ragged pixels at start, mask for ragged pixels at end,
257and the number of whole longwords between the ends.
258
259maskpartialbits(x, w, mask)
260 works like maskbits(), except all the pixels are in the
261 same longword (i.e. (x&0xPIM + w) <= PPW)
262
263mask32bits(x, w, startmask, endmask, nlw)
264 as maskbits, but does not calculate nlw. it is used by
265 cfbGlyphBlt to put down glyphs <= PPW bits wide.
266
267getbits(psrc, x, w, dst)
268 starting at position x in psrc (x < PPW), collect w
269 pixels and put them in the screen left portion of dst.
270 psrc is a longword pointer. this may span longword boundaries.
271 it special-cases fetching all w bits from one longword.
272
273 +--------+--------+ +--------+
274 | | m |n| | ==> | m |n| |
275 +--------+--------+ +--------+
276 x x+w 0 w
277 psrc psrc+1 dst
278 m = PPW - x
279 n = w - m
280
281 implementation:
282 get m pixels, move to screen-left of dst, zeroing rest of dst;
283 get n pixels from next word, move screen-right by m, zeroing
284 lower m pixels of word.
285 OR the two things together.
286
287putbits(src, x, w, pdst, planemask)
288 starting at position x in pdst, put down the screen-leftmost
289 w bits of src. pdst is a longword pointer. this may
290 span longword boundaries.
291 it special-cases putting all w bits into the same longword.
292
293 +--------+ +--------+--------+
294 | m |n| | ==> | | m |n| |
295 +--------+ +--------+--------+
296 0 w x x+w
297 dst pdst pdst+1
298 m = PPW - x
299 n = w - m
300
301 implementation:
302 get m pixels, shift screen-right by x, zero screen-leftmost x
303 pixels; zero rightmost m bits of *pdst and OR in stuff
304 from before the semicolon.
305 shift src screen-left by m, zero bits n-32;
306 zero leftmost n pixels of *(pdst+1) and OR in the
307 stuff from before the semicolon.
308
309putbitsrop(src, x, w, pdst, planemask, ROP)
310 like putbits but calls DoRop with the rasterop ROP (see cfb.h for
311 DoRop)
312
313getleftbits(psrc, w, dst)
314 get the leftmost w (w<=PPW) bits from *psrc and put them
315 in dst. this is used by the cfbGlyphBlt code for glyphs
316 <=PPW bits wide.
317*/
318
319#if (BITMAP_BIT_ORDER == MSBFirst)
320#define BitRight(lw,n) ((lw) >> (n))
321#define BitLeft(lw,n) ((lw) << (n))
322#else /* (BITMAP_BIT_ORDER == LSBFirst) */
323#define BitRight(lw,n) ((lw) << (n))
324#define BitLeft(lw,n) ((lw) >> (n))
325#endif /* (BITMAP_BIT_ORDER == MSBFirst) */
326
327#define SCRLEFT(lw, n) BitLeft (lw, (n) * PSZ)
328#define SCRRIGHT(lw, n) BitRight(lw, (n) * PSZ)
329
330/*
331 * Note that the shift direction is independent of the byte ordering of the
332 * machine. The following is portable code.
333 */
334#if PPW == 16
335#define PFILL(p) ( ((p)&PMSK) | \
336 ((p)&PMSK) << PSZ | \
337 ((p)&PMSK) << 2*PSZ | \
338 ((p)&PMSK) << 3*PSZ | \
339 ((p)&PMSK) << 4*PSZ | \
340 ((p)&PMSK) << 5*PSZ | \
341 ((p)&PMSK) << 6*PSZ | \
342 ((p)&PMSK) << 7*PSZ | \
343 ((p)&PMSK) << 8*PSZ | \
344 ((p)&PMSK) << 9*PSZ | \
345 ((p)&PMSK) << 10*PSZ | \
346 ((p)&PMSK) << 11*PSZ | \
347 ((p)&PMSK) << 12*PSZ | \
348 ((p)&PMSK) << 13*PSZ | \
349 ((p)&PMSK) << 14*PSZ | \
350 ((p)&PMSK) << 15*PSZ )
351#define PFILL2(p, pf) { \
352 pf = (p) & PMSK; \
353 pf |= (pf << PSZ); \
354 pf |= (pf << 2*PSZ); \
355 pf |= (pf << 4*PSZ); \
356 pf |= (pf << 8*PSZ); \
357}
358#endif /* PPW == 16 */
359#if PPW == 8
360#define PFILL(p) ( ((p)&PMSK) | \
361 ((p)&PMSK) << PSZ | \
362 ((p)&PMSK) << 2*PSZ | \
363 ((p)&PMSK) << 3*PSZ | \
364 ((p)&PMSK) << 4*PSZ | \
365 ((p)&PMSK) << 5*PSZ | \
366 ((p)&PMSK) << 6*PSZ | \
367 ((p)&PMSK) << 7*PSZ )
368#define PFILL2(p, pf) { \
369 pf = (p) & PMSK; \
370 pf |= (pf << PSZ); \
371 pf |= (pf << 2*PSZ); \
372 pf |= (pf << 4*PSZ); \
373}
374#endif
375#if PPW == 4
376#define PFILL(p) ( ((p)&PMSK) | \
377 ((p)&PMSK) << PSZ | \
378 ((p)&PMSK) << 2*PSZ | \
379 ((p)&PMSK) << 3*PSZ )
380#define PFILL2(p, pf) { \
381 pf = (p) & PMSK; \
382 pf |= (pf << PSZ); \
383 pf |= (pf << 2*PSZ); \
384}
385#endif
386#if PPW == 2
387#define PFILL(p) ( ((p)&PMSK) | \
388 ((p)&PMSK) << PSZ )
389#define PFILL2(p, pf) { \
390 pf = (p) & PMSK; \
391 pf |= (pf << PSZ); \
392}
393#endif
394#if PPW == 1
395#define PFILL(p) (p)
396#define PFILL2(p,pf) (pf = (p))
397#endif
398
399/*
400 * Reduced raster op - using precomputed values, perform the above
401 * in three instructions
402 */
403
404#define DoRRop(dst, and, xor) (((dst) & (and)) ^ (xor))
405
406#define DoMaskRRop(dst, and, xor, mask) \
407 (((dst) & ((and) | ~(mask))) ^ (xor & mask))
408
409#if PSZ != 32 || PPW != 1
410
411# if (PSZ == 24 && PPW == 1)
412#define maskbits(x, w, startmask, endmask, nlw) {\
413 startmask = cfbstarttab[(x)&3]; \
414 endmask = cfbendtab[((x)+(w)) & 3]; \
415 nlw = ((((x)+(w))*3)>>2) - (((x)*3 +3)>>2); \
416}
417
418#define mask32bits(x, w, startmask, endmask) \
419 startmask = cfbstarttab[(x)&3]; \
420 endmask = cfbendtab[((x)+(w)) & 3];
421
422#define maskpartialbits(x, w, mask) \
423 mask = cfbstartpartial[(x) & 3] & cfbendpartial[((x)+(w)) & 3];
424
425#define maskbits24(x, w, startmask, endmask, nlw) \
426 startmask = cfbstarttab24[(x) & 3]; \
427 endmask = cfbendtab24[((x)+(w)) & 3]; \
428 if (startmask){ \
429 nlw = (((w) - (4 - ((x) & 3))) >> 2); \
430 } else { \
431 nlw = (w) >> 2; \
432 }
433
434#define getbits24(psrc, dst, index) {\
435 register int idx; \
436 switch(idx = ((index)&3)<<1){ \
437 case 0: \
438 dst = (*(psrc) &cfbmask[idx]); \
439 break; \
440 case 6: \
441 dst = BitLeft((*(psrc) &cfbmask[idx]), cfb24Shift[idx]); \
442 break; \
443 default: \
444 dst = BitLeft((*(psrc) &cfbmask[idx]), cfb24Shift[idx]) | \
445 BitRight(((*((psrc)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
446 }; \
447}
448
449#define putbits24(src, w, pdst, planemask, index) {\
450 register PixelGroup dstpixel; \
451 register unsigned int idx; \
452 switch(idx = ((index)&3)<<1){ \
453 case 0: \
454 dstpixel = (*(pdst) &cfbmask[idx]); \
455 break; \
456 case 6: \
457 dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx]); \
458 break; \
459 default: \
460 dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx])| \
461 BitRight(((*((pdst)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
462 }; \
463 dstpixel &= ~(planemask); \
464 dstpixel |= (src & planemask); \
465 *(pdst) &= cfbrmask[idx]; \
466 switch(idx){ \
467 case 0: \
468 *(pdst) |= (dstpixel & cfbmask[idx]); \
469 break; \
470 case 2: \
471 case 4: \
472 pdst++;idx++; \
473 *(pdst) = ((*(pdst)) & cfbrmask[idx]) | \
474 (BitLeft(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
475 pdst--;idx--; \
476 case 6: \
477 *(pdst) |= (BitRight(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
478 break; \
479 }; \
480}
481
482#define putbitsrop24(src, x, pdst, planemask, rop) \
483{ \
484 register PixelGroup t1, dstpixel; \
485 register unsigned int idx; \
486 switch(idx = (x)<<1){ \
487 case 0: \
488 dstpixel = (*(pdst) &cfbmask[idx]); \
489 break; \
490 case 6: \
491 dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx]); \
492 break; \
493 default: \
494 dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx])| \
495 BitRight(((*((pdst)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
496 }; \
497 DoRop(t1, rop, (src), dstpixel); \
498 dstpixel &= ~planemask; \
499 dstpixel |= (t1 & planemask); \
500 *(pdst) &= cfbrmask[idx]; \
501 switch(idx){ \
502 case 0: \
503 *(pdst) |= (dstpixel & cfbmask[idx]); \
504 break; \
505 case 2: \
506 case 4: \
507 *((pdst)+1) = ((*((pdst)+1)) & cfbrmask[idx+1]) | \
508 (BitLeft(dstpixel, cfb24Shift[idx+1]) & (cfbmask[idx+1])); \
509 case 6: \
510 *(pdst) |= (BitRight(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
511 }; \
512}
513# else /* PSZ == 24 && PPW == 1 */
514#define maskbits(x, w, startmask, endmask, nlw) \
515 startmask = cfbstarttab[(x)&PIM]; \
516 endmask = cfbendtab[((x)+(w)) & PIM]; \
517 if (startmask) \
518 nlw = (((w) - (PPW - ((x)&PIM))) >> PWSH); \
519 else \
520 nlw = (w) >> PWSH;
521
522#define maskpartialbits(x, w, mask) \
523 mask = cfbstartpartial[(x) & PIM] & cfbendpartial[((x) + (w)) & PIM];
524
525#define mask32bits(x, w, startmask, endmask) \
526 startmask = cfbstarttab[(x)&PIM]; \
527 endmask = cfbendtab[((x)+(w)) & PIM];
528
529/* FIXME */
530#define maskbits24(x, w, startmask, endmask, nlw) \
531 abort()
532#define getbits24(psrc, dst, index) \
533 abort()
534#define putbits24(src, w, pdst, planemask, index) \
535 abort()
536#define putbitsrop24(src, x, pdst, planemask, rop) \
537 abort()
538
539#endif /* PSZ == 24 && PPW == 1 */
540
541#define getbits(psrc, x, w, dst) \
542if ( ((x) + (w)) <= PPW) \
543{ \
544 dst = SCRLEFT(*(psrc), (x)); \
545} \
546else \
547{ \
548 int m; \
549 m = PPW-(x); \
550 dst = (SCRLEFT(*(psrc), (x)) & cfbendtab[m]) | \
551 (SCRRIGHT(*((psrc)+1), m) & cfbstarttab[m]); \
552}
553
554
555#define putbits(src, x, w, pdst, planemask) \
556if ( ((x)+(w)) <= PPW) \
557{ \
558 PixelGroup tmpmask; \
559 maskpartialbits((x), (w), tmpmask); \
560 tmpmask &= PFILL(planemask); \
561 *(pdst) = (*(pdst) & ~tmpmask) | (SCRRIGHT(src, x) & tmpmask); \
562} \
563else \
564{ \
565 unsigned int m; \
566 unsigned int n; \
567 PixelGroup pm = PFILL(planemask); \
568 m = PPW-(x); \
569 n = (w) - m; \
570 *(pdst) = (*(pdst) & (cfbendtab[x] | ~pm)) | \
571 (SCRRIGHT(src, x) & (cfbstarttab[x] & pm)); \
572 *((pdst)+1) = (*((pdst)+1) & (cfbstarttab[n] | ~pm)) | \
573 (SCRLEFT(src, m) & (cfbendtab[n] & pm)); \
574}
575#if defined(__GNUC__) && defined(mc68020)
576#undef getbits
577#define FASTGETBITS(psrc, x, w, dst) \
578 asm ("bfextu %3{%1:%2},%0" \
579 : "=d" (dst) : "di" (x), "di" (w), "o" (*(char *)(psrc)))
580
581#define getbits(psrc,x,w,dst) \
582{ \
583 FASTGETBITS(psrc, (x) * PSZ, (w) * PSZ, dst); \
584 dst = SCRLEFT(dst,PPW-(w)); \
585}
586
587#define FASTPUTBITS(src, x, w, pdst) \
588 asm ("bfins %3,%0{%1:%2}" \
589 : "=o" (*(char *)(pdst)) \
590 : "di" (x), "di" (w), "d" (src), "0" (*(char *) (pdst)))
591
592#undef putbits
593#define putbits(src, x, w, pdst, planemask) \
594{ \
595 if (planemask != PMSK) { \
596 PixelGroup _m, _pm; \
597 FASTGETBITS(pdst, (x) * PSZ , (w) * PSZ, _m); \
598 PFILL2(planemask, _pm); \
599 _m &= (~_pm); \
600 _m |= (SCRRIGHT(src, PPW-(w)) & _pm); \
601 FASTPUTBITS(_m, (x) * PSZ, (w) * PSZ, pdst); \
602 } else { \
603 FASTPUTBITS(SCRRIGHT(src, PPW-(w)), (x) * PSZ, (w) * PSZ, pdst); \
604 } \
605}
606
607
608#endif /* mc68020 */
609
610#define putbitsrop(src, x, w, pdst, planemask, rop) \
611if ( ((x)+(w)) <= PPW) \
612{ \
613 PixelGroup tmpmask; \
614 PixelGroup t1, t2; \
615 maskpartialbits((x), (w), tmpmask); \
616 PFILL2(planemask, t1); \
617 tmpmask &= t1; \
618 t1 = SCRRIGHT((src), (x)); \
619 DoRop(t2, rop, t1, *(pdst)); \
620 *(pdst) = (*(pdst) & ~tmpmask) | (t2 & tmpmask); \
621} \
622else \
623{ \
624 CfbBits m; \
625 CfbBits n; \
626 PixelGroup t1, t2; \
627 PixelGroup pm; \
628 PFILL2(planemask, pm); \
629 m = PPW-(x); \
630 n = (w) - m; \
631 t1 = SCRRIGHT((src), (x)); \
632 DoRop(t2, rop, t1, *(pdst)); \
633 *(pdst) = (*(pdst) & (cfbendtab[x] | ~pm)) | (t2 & (cfbstarttab[x] & pm));\
634 t1 = SCRLEFT((src), m); \
635 DoRop(t2, rop, t1, *((pdst) + 1)); \
636 *((pdst)+1) = (*((pdst)+1) & (cfbstarttab[n] | ~pm)) | \
637 (t2 & (cfbendtab[n] & pm)); \
638}
639
640#else /* PSZ == 32 && PPW == 1*/
641
642/*
643 * These macros can be optimized for 32-bit pixels since there is no
644 * need to worry about left/right edge masking. These macros were
645 * derived from the above using the following reductions:
646 *
647 * - x & PIW = 0 [since PIW = 0]
648 * - all masking tables are only indexed by 0 [ due to above ]
649 * - cfbstartab[0] and cfbendtab[0] = 0 [ no left/right edge masks]
650 * - cfbstartpartial[0] and cfbendpartial[0] = ~0 [no partial pixel mask]
651 *
652 * Macro reduction based upon constants cannot be performed automatically
653 * by the compiler since it does not know the contents of the masking
654 * arrays in cfbmskbits.c.
655 */
656#define maskbits(x, w, startmask, endmask, nlw) \
657 startmask = endmask = 0; \
658 nlw = (w);
659
660#define maskpartialbits(x, w, mask) \
661 mask = 0xFFFFFFFF;
662
663#define mask32bits(x, w, startmask, endmask) \
664 startmask = endmask = 0;
665
666/*
667 * For 32-bit operations, getbits(), putbits(), and putbitsrop()
668 * will only be invoked with x = 0 and w = PPW (1). The getbits()
669 * macro is only called within left/right edge logic, which doesn't
670 * happen for 32-bit pixels.
671 */
672#define getbits(psrc, x, w, dst) (dst) = *(psrc)
673
674#define putbits(src, x, w, pdst, planemask) \
675 *(pdst) = (*(pdst) & ~planemask) | (src & planemask);
676
677#define putbitsrop(src, x, w, pdst, planemask, rop) \
678{ \
679 PixelGroup t1; \
680 DoRop(t1, rop, (src), *(pdst)); \
681 *(pdst) = (*(pdst) & ~planemask) | (t1 & planemask); \
682}
683
684#endif /* PSZ != 32 */
685
686/*
687 * Use these macros only when you're using the MergeRop stuff
688 * in ../mfb/mergerop.h
689 */
690
691/* useful only when not spanning destination longwords */
692#if PSZ == 24
693#define putbitsmropshort24(src,x,w,pdst,index) {\
694 PixelGroup _tmpmask; \
695 PixelGroup _t1; \
696 maskpartialbits ((x), (w), _tmpmask); \
697 _t1 = SCRRIGHT((src), (x)); \
698 DoMaskMergeRop24(_t1, pdst, _tmpmask, index); \
699}
700#endif
701#define putbitsmropshort(src,x,w,pdst) {\
702 PixelGroup _tmpmask; \
703 PixelGroup _t1; \
704 maskpartialbits ((x), (w), _tmpmask); \
705 _t1 = SCRRIGHT((src), (x)); \
706 *pdst = DoMaskMergeRop(_t1, *pdst, _tmpmask); \
707}
708
709/* useful only when spanning destination longwords */
710#define putbitsmroplong(src,x,w,pdst) { \
711 PixelGroup _startmask, _endmask; \
712 int _m; \
713 PixelGroup _t1; \
714 _m = PPW - (x); \
715 _startmask = cfbstarttab[x]; \
716 _endmask = cfbendtab[(w) - _m]; \
717 _t1 = SCRRIGHT((src), (x)); \
718 pdst[0] = DoMaskMergeRop(_t1,pdst[0],_startmask); \
719 _t1 = SCRLEFT ((src),_m); \
720 pdst[1] = DoMaskMergeRop(_t1,pdst[1],_endmask); \
721}
722
723#define putbitsmrop(src,x,w,pdst) \
724if ((x) + (w) <= PPW) {\
725 putbitsmropshort(src,x,w,pdst); \
726} else { \
727 putbitsmroplong(src,x,w,pdst); \
728}
729
730#if GETLEFTBITS_ALIGNMENT == 1
731#define getleftbits(psrc, w, dst) dst = *((unsigned int *) psrc)
732#define getleftbits24(psrc, w, dst, idx){ \
733 regiseter int index; \
734 switch(index = ((idx)&3)<<1){ \
735 case 0: \
736 dst = (*((unsigned int *) psrc))&cfbmask[index]; \
737 break; \
738 case 2: \
739 case 4: \
740 dst = BitLeft(((*((unsigned int *) psrc))&cfbmask[index]), cfb24Shift[index]); \
741 dst |= BitRight(((*((unsigned int *) psrc)+1)&cfbmask[index]), cfb4Shift[index]); \
742 break; \
743 case 6: \
744 dst = BitLeft((*((unsigned int *) psrc)),cfb24Shift[index]); \
745 break; \
746 }; \
747}
748#endif /* GETLEFTBITS_ALIGNMENT == 1 */
749
750#define getglyphbits(psrc, x, w, dst) \
751{ \
752 dst = BitLeft((unsigned) *(psrc), (x)); \
753 if ( ((x) + (w)) > 32) \
754 dst |= (BitRight((unsigned) *((psrc)+1), 32-(x))); \
755}
756#if GETLEFTBITS_ALIGNMENT == 2
757#define getleftbits(psrc, w, dst) \
758 { \
759 if ( ((int)(psrc)) & 0x01 ) \
760 getglyphbits( ((unsigned int *)(((char *)(psrc))-1)), 8, (w), (dst) ); \
761 else \
762 dst = *((unsigned int *) psrc); \
763 }
764#endif /* GETLEFTBITS_ALIGNMENT == 2 */
765
766#if GETLEFTBITS_ALIGNMENT == 4
767#define getleftbits(psrc, w, dst) \
768 { \
769 int off, off_b; \
770 off_b = (off = ( ((int)(psrc)) & 0x03)) << 3; \
771 getglyphbits( \
772 (unsigned int *)( ((char *)(psrc)) - off), \
773 (off_b), (w), (dst) \
774 ); \
775 }
776#endif /* GETLEFTBITS_ALIGNMENT == 4 */
777
778/*
779 * getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix )
780 *
781 * Converts bits to pixels in a reasonable way. Takes w (1 <= w <= PPW)
782 * bits from *psrcstip, starting at bit x; call this a quartet of bits.
783 * Then, takes the pixels from *psrcpix corresponding to the one-bits (if
784 * ones is TRUE) or the zero-bits (if ones is FALSE) of the quartet
785 * and puts these pixels into destpix.
786 *
787 * Example:
788 *
789 * getstipplepixels( &(0x08192A3B), 17, 4, 1, &(0x4C5D6E7F), dest )
790 *
791 * 0x08192A3B = 0000 1000 0001 1001 0010 1010 0011 1011
792 *
793 * This will take 4 bits starting at bit 17, so the quartet is 0x5 = 0101.
794 * It will take pixels from 0x4C5D6E7F corresponding to the one-bits in this
795 * quartet, so dest = 0x005D007F.
796 *
797 * XXX Works with both byte order.
798 * XXX This works for all values of x and w within a doubleword.
799 */
800#if (BITMAP_BIT_ORDER == MSBFirst)
801#define getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix ) \
802{ \
803 PixelGroup q; \
804 int m; \
805 if ((m = ((x) - ((PPW*PSZ)-PPW))) > 0) { \
806 q = (*(psrcstip)) << m; \
807 if ( (x)+(w) > (PPW*PSZ) ) \
808 q |= *((psrcstip)+1) >> ((PPW*PSZ)-m); \
809 } \
810 else \
811 q = (*(psrcstip)) >> -m; \
812 q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
813 *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
814}
815/* I just copied this to get the linker satisfied on PowerPC,
816 * so this may not be correct at all.
817 */
818#define getstipplepixels24(psrcstip,xt,ones,psrcpix,destpix,stipindex) \
819{ \
820 PixelGroup q; \
821 q = *(psrcstip) >> (xt); \
822 q = ((ones) ? q : ~q) & 1; \
823 *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
824}
825#else /* BITMAP_BIT_ORDER == LSB */
826
827/* this must load 32 bits worth; for most machines, thats an int */
828#define CfbFetchUnaligned(x) ldl_u(x)
829
830#define getstipplepixels( psrcstip, xt, w, ones, psrcpix, destpix ) \
831{ \
832 PixelGroup q; \
833 q = CfbFetchUnaligned(psrcstip) >> (xt); \
834 if ( ((xt)+(w)) > (PPW*PSZ) ) \
835 q |= (CfbFetchUnaligned((psrcstip)+1)) << ((PPW*PSZ)-(xt)); \
836 q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
837 *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
838}
839#if PSZ == 24
840# if 0
841#define getstipplepixels24(psrcstip,xt,w,ones,psrcpix,destpix,stipindex,srcindex,dstindex) \
842{ \
843 PixelGroup q; \
844 CfbBits src; \
845 register unsigned int sidx; \
846 register unsigned int didx; \
847 sidx = ((srcindex) & 3)<<1; \
848 didx = ((dstindex) & 3)<<1; \
849 q = *(psrcstip) >> (xt); \
850/* if((srcindex)!=0)*/ \
851/* src = (((*(psrcpix)) << cfb24Shift[sidx]) & (cfbmask[sidx])) |*/ \
852/* (((*((psrcpix)+1)) << cfb24Shift[sidx+1]) & (cfbmask[sidx+1])); */\
853/* else */\
854 src = (*(psrcpix))&0xFFFFFF; \
855 if ( ((xt)+(w)) > PGSZ ) \
856 q |= (*((psrcstip)+1)) << (PGSZ -(xt)); \
857 q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
858 src &= QuartetPixelMaskTable[q]; \
859 *(destpix) &= cfbrmask[didx]; \
860 switch(didx) {\
861 case 0: \
862 *(destpix) |= (src &cfbmask[didx]); \
863 break; \
864 case 2: \
865 case 4: \
866 destpix++;didx++; \
867 *(destpix) = ((*(destpix)) & (cfbrmask[didx]))| \
868 (BitLeft(src, cfb24Shift[didx]) & (cfbmask[didx])); \
869 destpix--; didx--;\
870 case 6: \
871 *(destpix) |= (BitRight(src, cfb24Shift[didx]) & cfbmask[didx]); \
872 break; \
873 }; \
874}
875# else
876#define getstipplepixels24(psrcstip,xt,ones,psrcpix,destpix,stipindex) \
877{ \
878 PixelGroup q; \
879 q = *(psrcstip) >> (xt); \
880 q = ((ones) ? q : ~q) & 1; \
881 *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
882}
883# endif
884#endif /* PSZ == 24 */
885#endif
886
887extern PixelGroup cfbstarttab[];
888extern PixelGroup cfbendtab[];
889extern PixelGroup cfbstartpartial[];
890extern PixelGroup cfbendpartial[];
891extern PixelGroup cfbrmask[];
892extern PixelGroup cfbmask[];
893extern PixelGroup QuartetBitsTable[];
894extern PixelGroup QuartetPixelMaskTable[];
895#if PSZ == 24
896extern int cfb24Shift[];
897#endif
Note: See TracBrowser for help on using the repository browser.

© 2024 Oracle Support Privacy / Do Not Sell My Info Terms of Use Trademark Policy Automated Access Etiquette