45e9809aff7304721fddb95654901b32195c9c7avboxsync/************************************************************
45e9809aff7304721fddb95654901b32195c9c7avboxsyncCopyright 1987 by Sun Microsystems, Inc. Mountain View, CA.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync All Rights Reserved
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncPermission to use, copy, modify, and distribute this
45e9809aff7304721fddb95654901b32195c9c7avboxsyncsoftware and its documentation for any purpose and without
45e9809aff7304721fddb95654901b32195c9c7avboxsyncfee is hereby granted, provided that the above copyright no-
45e9809aff7304721fddb95654901b32195c9c7avboxsynctice appear in all copies and that both that copyright no-
45e9809aff7304721fddb95654901b32195c9c7avboxsynctice and this permission notice appear in supporting docu-
45e9809aff7304721fddb95654901b32195c9c7avboxsyncmentation, and that the names of Sun or The Open Group
45e9809aff7304721fddb95654901b32195c9c7avboxsyncnot be used in advertising or publicity pertaining to
45e9809aff7304721fddb95654901b32195c9c7avboxsyncdistribution of the software without specific prior
45e9809aff7304721fddb95654901b32195c9c7avboxsyncwritten permission. Sun and The Open Group make no
45e9809aff7304721fddb95654901b32195c9c7avboxsyncrepresentations about the suitability of this software for
45e9809aff7304721fddb95654901b32195c9c7avboxsyncany purpose. It is provided "as is" without any express or
45e9809aff7304721fddb95654901b32195c9c7avboxsyncimplied warranty.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncSUN DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
45e9809aff7304721fddb95654901b32195c9c7avboxsyncINCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
45e9809aff7304721fddb95654901b32195c9c7avboxsyncNESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SUN BE LI-
45e9809aff7304721fddb95654901b32195c9c7avboxsyncABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
45e9809aff7304721fddb95654901b32195c9c7avboxsyncANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
45e9809aff7304721fddb95654901b32195c9c7avboxsyncPROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR
45e9809aff7304721fddb95654901b32195c9c7avboxsyncOTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH
45e9809aff7304721fddb95654901b32195c9c7avboxsyncTHE USE OR PERFORMANCE OF THIS SOFTWARE.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync********************************************************/
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* Optimizations for PSZ == 32 added by Kyle Marvin (marvin@vitec.com) */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#include <X11/X.h>
45e9809aff7304721fddb95654901b32195c9c7avboxsync#include <X11/Xmd.h>
45e9809aff7304721fddb95654901b32195c9c7avboxsync#include "servermd.h"
45e9809aff7304721fddb95654901b32195c9c7avboxsync#include "compiler.h"
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * ==========================================================================
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Converted from mfb to support memory-mapped color framebuffer by smarks@sun,
45e9809aff7304721fddb95654901b32195c9c7avboxsync * April-May 1987.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * The way I did the conversion was to consider each longword as an
45e9809aff7304721fddb95654901b32195c9c7avboxsync * array of four bytes instead of an array of 32 one-bit pixels. So
45e9809aff7304721fddb95654901b32195c9c7avboxsync * getbits() and putbits() retain much the same calling sequence, but
45e9809aff7304721fddb95654901b32195c9c7avboxsync * they move bytes around instead of bits. Of course, this entails the
45e9809aff7304721fddb95654901b32195c9c7avboxsync * removal of all of the one-bit-pixel dependencies from the other
45e9809aff7304721fddb95654901b32195c9c7avboxsync * files, but the major bit-hacking stuff should be covered here.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * I've created some new macros that make it easier to understand what's
45e9809aff7304721fddb95654901b32195c9c7avboxsync * going on in the pixel calculations, and that make it easier to change the
45e9809aff7304721fddb95654901b32195c9c7avboxsync * pixel size.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * name explanation
45e9809aff7304721fddb95654901b32195c9c7avboxsync * ---- -----------
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PSZ pixel size (in bits)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZ pixel group size (in bits)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZB pixel group size (in bytes)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZBMSK mask with lowest PGSZB bits set to 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PPW pixels per word (pixels per pixel group)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PPWMSK mask with lowest PPW bits set to 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PLST index of last pixel in a word (should be PPW-1)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PIM pixel index mask (index within a pixel group)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PWSH pixel-to-word shift (should be log2(PPW))
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PMSK mask with lowest PSZ bits set to 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Here are some sample values. In the notation cfbA,B: A is PSZ, and
45e9809aff7304721fddb95654901b32195c9c7avboxsync * B is PGSZB. All the other values are derived from these
45e9809aff7304721fddb95654901b32195c9c7avboxsync * two. This table does not show all combinations!
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * name cfb8,4 cfb24,4 cfb32,4 cfb8,8 cfb24,8 cfb32,8
45e9809aff7304721fddb95654901b32195c9c7avboxsync * ---- ------ ------- ------ ------ ------ -------
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PSZ 8 24 32 8 24 32
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZ 32 32 32 64 64 64
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZB 4 4 4 8 8 8
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZBMSK 0xF 0xF? 0xF 0xFF 0xFF 0xFF
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PPW 4 1 1 8 2 2
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PPWMSK 0xF 0x1 0x1 0xFF 0x3? 0x3
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PLST 3 0 0 7 1 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PIM 0x3 0x0 0x0 0x7 0x1? 0x1
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PWSH 2 0 0 3 1 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PMSK 0xFF 0xFFFFFF 0xFFFFFFFF 0xFF 0xFFFFFF 0xFFFFFFFF
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * I have also added a new macro, PFILL, that takes one pixel and
45e9809aff7304721fddb95654901b32195c9c7avboxsync * replicates it throughout a word. This macro definition is dependent
45e9809aff7304721fddb95654901b32195c9c7avboxsync * upon pixel and word size; it doesn't use macros like PPW and so
45e9809aff7304721fddb95654901b32195c9c7avboxsync * forth. Examples: for monochrome, PFILL(1) => 0xffffffff, PFILL(0) =>
45e9809aff7304721fddb95654901b32195c9c7avboxsync * 0x00000000. For 8-bit color, PFILL(0x5d) => 0x5d5d5d5d. This macro
45e9809aff7304721fddb95654901b32195c9c7avboxsync * is used primarily for replicating a plane mask into a word.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Color framebuffers operations also support the notion of a plane
45e9809aff7304721fddb95654901b32195c9c7avboxsync * mask. This mask determines which planes of the framebuffer can be
45e9809aff7304721fddb95654901b32195c9c7avboxsync * altered; the others are left unchanged. I have added another
45e9809aff7304721fddb95654901b32195c9c7avboxsync * parameter to the putbits and putbitsrop macros that is the plane
45e9809aff7304721fddb95654901b32195c9c7avboxsync * mask.
45e9809aff7304721fddb95654901b32195c9c7avboxsync * ==========================================================================
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Keith Packard (keithp@suse.com)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * 64bit code is no longer supported; it requires DIX support
45e9809aff7304721fddb95654901b32195c9c7avboxsync * for repadding images which significantly impacts performance
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PSZ needs to be defined before we get here. Usually it comes from a
45e9809aff7304721fddb95654901b32195c9c7avboxsync * -DPSZ=foo on the compilation command line.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#ifndef PSZ
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PSZ 8
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PixelGroup is the data type used to operate on groups of pixels.
45e9809aff7304721fddb95654901b32195c9c7avboxsync * We typedef it here to CARD32 with the assumption that you
45e9809aff7304721fddb95654901b32195c9c7avboxsync * want to manipulate 32 bits worth of pixels at a time as you can. If CARD32
45e9809aff7304721fddb95654901b32195c9c7avboxsync * is not appropriate for your server, define it to something else
45e9809aff7304721fddb95654901b32195c9c7avboxsync * before including this file. In this case you will also have to define
45e9809aff7304721fddb95654901b32195c9c7avboxsync * PGSZB to the size in bytes of PixelGroup.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#ifndef PixelGroup
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PixelGroup CARD32
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PGSZB 4
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PixelGroup */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#ifndef CfbBits
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define CfbBits CARD32
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PGSZ (PGSZB << 3)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PPW (PGSZ/PSZ)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PLST (PPW-1)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIM PLST
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PMSK (((PixelGroup)1 << PSZ) - 1)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PPWMSK (((PixelGroup)1 << PPW) - 1) /* instead of BITMSK */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PGSZBMSK (((PixelGroup)1 << PGSZB) - 1)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* set PWSH = log2(PPW) using brute force */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PWSH 0
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 2
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PWSH 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 4
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PWSH 2
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 8
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PWSH 3
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 16
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PWSH 4
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 16 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 8 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 4 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 2 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 1 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* Defining PIXEL_ADDR means that individual pixels are addressable by this
45e9809aff7304721fddb95654901b32195c9c7avboxsync * machine (as type PixelType). A possible CFB architecture which supported
45e9809aff7304721fddb95654901b32195c9c7avboxsync * 8-bits-per-pixel on a non byte-addressable machine would not have this
45e9809aff7304721fddb95654901b32195c9c7avboxsync * defined.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Defining FOUR_BIT_CODE means that cfb knows how to stipple on this machine;
45e9809aff7304721fddb95654901b32195c9c7avboxsync * eventually, stippling code for 16 and 32 bit devices should be written
45e9809aff7304721fddb95654901b32195c9c7avboxsync * which would allow them to also use FOUR_BIT_CODE. There isn't that
45e9809aff7304721fddb95654901b32195c9c7avboxsync * much to do in those cases, but it would make them quite a bit faster.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 8
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIXEL_ADDR
45e9809aff7304721fddb95654901b32195c9c7avboxsynctypedef CARD8 PixelType;
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define FOUR_BIT_CODE
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 16
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIXEL_ADDR
45e9809aff7304721fddb95654901b32195c9c7avboxsynctypedef CARD16 PixelType;
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 24
45e9809aff7304721fddb95654901b32195c9c7avboxsync#undef PMSK
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PMSK 0xFFFFFF
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*#undef PIM
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIM 3*/
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIXEL_ADDR
45e9809aff7304721fddb95654901b32195c9c7avboxsynctypedef CARD32 PixelType;
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 32
45e9809aff7304721fddb95654901b32195c9c7avboxsync#undef PMSK
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PMSK 0xFFFFFFFF
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PIXEL_ADDR
45e9809aff7304721fddb95654901b32195c9c7avboxsynctypedef CARD32 PixelType;
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* the following notes use the following conventions:
45e9809aff7304721fddb95654901b32195c9c7avboxsyncSCREEN LEFT SCREEN RIGHT
45e9809aff7304721fddb95654901b32195c9c7avboxsyncin this file and maskbits.c, left and right refer to screen coordinates,
45e9809aff7304721fddb95654901b32195c9c7avboxsyncNOT bit numbering in registers.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsynccfbstarttab[n]
45e9809aff7304721fddb95654901b32195c9c7avboxsync pixels[0,n-1] = 0's pixels[n,PPW-1] = 1's
45e9809aff7304721fddb95654901b32195c9c7avboxsynccfbendtab[n] =
45e9809aff7304721fddb95654901b32195c9c7avboxsync pixels[0,n-1] = 1's pixels[n,PPW-1] = 0's
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsynccfbstartpartial[], cfbendpartial[]
45e9809aff7304721fddb95654901b32195c9c7avboxsync these are used as accelerators for doing putbits and masking out
45e9809aff7304721fddb95654901b32195c9c7avboxsyncbits that are all contained between longword boudaries. the extra
45e9809aff7304721fddb95654901b32195c9c7avboxsync256 bytes of data seems a small price to pay -- code is smaller,
45e9809aff7304721fddb95654901b32195c9c7avboxsyncand narrow things (e.g. window borders) go faster.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncthe names may seem misleading; they are derived not from which end
45e9809aff7304721fddb95654901b32195c9c7avboxsyncof the word the bits are turned on, but at which end of a scanline
45e9809aff7304721fddb95654901b32195c9c7avboxsyncthe table tends to be used.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsynclook at the tables and macros to understand boundary conditions.
45e9809aff7304721fddb95654901b32195c9c7avboxsync(careful readers will note that starttab[n] = ~endtab[n] for n != 0)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync-----------------------------------------------------------------------
45e9809aff7304721fddb95654901b32195c9c7avboxsyncthese two macros depend on the screen's bit ordering.
45e9809aff7304721fddb95654901b32195c9c7avboxsyncin both of them x is a screen position. they are used to
45e9809aff7304721fddb95654901b32195c9c7avboxsynccombine bits collected from multiple longwords into a
45e9809aff7304721fddb95654901b32195c9c7avboxsyncsingle destination longword, and to unpack a single
45e9809aff7304721fddb95654901b32195c9c7avboxsyncsource longword into multiple destinations.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncSCRLEFT(dst, x)
45e9809aff7304721fddb95654901b32195c9c7avboxsync takes dst[x, PPW] and moves them to dst[0, PPW-x]
45e9809aff7304721fddb95654901b32195c9c7avboxsync the contents of the rest of dst are 0 ONLY IF
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst is UNSIGNED.
45e9809aff7304721fddb95654901b32195c9c7avboxsync is cast as an unsigned.
45e9809aff7304721fddb95654901b32195c9c7avboxsync this is a right shift on the VAX, left shift on
45e9809aff7304721fddb95654901b32195c9c7avboxsync Sun and pc-rt.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncSCRRIGHT(dst, x)
45e9809aff7304721fddb95654901b32195c9c7avboxsync takes dst[0,x] and moves them to dst[PPW-x, PPW]
45e9809aff7304721fddb95654901b32195c9c7avboxsync the contents of the rest of dst are 0 ONLY IF
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst is UNSIGNED.
45e9809aff7304721fddb95654901b32195c9c7avboxsync this is a left shift on the VAX, right shift on
45e9809aff7304721fddb95654901b32195c9c7avboxsync Sun and pc-rt.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncthe remaining macros are cpu-independent; all bit order dependencies
45e9809aff7304721fddb95654901b32195c9c7avboxsyncare built into the tables and the two macros above.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncmaskbits(x, w, startmask, endmask, nlw)
45e9809aff7304721fddb95654901b32195c9c7avboxsync for a span of width w starting at position x, returns
45e9809aff7304721fddb95654901b32195c9c7avboxsynca mask for ragged pixels at start, mask for ragged pixels at end,
45e9809aff7304721fddb95654901b32195c9c7avboxsyncand the number of whole longwords between the ends.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncmaskpartialbits(x, w, mask)
45e9809aff7304721fddb95654901b32195c9c7avboxsync works like maskbits(), except all the pixels are in the
45e9809aff7304721fddb95654901b32195c9c7avboxsync same longword (i.e. (x&0xPIM + w) <= PPW)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncmask32bits(x, w, startmask, endmask, nlw)
45e9809aff7304721fddb95654901b32195c9c7avboxsync as maskbits, but does not calculate nlw. it is used by
45e9809aff7304721fddb95654901b32195c9c7avboxsync cfbGlyphBlt to put down glyphs <= PPW bits wide.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncgetbits(psrc, x, w, dst)
45e9809aff7304721fddb95654901b32195c9c7avboxsync starting at position x in psrc (x < PPW), collect w
45e9809aff7304721fddb95654901b32195c9c7avboxsync pixels and put them in the screen left portion of dst.
45e9809aff7304721fddb95654901b32195c9c7avboxsync psrc is a longword pointer. this may span longword boundaries.
45e9809aff7304721fddb95654901b32195c9c7avboxsync it special-cases fetching all w bits from one longword.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync +--------+--------+ +--------+
45e9809aff7304721fddb95654901b32195c9c7avboxsync | | m |n| | ==> | m |n| |
45e9809aff7304721fddb95654901b32195c9c7avboxsync +--------+--------+ +--------+
45e9809aff7304721fddb95654901b32195c9c7avboxsync x x+w 0 w
45e9809aff7304721fddb95654901b32195c9c7avboxsync psrc psrc+1 dst
45e9809aff7304721fddb95654901b32195c9c7avboxsync m = PPW - x
45e9809aff7304721fddb95654901b32195c9c7avboxsync n = w - m
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync implementation:
45e9809aff7304721fddb95654901b32195c9c7avboxsync get m pixels, move to screen-left of dst, zeroing rest of dst;
45e9809aff7304721fddb95654901b32195c9c7avboxsync get n pixels from next word, move screen-right by m, zeroing
45e9809aff7304721fddb95654901b32195c9c7avboxsync lower m pixels of word.
45e9809aff7304721fddb95654901b32195c9c7avboxsync OR the two things together.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncputbits(src, x, w, pdst, planemask)
45e9809aff7304721fddb95654901b32195c9c7avboxsync starting at position x in pdst, put down the screen-leftmost
45e9809aff7304721fddb95654901b32195c9c7avboxsync w bits of src. pdst is a longword pointer. this may
45e9809aff7304721fddb95654901b32195c9c7avboxsync span longword boundaries.
45e9809aff7304721fddb95654901b32195c9c7avboxsync it special-cases putting all w bits into the same longword.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync +--------+ +--------+--------+
45e9809aff7304721fddb95654901b32195c9c7avboxsync | m |n| | ==> | | m |n| |
45e9809aff7304721fddb95654901b32195c9c7avboxsync +--------+ +--------+--------+
45e9809aff7304721fddb95654901b32195c9c7avboxsync 0 w x x+w
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst pdst pdst+1
45e9809aff7304721fddb95654901b32195c9c7avboxsync m = PPW - x
45e9809aff7304721fddb95654901b32195c9c7avboxsync n = w - m
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync implementation:
45e9809aff7304721fddb95654901b32195c9c7avboxsync get m pixels, shift screen-right by x, zero screen-leftmost x
45e9809aff7304721fddb95654901b32195c9c7avboxsync pixels; zero rightmost m bits of *pdst and OR in stuff
45e9809aff7304721fddb95654901b32195c9c7avboxsync from before the semicolon.
45e9809aff7304721fddb95654901b32195c9c7avboxsync shift src screen-left by m, zero bits n-32;
45e9809aff7304721fddb95654901b32195c9c7avboxsync zero leftmost n pixels of *(pdst+1) and OR in the
45e9809aff7304721fddb95654901b32195c9c7avboxsync stuff from before the semicolon.
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncputbitsrop(src, x, w, pdst, planemask, ROP)
45e9809aff7304721fddb95654901b32195c9c7avboxsync like putbits but calls DoRop with the rasterop ROP (see cfb.h for
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncgetleftbits(psrc, w, dst)
45e9809aff7304721fddb95654901b32195c9c7avboxsync get the leftmost w (w<=PPW) bits from *psrc and put them
45e9809aff7304721fddb95654901b32195c9c7avboxsync in dst. this is used by the cfbGlyphBlt code for glyphs
45e9809aff7304721fddb95654901b32195c9c7avboxsync <=PPW bits wide.
45e9809aff7304721fddb95654901b32195c9c7avboxsync*/
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if (BITMAP_BIT_ORDER == MSBFirst)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define BitRight(lw,n) ((lw) >> (n))
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define BitLeft(lw,n) ((lw) << (n))
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else /* (BITMAP_BIT_ORDER == LSBFirst) */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define BitRight(lw,n) ((lw) << (n))
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define BitLeft(lw,n) ((lw) >> (n))
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* (BITMAP_BIT_ORDER == MSBFirst) */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define SCRLEFT(lw, n) BitLeft (lw, (n) * PSZ)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define SCRRIGHT(lw, n) BitRight(lw, (n) * PSZ)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Note that the shift direction is independent of the byte ordering of the
45e9809aff7304721fddb95654901b32195c9c7avboxsync * machine. The following is portable code.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 16
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL(p) ( ((p)&PMSK) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 2*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 3*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 4*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 5*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 6*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 7*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 8*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 9*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 10*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 11*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 12*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 13*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 14*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 15*PSZ )
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL2(p, pf) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf = (p) & PMSK; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 2*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 4*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 8*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PPW == 16 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 8
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL(p) ( ((p)&PMSK) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 2*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 3*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 4*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 5*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 6*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 7*PSZ )
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL2(p, pf) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf = (p) & PMSK; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 2*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 4*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 4
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL(p) ( ((p)&PMSK) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 2*PSZ | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << 3*PSZ )
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL2(p, pf) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf = (p) & PMSK; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << 2*PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 2
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL(p) ( ((p)&PMSK) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ((p)&PMSK) << PSZ )
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL2(p, pf) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf = (p) & PMSK; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pf |= (pf << PSZ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PPW == 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL(p) (p)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define PFILL2(p,pf) (pf = (p))
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Reduced raster op - using precomputed values, perform the above
45e9809aff7304721fddb95654901b32195c9c7avboxsync * in three instructions
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define DoRRop(dst, and, xor) (((dst) & (and)) ^ (xor))
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define DoMaskRRop(dst, and, xor, mask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (((dst) & ((and) | ~(mask))) ^ (xor & mask))
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ != 32 || PPW != 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync# if (PSZ == 24 && PPW == 1)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskbits(x, w, startmask, endmask, nlw) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = cfbstarttab[(x)&3]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync endmask = cfbendtab[((x)+(w)) & 3]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = ((((x)+(w))*3)>>2) - (((x)*3 +3)>>2); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define mask32bits(x, w, startmask, endmask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = cfbstarttab[(x)&3]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync endmask = cfbendtab[((x)+(w)) & 3];
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskpartialbits(x, w, mask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync mask = cfbstartpartial[(x) & 3] & cfbendpartial[((x)+(w)) & 3];
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskbits24(x, w, startmask, endmask, nlw) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = cfbstarttab24[(x) & 3]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync endmask = cfbendtab24[((x)+(w)) & 3]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if (startmask){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = (((w) - (4 - ((x) & 3))) >> 2); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync } else { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = (w) >> 2; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getbits24(psrc, dst, index) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync register int idx; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(idx = ((index)&3)<<1){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = (*(psrc) &cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = BitLeft((*(psrc) &cfbmask[idx]), cfb24Shift[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync default: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = BitLeft((*(psrc) &cfbmask[idx]), cfb24Shift[idx]) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync BitRight(((*((psrc)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbits24(src, w, pdst, planemask, index) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync register PixelGroup dstpixel; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync register unsigned int idx; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(idx = ((index)&3)<<1){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = (*(pdst) &cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync default: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx])| \
45e9809aff7304721fddb95654901b32195c9c7avboxsync BitRight(((*((pdst)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel &= ~(planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel |= (src & planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) &= cfbrmask[idx]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(idx){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) |= (dstpixel & cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 2: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 4: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pdst++;idx++; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = ((*(pdst)) & cfbrmask[idx]) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (BitLeft(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pdst--;idx--; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) |= (BitRight(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsrop24(src, x, pdst, planemask, rop) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync register PixelGroup t1, dstpixel; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync register unsigned int idx; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(idx = (x)<<1){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = (*(pdst) &cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync default: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel = BitLeft((*(pdst) &cfbmask[idx]), cfb24Shift[idx])| \
45e9809aff7304721fddb95654901b32195c9c7avboxsync BitRight(((*((pdst)+1)) &cfbmask[idx+1]), cfb24Shift[idx+1]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop(t1, rop, (src), dstpixel); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel &= ~planemask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dstpixel |= (t1 & planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) &= cfbrmask[idx]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(idx){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) |= (dstpixel & cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 2: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 4: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *((pdst)+1) = ((*((pdst)+1)) & cfbrmask[idx+1]) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (BitLeft(dstpixel, cfb24Shift[idx+1]) & (cfbmask[idx+1])); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) |= (BitRight(dstpixel, cfb24Shift[idx]) & cfbmask[idx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync# else /* PSZ == 24 && PPW == 1 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskbits(x, w, startmask, endmask, nlw) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = cfbstarttab[(x)&PIM]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync endmask = cfbendtab[((x)+(w)) & PIM]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if (startmask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = (((w) - (PPW - ((x)&PIM))) >> PWSH); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync else \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = (w) >> PWSH;
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskpartialbits(x, w, mask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync mask = cfbstartpartial[(x) & PIM] & cfbendpartial[((x) + (w)) & PIM];
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define mask32bits(x, w, startmask, endmask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = cfbstarttab[(x)&PIM]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync endmask = cfbendtab[((x)+(w)) & PIM];
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* FIXME */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskbits24(x, w, startmask, endmask, nlw) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync abort()
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getbits24(psrc, dst, index) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync abort()
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbits24(src, w, pdst, planemask, index) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync abort()
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsrop24(src, x, pdst, planemask, rop) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync abort()
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PSZ == 24 && PPW == 1 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getbits(psrc, x, w, dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncif ( ((x) + (w)) <= PPW) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = SCRLEFT(*(psrc), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync} \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncelse \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync int m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync m = PPW-(x); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = (SCRLEFT(*(psrc), (x)) & cfbendtab[m]) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (SCRRIGHT(*((psrc)+1), m) & cfbstarttab[m]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbits(src, x, w, pdst, planemask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncif ( ((x)+(w)) <= PPW) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup tmpmask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync maskpartialbits((x), (w), tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync tmpmask &= PFILL(planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & ~tmpmask) | (SCRRIGHT(src, x) & tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync} \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncelse \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync unsigned int m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync unsigned int n; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup pm = PFILL(planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync m = PPW-(x); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync n = (w) - m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & (cfbendtab[x] | ~pm)) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (SCRRIGHT(src, x) & (cfbstarttab[x] & pm)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *((pdst)+1) = (*((pdst)+1) & (cfbstarttab[n] | ~pm)) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (SCRLEFT(src, m) & (cfbendtab[n] & pm)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if defined(__GNUC__) && defined(mc68020)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#undef getbits
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define FASTGETBITS(psrc, x, w, dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync asm ("bfextu %3{%1:%2},%0" \
45e9809aff7304721fddb95654901b32195c9c7avboxsync : "=d" (dst) : "di" (x), "di" (w), "o" (*(char *)(psrc)))
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getbits(psrc,x,w,dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync FASTGETBITS(psrc, (x) * PSZ, (w) * PSZ, dst); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = SCRLEFT(dst,PPW-(w)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define FASTPUTBITS(src, x, w, pdst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync asm ("bfins %3,%0{%1:%2}" \
45e9809aff7304721fddb95654901b32195c9c7avboxsync : "=o" (*(char *)(pdst)) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync : "di" (x), "di" (w), "d" (src), "0" (*(char *) (pdst)))
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#undef putbits
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbits(src, x, w, pdst, planemask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if (planemask != PMSK) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _m, _pm; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync FASTGETBITS(pdst, (x) * PSZ , (w) * PSZ, _m); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PFILL2(planemask, _pm); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _m &= (~_pm); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _m |= (SCRRIGHT(src, PPW-(w)) & _pm); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync FASTPUTBITS(_m, (x) * PSZ, (w) * PSZ, pdst); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync } else { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync FASTPUTBITS(SCRRIGHT(src, PPW-(w)), (x) * PSZ, (w) * PSZ, pdst); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync } \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* mc68020 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsrop(src, x, w, pdst, planemask, rop) \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncif ( ((x)+(w)) <= PPW) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup tmpmask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup t1, t2; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync maskpartialbits((x), (w), tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PFILL2(planemask, t1); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync tmpmask &= t1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync t1 = SCRRIGHT((src), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop(t2, rop, t1, *(pdst)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & ~tmpmask) | (t2 & tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync} \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncelse \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync CfbBits m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync CfbBits n; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup t1, t2; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup pm; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PFILL2(planemask, pm); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync m = PPW-(x); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync n = (w) - m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync t1 = SCRRIGHT((src), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop(t2, rop, t1, *(pdst)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & (cfbendtab[x] | ~pm)) | (t2 & (cfbstarttab[x] & pm));\
45e9809aff7304721fddb95654901b32195c9c7avboxsync t1 = SCRLEFT((src), m); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop(t2, rop, t1, *((pdst) + 1)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *((pdst)+1) = (*((pdst)+1) & (cfbstarttab[n] | ~pm)) | \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (t2 & (cfbendtab[n] & pm)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else /* PSZ == 32 && PPW == 1*/
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * These macros can be optimized for 32-bit pixels since there is no
45e9809aff7304721fddb95654901b32195c9c7avboxsync * need to worry about left/right edge masking. These macros were
45e9809aff7304721fddb95654901b32195c9c7avboxsync * derived from the above using the following reductions:
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * - x & PIW = 0 [since PIW = 0]
45e9809aff7304721fddb95654901b32195c9c7avboxsync * - all masking tables are only indexed by 0 [ due to above ]
45e9809aff7304721fddb95654901b32195c9c7avboxsync * - cfbstartab[0] and cfbendtab[0] = 0 [ no left/right edge masks]
45e9809aff7304721fddb95654901b32195c9c7avboxsync * - cfbstartpartial[0] and cfbendpartial[0] = ~0 [no partial pixel mask]
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Macro reduction based upon constants cannot be performed automatically
45e9809aff7304721fddb95654901b32195c9c7avboxsync * by the compiler since it does not know the contents of the masking
45e9809aff7304721fddb95654901b32195c9c7avboxsync * arrays in cfbmskbits.c.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskbits(x, w, startmask, endmask, nlw) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = endmask = 0; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync nlw = (w);
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define maskpartialbits(x, w, mask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync mask = 0xFFFFFFFF;
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define mask32bits(x, w, startmask, endmask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync startmask = endmask = 0;
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * For 32-bit operations, getbits(), putbits(), and putbitsrop()
45e9809aff7304721fddb95654901b32195c9c7avboxsync * will only be invoked with x = 0 and w = PPW (1). The getbits()
45e9809aff7304721fddb95654901b32195c9c7avboxsync * macro is only called within left/right edge logic, which doesn't
45e9809aff7304721fddb95654901b32195c9c7avboxsync * happen for 32-bit pixels.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getbits(psrc, x, w, dst) (dst) = *(psrc)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbits(src, x, w, pdst, planemask) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & ~planemask) | (src & planemask);
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsrop(src, x, w, pdst, planemask, rop) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup t1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoRop(t1, rop, (src), *(pdst)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(pdst) = (*(pdst) & ~planemask) | (t1 & planemask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PSZ != 32 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Use these macros only when you're using the MergeRop stuff
45e9809aff7304721fddb95654901b32195c9c7avboxsync * in ../mfb/mergerop.h
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* useful only when not spanning destination longwords */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 24
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsmropshort24(src,x,w,pdst,index) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _tmpmask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _t1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync maskpartialbits ((x), (w), _tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _t1 = SCRRIGHT((src), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync DoMaskMergeRop24(_t1, pdst, _tmpmask, index); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsmropshort(src,x,w,pdst) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _tmpmask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _t1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync maskpartialbits ((x), (w), _tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _t1 = SCRRIGHT((src), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *pdst = DoMaskMergeRop(_t1, *pdst, _tmpmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* useful only when spanning destination longwords */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsmroplong(src,x,w,pdst) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _startmask, _endmask; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync int _m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup _t1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _m = PPW - (x); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _startmask = cfbstarttab[x]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _endmask = cfbendtab[(w) - _m]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _t1 = SCRRIGHT((src), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pdst[0] = DoMaskMergeRop(_t1,pdst[0],_startmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync _t1 = SCRLEFT ((src),_m); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync pdst[1] = DoMaskMergeRop(_t1,pdst[1],_endmask); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define putbitsmrop(src,x,w,pdst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsyncif ((x) + (w) <= PPW) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync putbitsmropshort(src,x,w,pdst); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync} else { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync putbitsmroplong(src,x,w,pdst); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if GETLEFTBITS_ALIGNMENT == 1
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getleftbits(psrc, w, dst) dst = *((unsigned int *) psrc)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getleftbits24(psrc, w, dst, idx){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync regiseter int index; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(index = ((idx)&3)<<1){ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = (*((unsigned int *) psrc))&cfbmask[index]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 2: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 4: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = BitLeft(((*((unsigned int *) psrc))&cfbmask[index]), cfb24Shift[index]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst |= BitRight(((*((unsigned int *) psrc)+1)&cfbmask[index]), cfb4Shift[index]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = BitLeft((*((unsigned int *) psrc)),cfb24Shift[index]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* GETLEFTBITS_ALIGNMENT == 1 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getglyphbits(psrc, x, w, dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = BitLeft((unsigned) *(psrc), (x)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ( ((x) + (w)) > 32) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst |= (BitRight((unsigned) *((psrc)+1), 32-(x))); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if GETLEFTBITS_ALIGNMENT == 2
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getleftbits(psrc, w, dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ( ((int)(psrc)) & 0x01 ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync getglyphbits( ((unsigned int *)(((char *)(psrc))-1)), 8, (w), (dst) ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync else \
45e9809aff7304721fddb95654901b32195c9c7avboxsync dst = *((unsigned int *) psrc); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* GETLEFTBITS_ALIGNMENT == 2 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if GETLEFTBITS_ALIGNMENT == 4
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getleftbits(psrc, w, dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync int off, off_b; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync off_b = (off = ( ((int)(psrc)) & 0x03)) << 3; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync getglyphbits( \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (unsigned int *)( ((char *)(psrc)) - off), \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (off_b), (w), (dst) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync ); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* GETLEFTBITS_ALIGNMENT == 4 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/*
45e9809aff7304721fddb95654901b32195c9c7avboxsync * getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix )
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Converts bits to pixels in a reasonable way. Takes w (1 <= w <= PPW)
45e9809aff7304721fddb95654901b32195c9c7avboxsync * bits from *psrcstip, starting at bit x; call this a quartet of bits.
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Then, takes the pixels from *psrcpix corresponding to the one-bits (if
45e9809aff7304721fddb95654901b32195c9c7avboxsync * ones is TRUE) or the zero-bits (if ones is FALSE) of the quartet
45e9809aff7304721fddb95654901b32195c9c7avboxsync * and puts these pixels into destpix.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * Example:
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * getstipplepixels( &(0x08192A3B), 17, 4, 1, &(0x4C5D6E7F), dest )
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * 0x08192A3B = 0000 1000 0001 1001 0010 1010 0011 1011
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * This will take 4 bits starting at bit 17, so the quartet is 0x5 = 0101.
45e9809aff7304721fddb95654901b32195c9c7avboxsync * It will take pixels from 0x4C5D6E7F corresponding to the one-bits in this
45e9809aff7304721fddb95654901b32195c9c7avboxsync * quartet, so dest = 0x005D007F.
45e9809aff7304721fddb95654901b32195c9c7avboxsync *
45e9809aff7304721fddb95654901b32195c9c7avboxsync * XXX Works with both byte order.
45e9809aff7304721fddb95654901b32195c9c7avboxsync * XXX This works for all values of x and w within a doubleword.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if (BITMAP_BIT_ORDER == MSBFirst)
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup q; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync int m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ((m = ((x) - ((PPW*PSZ)-PPW))) > 0) { \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = (*(psrcstip)) << m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ( (x)+(w) > (PPW*PSZ) ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q |= *((psrcstip)+1) >> ((PPW*PSZ)-m); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync } \
45e9809aff7304721fddb95654901b32195c9c7avboxsync else \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = (*(psrcstip)) >> -m; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* I just copied this to get the linker satisfied on PowerPC,
45e9809aff7304721fddb95654901b32195c9c7avboxsync * so this may not be correct at all.
45e9809aff7304721fddb95654901b32195c9c7avboxsync */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getstipplepixels24(psrcstip,xt,ones,psrcpix,destpix,stipindex) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup q; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = *(psrcstip) >> (xt); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = ((ones) ? q : ~q) & 1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#else /* BITMAP_BIT_ORDER == LSB */
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* this must load 32 bits worth; for most machines, thats an int */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define CfbFetchUnaligned(x) ldl_u(x)
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getstipplepixels( psrcstip, xt, w, ones, psrcpix, destpix ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup q; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = CfbFetchUnaligned(psrcstip) >> (xt); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ( ((xt)+(w)) > (PPW*PSZ) ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q |= (CfbFetchUnaligned((psrcstip)+1)) << ((PPW*PSZ)-(xt)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 24
45e9809aff7304721fddb95654901b32195c9c7avboxsync# if 0
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getstipplepixels24(psrcstip,xt,w,ones,psrcpix,destpix,stipindex,srcindex,dstindex) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup q; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync CfbBits src; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync register unsigned int sidx; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync register unsigned int didx; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync sidx = ((srcindex) & 3)<<1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync didx = ((dstindex) & 3)<<1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = *(psrcstip) >> (xt); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* if((srcindex)!=0)*/ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* src = (((*(psrcpix)) << cfb24Shift[sidx]) & (cfbmask[sidx])) |*/ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* (((*((psrcpix)+1)) << cfb24Shift[sidx+1]) & (cfbmask[sidx+1])); */\
45e9809aff7304721fddb95654901b32195c9c7avboxsync/* else */\
45e9809aff7304721fddb95654901b32195c9c7avboxsync src = (*(psrcpix))&0xFFFFFF; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync if ( ((xt)+(w)) > PGSZ ) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q |= (*((psrcstip)+1)) << (PGSZ -(xt)); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = QuartetBitsTable[(w)] & ((ones) ? q : ~q); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync src &= QuartetPixelMaskTable[q]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) &= cfbrmask[didx]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync switch(didx) {\
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 0: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) |= (src &cfbmask[didx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 2: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 4: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync destpix++;didx++; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) = ((*(destpix)) & (cfbrmask[didx]))| \
45e9809aff7304721fddb95654901b32195c9c7avboxsync (BitLeft(src, cfb24Shift[didx]) & (cfbmask[didx])); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync destpix--; didx--;\
45e9809aff7304721fddb95654901b32195c9c7avboxsync case 6: \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) |= (BitRight(src, cfb24Shift[didx]) & cfbmask[didx]); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync break; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync }; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync# else
45e9809aff7304721fddb95654901b32195c9c7avboxsync#define getstipplepixels24(psrcstip,xt,ones,psrcpix,destpix,stipindex) \
45e9809aff7304721fddb95654901b32195c9c7avboxsync{ \
45e9809aff7304721fddb95654901b32195c9c7avboxsync PixelGroup q; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = *(psrcstip) >> (xt); \
45e9809aff7304721fddb95654901b32195c9c7avboxsync q = ((ones) ? q : ~q) & 1; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync *(destpix) = (*(psrcpix)) & QuartetPixelMaskTable[q]; \
45e9809aff7304721fddb95654901b32195c9c7avboxsync}
45e9809aff7304721fddb95654901b32195c9c7avboxsync# endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif /* PSZ == 24 */
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif
45e9809aff7304721fddb95654901b32195c9c7avboxsync
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbstarttab[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbendtab[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbstartpartial[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbendpartial[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbrmask[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup cfbmask[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup QuartetBitsTable[];
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern PixelGroup QuartetPixelMaskTable[];
45e9809aff7304721fddb95654901b32195c9c7avboxsync#if PSZ == 24
45e9809aff7304721fddb95654901b32195c9c7avboxsyncextern int cfb24Shift[];
45e9809aff7304721fddb95654901b32195c9c7avboxsync#endif