#ifdef HAVE_DIX_CONFIG_H
#include <dix-config.h>
#endif
#include <stdlib.h>
#include <X11/X.h>
#include "gcstruct.h"
#include "windowstr.h"
#include "pixmapstr.h"
#include "regionstr.h"
#include "scrnintstr.h"
#include "mistruct.h"
#include "cfb.h"
#include "cfbmskbits.h"
#include "cfbrrop.h"
#include "miline.h"
#ifdef PIXEL_ADDR
#if defined(__GNUC__) && defined(mc68020)
#define STUPID volatile
#define REARRANGE
#else
#define STUPID
#endif
#ifdef __GNUC__
#define I_H do{
#define I_T }while(0);
#define IMPORTANT_START I_H I_H I_H I_H I_H I_H I_H I_H I_H I_H
#define IMPORTANT_END I_T I_T I_T I_T I_T I_T I_T I_T I_T I_T
#else
#define IMPORTANT_START
#define IMPORTANT_END
#endif
#define isClipped(c,ul,lr) ((((c) - (ul)) | ((lr) - (c))) & ClipMask)
#ifdef POLYSEGMENT
# if (defined(sun) || defined(__bsdi__)) && \
(defined(sparc) || defined(__sparc__))
# define WIDTH_FAST 1152
# endif
# ifdef ultrix
# define WIDTH_FAST 1024
# endif
# ifdef Mips
# define WIDTH_FAST 4096
# endif
# ifdef WIDTH_FAST
# if WIDTH_FAST == 1024
# define FAST_MUL(y) ((y) << 10)
# endif
# if WIDTH_FAST == 1152
# define FAST_MUL(y) (((y) << 10) + ((y) << 7))
# endif
# if WIDTH_FAST == 1280
# define FAST_MUL(y) (((y) << 10) + ((y) << 8))
# endif
# if WIDTH_FAST == 2048
# define FAST_MUL(y) ((y) << 11)
# endif
# if WIDTH_FAST == 4096
# define FAST_MUL(y) ((y) << 12)
# endif
# endif
# if defined(WIDTH_SHIFT)
# ifdef FAST_MUL
# define FUNC_NAME(e) RROP_NAME(RROP_NAME_CAT(e,Shift))
# if RROP == GXcopy
# define INCLUDE_OTHERS
# define SERIOUS_UNROLLING
# endif
# define INCLUDE_DRAW
# define NWIDTH(nwidth) WIDTH_FAST
# define WIDTH_MUL(y,w) FAST_MUL(y)
# endif
# else
# define FUNC_NAME(e) RROP_NAME(e)
# define WIDTH_MUL(y,w) ((y) * (w))
# define NWIDTH(nwidth) (nwidth)
# define INCLUDE_DRAW
# if !defined (FAST_MUL) && RROP == GXcopy
# define INCLUDE_OTHERS
# define SERIOUS_UNROLLING
# endif
# endif
#else
# define INCLUDE_DRAW
# define WIDTH_MUL(y,w) ((y) * (w))
# define NWIDTH(nwidth) nwidth
# ifdef PREVIOUS
# define FUNC_NAME(e) RROP_NAME(RROP_NAME_CAT(e,Previous))
# else
# define FUNC_NAME(e) RROP_NAME(e)
# if RROP == GXcopy
# define INCLUDE_OTHERS
# ifdef PLENTIFUL_REGISTERS
# define SAVE_X2Y2
# endif
# define ORIGIN
# define SERIOUS_UNROLLING
# else
# define EITHER_MODE
# endif
# endif
#endif
#if PSZ == 24
#define PXL2ADR(x) ((x)*3 >> 2)
#if RROP == GXcopy
#define body_rop \
addrp = (PixelType *)((unsigned long)addrb & ~0x03); \
switch((unsigned long)addrb & 3){ \
case 0: \
*addrp = (*addrp & 0xFF000000)|(piQxelXor[0] & 0xFFFFFF); \
break; \
case 1: \
*addrp = (*addrp & 0xFF)|(piQxelXor[2] & 0xFFFFFF00); \
break; \
case 3: \
*addrp = (*addrp & 0xFFFFFF)|(piQxelXor[0] & 0xFF000000); \
*(addrp+1)=(*(addrp+1) & 0xFFFF0000)|(piQxelXor[1] & 0xFFFF); \
break; \
case 2: \
*addrp = (*addrp & 0xFFFF)|(piQxelXor[1] & 0xFFFF0000); \
*(addrp+1)=(*(addrp+1) & 0xFFFFFF00)|(piQxelXor[2] & 0xFF); \
break; \
}
#endif
#if RROP == GXxor
#define body_rop \
addrp = (PixelType *)((unsigned long)addrb & ~0x03); \
switch((unsigned long)addrb & 3){ \
case 0: \
*addrp ^= piQxelXor[0] & 0xFFFFFF; \
break; \
case 1: \
*addrp ^= piQxelXor[2] & 0xFFFFFF00; \
break; \
case 3: \
*addrp ^= piQxelXor[0] & 0xFF000000; \
*(addrp+1) ^= piQxelXor[1] & 0xFFFF; \
break; \
case 2: \
*addrp ^= piQxelXor[1] & 0xFFFF0000; \
*(addrp+1) ^= piQxelXor[2] & 0xFF; \
break; \
}
#endif
#if RROP == GXand
#define body_rop \
addrp = (PixelType *)((unsigned long)addrb & ~0x03); \
switch((unsigned long)addrb & 3){ \
case 0: \
*addrp &= piQxelAnd[0] | 0xFF000000; \
break; \
case 1: \
*addrp &= piQxelAnd[2] | 0xFF; \
break; \
case 3: \
*addrp &= 0xFFFFFF | piQxelAnd[0]; \
*(addrp+1) &= 0xFFFF0000 | piQxelAnd[1]; \
break; \
case 2: \
*addrp &= 0xFFFF | piQxelAnd[1]; \
*(addrp+1) &= 0xFFFFFF00 | piQxelAnd[2]; \
break; \
}
#endif
#if RROP == GXor
#define body_rop \
addrp = (PixelType *)((unsigned long)addrb & ~0x03); \
switch((unsigned long)addrb & 3){ \
case 0: \
*addrp |= piQxelOr[0] & 0xFFFFFF; \
break; \
case 1: \
*addrp |= piQxelOr[2] & 0xFFFFFF00; \
break; \
case 3: \
*addrp |= piQxelOr[0] & 0xFF000000; \
*(addrp+1) |= piQxelOr[1] & 0xFFFF; \
break; \
case 2: \
*addrp |= piQxelOr[1] & 0xFFFF0000; \
*(addrp+1) |= piQxelOr[2] & 0xFF; \
break; \
}
#endif
#if RROP == GXset
#define body_rop \
addrp = (PixelType *)((unsigned long)addrb & ~0x03); \
switch((unsigned long)addrb & 3){ \
case 0: \
*addrp = (*addrp & (piQxelAnd[0]|0xFF000000)) \
^ (piQxelXor[0] & 0xFFFFFF); \
break; \
case 1: \
*addrp = (*addrp & (piQxelAnd[2]|0xFF)) \
^ (piQxelXor[2] & 0xFFFFFF00); \
break; \
case 3: \
*addrp = (*addrp & (piQxelAnd[0]|0xFFFFFF)) \
^ (piQxelXor[0] & 0xFF000000); \
*(addrp+1) = (*(addrp+1) & (piQxelAnd[1]|0xFFFF0000)) \
^ (piQxelXor[1] & 0xFFFF); \
break; \
case 2: \
*addrp = (*addrp & (piQxelAnd[1]|0xFFFF)) \
^ (piQxelXor[1] & 0xFFFF0000); \
*(addrp+1) = (*(addrp+1) & (piQxelAnd[2]|0xFFFFFF00)) \
^ (piQxelXor[2] & 0xFF); \
break; \
}
#endif
#endif
#define BUGFIX_clip
#ifdef INCLUDE_DRAW
int
#ifdef POLYSEGMENT
FUNC_NAME(cfb8SegmentSS1Rect) (pDrawable, pGC, nseg, pSegInit)
DrawablePtr pDrawable;
GCPtr pGC;
int nseg;
xSegment *pSegInit;
#else
FUNC_NAME(cfb8LineSS1Rect) (pDrawable, pGC, mode, npt, pptInit, pptInitOrig,
x1p,y1p,x2p,y2p)
DrawablePtr pDrawable;
GCPtr pGC;
int mode;
int npt;
DDXPointPtr pptInit, pptInitOrig;
int *x1p, *y1p, *x2p, *y2p;
#endif
{
register long e;
register int y1_or_e1;
register PixelType *addrp;
register int stepmajor;
register int stepminor;
#ifndef REARRANGE
register long e3;
#endif
#ifdef mc68000
register short x1_or_len;
#else
register int x1_or_len;
#endif
RROP_DECLARE
#ifdef SAVE_X2Y2
# define c2 y2
#else
register int c2;
#endif
#if !defined(ORIGIN) && !defined(POLYSEGMENT)
register int _x1 = 0, _y1 = 0, _x2 = 0, _y2 = 0;
int extents_x1, extents_y1, extents_x2, extents_y2;
#endif
#ifndef PREVIOUS
register int upperleft, lowerright;
CARD32 ClipMask = 0x80008000;
#endif
#ifdef POLYSEGMENT
register int capStyle;
#endif
#ifdef SAVE_X2Y2
register int x2, y2;
# define X1 x1_or_len
# define Y1 y1_or_e1
# define X2 x2
# define Y2 y2
#else
# ifdef POLYSEGMENT
# define X1 x1_or_len
# define Y1 y1_or_e1
# else
# define X1 intToX(y1_or_e1)
# define Y1 intToY(y1_or_e1)
# endif
# define X2 intToX(c2)
# define Y2 intToY(c2)
#endif
PixelType *addr;
int nwidth;
cfbPrivGCPtr devPriv;
BoxPtr extents;
int *ppt;
#if PSZ == 24
int xBase;
int xOffset;
PixelType *addrLineEnd;
char *addrb;
int stepmajor3, stepminor3, majordx, minordx;
#endif
#ifndef POLYSEGMENT
#ifndef ORIGIN
#ifdef BUGFIX_clip
int ex_x1, ex_y1, ex_x2, ex_y2;
#endif
#endif
#endif
int octant;
unsigned int bias = miGetZeroLineBias(pDrawable->pScreen);
devPriv = cfbGetGCPrivate(pGC);
cfbGetPixelWidthAndPointer (pDrawable, nwidth, addr);
#ifndef REARRANGE
RROP_FETCH_GCPRIV(devPriv);
#endif
extents = &pGC->pCompositeClip->extents;
#ifndef PREVIOUS
c2 = *((int *) &pDrawable->x);
c2 -= (c2 & 0x8000) << 1;
upperleft = *((int *) &extents->x1) - c2;
lowerright = *((int *) &extents->x2) - c2 - 0x00010001;
#endif
#ifndef POLYSEGMENT
#ifndef ORIGIN
#ifdef BUGFIX_clip
ex_x1 = extents->x1 - pDrawable->x;
ex_y1 = extents->y1 - pDrawable->y;
ex_x2 = extents->x2 - pDrawable->x;
ex_y2 = extents->y2 - pDrawable->y;
#endif
#endif
#endif
#if PSZ == 24
xBase = pDrawable->x;
addr += WIDTH_MUL(pDrawable->y,nwidth);
#else
addr = addr + WIDTH_MUL(pDrawable->y,nwidth) + pDrawable->x;
#endif
#ifdef POLYSEGMENT
capStyle = pGC->capStyle - CapNotLast;
ppt = (int *) pSegInit;
while (nseg--)
#else
#ifdef EITHER_MODE
mode -= CoordModePrevious;
if (!mode)
#endif
#ifndef ORIGIN
{
ppt = (int *)pptInit + 1;
_x1 = *x1p;
_y1 = *y1p;
extents_x1 = extents->x1 - pDrawable->x;
extents_x2 = extents->x2 - pDrawable->x;
extents_y1 = extents->y1 - pDrawable->y;
extents_y2 = extents->y2 - pDrawable->y;
if (_x1 < extents_x1 || _x1 >= extents_x2 ||
_y1 < extents_y1 || _y1 >= extents_y2)
{
c2 = *ppt++;
intToCoord(c2, _x2, _y2);
*x2p = _x1 + _x2;
*y2p = _y1 + _y2;
return 1;
}
#if PSZ == 24
addrLineEnd = addr + WIDTH_MUL(_y1, nwidth);
xOffset = xBase + _x1;
addrb = (char *)addrLineEnd + xOffset * 3;
addrp = (PixelType *)((unsigned long)addrb & ~0x03);
#else
addrp = addr + WIDTH_MUL(_y1, nwidth) + _x1;
#endif
_x2 = _x1;
_y2 = _y1;
}
#endif
#ifdef EITHER_MODE
else
#endif
#ifndef PREVIOUS
{
ppt = (int *) pptInit;
c2 = *ppt++;
if (isClipped (c2, upperleft, lowerright))
{
return 1;
}
#ifdef SAVE_X2Y2
intToCoord(c2,x2,y2);
#endif
#if PSZ == 24
addrLineEnd = addr + WIDTH_MUL(Y2, nwidth);
xOffset = xBase + X2;
addrb = (char *)addrLineEnd + xOffset * 3;
addrp = (PixelType *)((unsigned long)addrb & ~0x03);
#else
addrp = addr + WIDTH_MUL(Y2, nwidth) + X2;
#endif
}
#endif
while (--npt)
#endif
{
#ifdef POLYSEGMENT
y1_or_e1 = ppt[0];
c2 = ppt[1];
ppt += 2;
if (isClipped(y1_or_e1,upperleft,lowerright)|isClipped(c2,upperleft,lowerright))
break;
intToCoord(y1_or_e1,x1_or_len,y1_or_e1);
#if PSZ == 24
addrLineEnd = addr + WIDTH_MUL(y1_or_e1, nwidth);
xOffset = xBase + x1_or_len;
addrb = (char *)addrLineEnd + xOffset * 3;
addrp = (PixelType *)((unsigned long)addrb & ~0x03);
#else
addrp = addr + WIDTH_MUL(y1_or_e1, nwidth) + x1_or_len;
#endif
#else
#ifdef EITHER_MODE
if (!mode)
#endif
#ifndef ORIGIN
{
_x1 = _x2;
_y1 = _y2;
c2 = *ppt++;
intToCoord(c2, _x2, _y2);
_x2 = _x1 + _x2;
_y2 = _y1 + _y2;
#ifdef BUGFIX_clip
if (_x2 < ex_x1 || _x2 >= ex_x2 ||
_y2 < ex_y1 || _y2 >= ex_y2)
#else
if (_x2 < extents_x1 || _x2 >= extents_x2 ||
_y2 < extents_y1 || _y2 >= extents_y2)
#endif
{
break;
}
CalcLineDeltas(_x1, _y1, _x2, _y2, x1_or_len, y1_or_e1,
stepmajor, stepminor, 1, NWIDTH(nwidth), octant);
}
#endif
#ifdef EITHER_MODE
else
#endif
#ifndef PREVIOUS
{
#ifndef SAVE_X2Y2
y1_or_e1 = c2;
#else
y1_or_e1 = y2;
x1_or_len = x2;
#endif
c2 = *ppt++;
if (isClipped (c2, upperleft, lowerright))
break;
#ifdef SAVE_X2Y2
intToCoord(c2,x2,y2);
#endif
CalcLineDeltas(X1, Y1, X2, Y2, x1_or_len, y1_or_e1,
stepmajor, stepminor, 1, NWIDTH(nwidth), octant);
}
#endif
#endif
#ifdef POLYSEGMENT
CalcLineDeltas(X1, Y1, X2, Y2, x1_or_len, y1_or_e1,
stepmajor, stepminor, 1, NWIDTH(nwidth), octant);
if (y1_or_e1 != 0)
{
#endif
if (x1_or_len < y1_or_e1)
{
#ifdef REARRANGE
register int e3;
#endif
e3 = x1_or_len;
x1_or_len = y1_or_e1;
y1_or_e1 = e3;
e3 = stepminor;
stepminor = stepmajor;
stepmajor = e3;
SetYMajorOctant(octant);
}
e = -x1_or_len;
#ifdef POLYSEGMENT
if (!capStyle)
x1_or_len--;
#endif
{
#ifdef REARRANGE
register int e3;
RROP_DECLARE
RROP_FETCH_GCPRIV(devPriv);
#endif
y1_or_e1 = y1_or_e1 << 1;
e3 = e << 1;
FIXUP_ERROR(e, octant, bias);
#if PSZ == 24
if (stepmajor == 1 || stepmajor == -1){
stepmajor3 = stepmajor * 3;
stepminor3 = stepminor * sizeof (CfbBits);
majordx = stepmajor; minordx = 0;
} else {
stepmajor3 = stepmajor * sizeof (CfbBits);
stepminor3 = stepminor * 3;
majordx = 0; minordx = stepminor;
}
#endif
#if PSZ == 24
#define body {\
body_rop \
addrb += stepmajor3; \
xOffset += majordx; \
e += y1_or_e1; \
if (e >= 0){ \
addrb += stepminor3; \
xOffset += minordx; \
e += e3; \
} \
}
#else
#define body {\
RROP_SOLID(addrp); \
addrp += stepmajor; \
e += y1_or_e1; \
if (e >= 0) \
{ \
addrp += stepminor; \
e += e3; \
} \
}
#endif
#ifdef LARGE_INSTRUCTION_CACHE
# ifdef SERIOUS_UNROLLING
# define UNROLL 16
# else
# define UNROLL 4
# endif
#define CASE(n) case -n: body
while ((x1_or_len -= UNROLL) >= 0)
{
body body body body
# if UNROLL >= 8
body body body body
# endif
# if UNROLL >= 12
body body body body
# endif
# if UNROLL >= 16
body body body body
# endif
}
switch (x1_or_len)
{
CASE(1) CASE(2) CASE(3)
# if UNROLL >= 8
CASE(4) CASE(5) CASE(6) CASE(7)
# endif
# if UNROLL >= 12
CASE(8) CASE(9) CASE(10) CASE(11)
# endif
# if UNROLL >= 16
CASE(12) CASE(13) CASE(14) CASE(15)
# endif
}
#else
IMPORTANT_START
IMPORTANT_START
if (x1_or_len & 1)
body
x1_or_len >>= 1;
while (x1_or_len--) {
body body
}
IMPORTANT_END
IMPORTANT_END
#endif
#ifdef POLYSEGMENT
#if PSZ == 24
body_rop
#else
RROP_SOLID(addrp);
#endif
#endif
#if PSZ == 24
addrp = (PixelType *)((unsigned long)addrb & ~0x03);
#endif
}
#undef body
#ifdef POLYSEGMENT
}
else
{
# ifdef REARRANGE
register int e3;
RROP_DECLARE
RROP_FETCH_GCPRIV(devPriv);
# endif
if (stepmajor < 0)
{
#if PSZ == 24
xOffset -= x1_or_len;
addrp = addrLineEnd + PXL2ADR(xOffset);
#else
addrp -= x1_or_len;
#endif
if (capStyle)
x1_or_len++;
else
#if PSZ == 24
xOffset++;
addrp = addrLineEnd + PXL2ADR(xOffset);
#else
addrp++;
#endif
}
else
{
#if PSZ == 24
addrp = addrLineEnd + PXL2ADR(xOffset);
#endif
if (capStyle)
x1_or_len++;
}
# if PSZ == 24
y1_or_e1 = xOffset & 3;
# else
# if PGSZ == 64
y1_or_e1 = ((long) addrp) & 0x7;
addrp = (PixelType *) (((unsigned char *) addrp) - y1_or_e1);
# else
y1_or_e1 = ((long) addrp) & PIM;
addrp = (PixelType *) (((unsigned char *) addrp) - y1_or_e1);
# endif
#if PGSZ == 32
# if PWSH != 2
y1_or_e1 >>= (2 - PWSH);
# endif
#else
# if PWSH != 3
y1_or_e1 >>= (3 - PWSH);
# endif
#endif
# endif
#if PSZ == 24
{
#if RROP == GXcopy
register int nlmiddle;
int leftIndex = xOffset & 3;
int rightIndex = (xOffset + x1_or_len) & 3;
#else
register int pidx;
#endif
#if RROP == GXcopy
nlmiddle = x1_or_len;
if(leftIndex){
nlmiddle -= (4 - leftIndex);
}
if(rightIndex){
nlmiddle -= rightIndex;
}
nlmiddle >>= 2;
switch(leftIndex+x1_or_len){
case 4:
switch(leftIndex){
case 0:
*addrp++ = piQxelXor[0];
*addrp++ = piQxelXor[1];
*addrp = piQxelXor[2];
break;
case 1:
*addrp = ((*addrp) & 0xFFFFFF) | (piQxelXor[0] & 0xFF000000);
addrp++;
*addrp = piQxelXor[1];
addrp++;
*addrp = piQxelXor[2];
break;
case 2:
*addrp = ((*addrp) & 0xFFFF) | (piQxelXor[1] & 0xFFFF0000);
addrp++;
*addrp = piQxelXor[2];
break;
case 3:
*addrp = ((*addrp) & 0xFF) | (piQxelXor[2] & 0xFFFFFF00);
break;
}
break;
case 3:
switch(leftIndex){
case 0:
*addrp++ = piQxelXor[0];
*addrp++ = piQxelXor[1];
*addrp = ((*addrp) & 0xFFFFFF00) | (piQxelXor[2] & 0xFF);
break;
case 1:
*addrp = ((*addrp) & 0xFFFFFF) | (piQxelXor[0] & 0xFF000000);
addrp++;
*addrp = piQxelXor[1];
addrp++;
*addrp = ((*addrp) & 0xFFFFFF00) | (piQxelXor[2] & 0xFF);
break;
case 2:
*addrp = ((*addrp) & 0xFFFF) | (piQxelXor[1] & 0xFFFF0000);
addrp++;
*addrp = ((*addrp) & 0xFFFFFF00) | (piQxelXor[2] & 0xFF);
break;
}
break;
case 2:
switch(leftIndex){
case 1:
*addrp = ((*addrp) & 0xFFFFFF) | (piQxelXor[0] & 0xFF000000);
addrp++;
*addrp = ((*addrp) & 0xFFFF0000) | (piQxelXor[1] & 0xFFFF);
break;
case 0:
*addrp++ = piQxelXor[0];
*addrp = ((*addrp) & 0xFFFF0000) | (piQxelXor[1] & 0xFFFF);
break;
}
break;
case 1:
if(x1_or_len){
*addrp = ((*addrp) & 0xFF000000) | (piQxelXor[0] & 0xFFFFFF);
}
break;
case 0:
break;
default:
{
switch(leftIndex){
case 0:
break;
case 1:
*addrp = ((*addrp) & 0xFFFFFF) | (piQxelXor[0] & 0xFF000000);
addrp++;
*addrp = piQxelXor[1];
addrp++;
*addrp = piQxelXor[2];
addrp++;
break;
case 2:
*addrp = ((*addrp) & 0xFFFF) | (piQxelXor[1] & 0xFFFF0000);
addrp++;
*addrp = piQxelXor[2];
addrp++;
break;
case 3:
*addrp = ((*addrp) & 0xFF) | (piQxelXor[2] & 0xFFFFFF00);
addrp++;
break;
}
while(nlmiddle--){
*addrp++ = piQxelXor[0];
*addrp++ = piQxelXor[1];
*addrp++ = piQxelXor[2];
}
switch(rightIndex++){
case 0:
break;
case 1:
*addrp = ((*addrp) & 0xFF000000) | (piQxelXor[0] & 0xFFFFFF);
break;
case 2:
*addrp++ = piQxelXor[0];
*addrp = ((*addrp) & 0xFFFF0000) | (piQxelXor[1] & 0xFFFF);
break;
case 3:
*addrp++ = piQxelXor[0];
*addrp++ = piQxelXor[1];
*addrp = ((*addrp) & 0xFFFFFF00) | (piQxelXor[2] & 0xFF);
break;
}
}
}
#else
addrp = (PixelType *)((char *)addrLineEnd + ((xOffset * 3) & ~0x03));
if (x1_or_len <= 1){
if (x1_or_len)
RROP_SOLID24(addrp, xOffset);
} else {
maskbits(xOffset, x1_or_len, e, e3, x1_or_len);
pidx = xOffset & 3;
if (e){
RROP_SOLID_MASK(addrp, e, pidx-1);
addrp++;
if (pidx == 3)
pidx = 0;
}
while (--x1_or_len >= 0){
RROP_SOLID(addrp, pidx);
addrp++;
if (++pidx == 3)
pidx = 0;
}
if (e3)
RROP_SOLID_MASK(addrp, e3, pidx);
}
#endif
}
#else
if (y1_or_e1 + x1_or_len <= PPW)
{
if (x1_or_len)
{
maskpartialbits(y1_or_e1, x1_or_len, e)
RROP_SOLID_MASK((CfbBits *) addrp, e);
}
}
else
{
maskbits(y1_or_e1, x1_or_len, e, e3, x1_or_len)
if (e)
{
RROP_SOLID_MASK((CfbBits *) addrp, e);
addrp += PPW;
}
RROP_SPAN(addrp, x1_or_len)
if (e3)
RROP_SOLID_MASK((CfbBits *) addrp, e3);
}
#endif
}
#endif
}
#ifdef POLYSEGMENT
if (nseg >= 0)
return (xSegment *) ppt - pSegInit;
#else
if (npt)
{
#ifdef EITHER_MODE
if (!mode)
#endif
#ifndef ORIGIN
{
*x1p = _x1;
*y1p = _y1;
*x2p = _x2;
*y2p = _y2;
}
#endif
return ((DDXPointPtr) ppt - pptInit) - 1;
}
# ifndef ORIGIN
# define C2 c2
# else
# define C2 ppt[-1]
# endif
#ifdef EITHER_MODE
if (pGC->capStyle != CapNotLast &&
((mode ? (C2 != *((int *) pptInitOrig))
: ((_x2 != pptInitOrig->x) ||
(_y2 != pptInitOrig->y)))
|| (ppt == ((int *)pptInitOrig) + 2)))
#endif
#ifdef PREVIOUS
if (pGC->capStyle != CapNotLast &&
((_x2 != pptInitOrig->x) ||
(_y2 != pptInitOrig->y) ||
(ppt == ((int *)pptInitOrig) + 2)))
#endif
#ifdef ORIGIN
if (pGC->capStyle != CapNotLast &&
((C2 != *((int *) pptInitOrig)) ||
(ppt == ((int *)pptInitOrig) + 2)))
#endif
{
# ifdef REARRANGE
RROP_DECLARE
RROP_FETCH_GCPRIV(devPriv);
# endif
#if PSZ == 24
#if RROP == GXcopy
switch(xOffset & 3){
case 0:
*addrp = ((*addrp)&0xFF000000)|(piQxelXor[0] & 0xFFFFFF);
break;
case 3:
*addrp = ((*addrp)&0xFF)|(piQxelXor[2] & 0xFFFFFF00);
break;
case 1:
*addrp = ((*addrp)&0xFFFFFF)|(piQxelXor[0] & 0xFF000000);
*(addrp+1) = ((*(addrp+1))&0xFFFF0000)|(piQxelXor[1] & 0xFFFF);
break;
case 2:
*addrp = ((*addrp)&0xFFFF)|(piQxelXor[1] & 0xFFFF0000);
*(addrp+1) = ((*(addrp+1))&0xFFFFFF00)|(piQxelXor[2] & 0xFF);
break;
}
#endif
#if RROP == GXxor
switch(xOffset & 3){
case 0:
*addrp ^= (piQxelXor[0] & 0xFFFFFF);
break;
case 3:
*addrp ^= (piQxelXor[2] & 0xFFFFFF00);
break;
case 1:
*addrp ^= (piQxelXor[0] & 0xFF000000);
*(addrp+1) ^= (piQxelXor[1] & 0xFFFF);
break;
case 2:
*addrp ^= (piQxelXor[1] & 0xFFFF0000);
*(addrp+1) ^= (piQxelXor[2] & 0xFF);
break;
}
#endif
#if RROP == GXand
switch(xOffset & 3){
case 0:
*addrp &= (piQxelAnd[0] | 0xFF000000);
break;
case 3:
*addrp &= (piQxelAnd[2] | 0xFF);
break;
case 1:
*addrp &= (0xFFFFFF|piQxelAnd[0]);
*(addrp+1) &= (0xFFFF0000|piQxelAnd[1]);
break;
case 2:
*addrp &= (0xFFFF|piQxelAnd[1]);
*(addrp+1) &= (0xFFFFFF00|piQxelAnd[2]);
break;
}
#endif
#if RROP == GXor
switch(xOffset & 3){
case 0:
*addrp |= (piQxelOr[0] & 0xFFFFFF);
break;
case 3:
*addrp |= (piQxelOr[2] & 0xFFFFFF00);
break;
case 1:
*addrp |= (piQxelOr[0] & 0xFF000000);
*(addrp+1) |= (piQxelOr[1] & 0xFFFF);
break;
case 2:
*addrp |= (piQxelOr[1] & 0xFFFF0000);
*(addrp+1) |= (piQxelOr[2] & 0xFF);
break;
}
#endif
#if RROP == GXset
switch(xOffset & 3){
case 0:
*addrp = (((*addrp)&(piQxelAnd[0] |0xFF000000))^(piQxelXor[0] & 0xFFFFFF));
break;
case 3:
*addrp = (((*addrp)&(piQxelAnd[2]|0xFF))^(piQxelXor[2] & 0xFFFFFF00));
break;
case 1:
*addrp = (((*addrp)&(piQxelAnd[0]|0xFFFFFF))^(piQxelXor[0] & 0xFF000000));
*(addrp+1) = (((*(addrp+1))&(piQxelAnd[1]|0xFFFF0000))^(piQxelXor[1] & 0xFFFF));
break;
case 2:
*addrp = (((*addrp)&(piQxelAnd[1]|0xFFFF))^(piQxelXor[1] & 0xFFFF0000));
*(addrp+1) = (((*(addrp+1))&(piQxelAnd[2]|0xFFFFFF00))^(piQxelXor[2] & 0xFF));
break;
}
#endif
#else
RROP_SOLID (addrp);
# endif
}
#endif
RROP_UNDECLARE;
return -1;
}
#endif
#ifdef INCLUDE_OTHERS
#ifdef POLYSEGMENT
void
cfb8SegmentSS1Rect (pDrawable, pGC, nseg, pSegInit)
DrawablePtr pDrawable;
GCPtr pGC;
int nseg;
xSegment *pSegInit;
{
int (*func)(DrawablePtr, GCPtr, int, xSegment *);
void (*clip)(DrawablePtr, GCPtr, int, int, int, int, BoxPtr, Bool);
int drawn;
cfbPrivGCPtr devPriv;
#if defined(__arm32__) && PSZ != 8
cfbSegmentSS(pDrawable, pGC, nseg, pSegInit);
return;
#endif
devPriv = cfbGetGCPrivate(pGC);
#ifdef NO_ONE_RECT
if (REGION_NUM_RECTS(pGC->pCompositeClip) != 1)
{
cfbSegmentSS(pDrawable, pGC, nseg, pSegInit);
return;
}
#endif
switch (devPriv->rop)
{
case GXcopy:
func = cfb8SegmentSS1RectCopy;
clip = cfb8ClippedLineCopy;
#ifdef FAST_MUL
if (cfbGetPixelWidth (pDrawable) == WIDTH_FAST)
func = cfb8SegmentSS1RectShiftCopy;
#endif
break;
case GXxor:
func = cfb8SegmentSS1RectXor;
clip = cfb8ClippedLineXor;
break;
default:
func = cfb8SegmentSS1RectGeneral;
clip = cfb8ClippedLineGeneral;
break;
}
while (nseg)
{
drawn = (*func) (pDrawable, pGC, nseg, pSegInit);
if (drawn == -1)
break;
(*clip) (pDrawable, pGC,
pSegInit[drawn-1].x1, pSegInit[drawn-1].y1,
pSegInit[drawn-1].x2, pSegInit[drawn-1].y2,
&pGC->pCompositeClip->extents,
pGC->capStyle == CapNotLast);
pSegInit += drawn;
nseg -= drawn;
}
}
#else
void
cfb8LineSS1Rect (pDrawable, pGC, mode, npt, pptInit)
DrawablePtr pDrawable;
GCPtr pGC;
int mode;
int npt;
DDXPointPtr pptInit;
{
int (*func)(DrawablePtr, GCPtr, int, int,
DDXPointPtr, DDXPointPtr,
int *, int *, int *, int *);
void (*clip)(DrawablePtr, GCPtr, int, int, int, int, BoxPtr, Bool);
int drawn;
cfbPrivGCPtr devPriv;
int x1, y1, x2, y2;
DDXPointPtr pptInitOrig = pptInit;
#if defined(__arm32__) && PSZ != 8
cfbLineSS(pDrawable, pGC, mode, npt, pptInit);
return;
#endif
devPriv = cfbGetGCPrivate(pGC);
#ifdef NO_ONE_RECT
if (REGION_NUM_RECTS(pGC->pCompositeClip) != 1)
{
cfbLineSS(pDrawable, pGC, mode, npt, pptInit);
return;
}
#endif
switch (devPriv->rop)
{
case GXcopy:
func = cfb8LineSS1RectCopy;
clip = cfb8ClippedLineCopy;
if (mode == CoordModePrevious)
func = cfb8LineSS1RectPreviousCopy;
break;
case GXxor:
func = cfb8LineSS1RectXor;
clip = cfb8ClippedLineXor;
break;
default:
func = cfb8LineSS1RectGeneral;
clip = cfb8ClippedLineGeneral;
break;
}
if (mode == CoordModePrevious)
{
x1 = pptInit->x;
y1 = pptInit->y;
while (npt > 1)
{
drawn = (*func) (pDrawable, pGC, mode, npt, pptInit, pptInitOrig,
&x1, &y1, &x2, &y2);
if (drawn == -1)
break;
(*clip) (pDrawable, pGC, x1, y1, x2, y2,
&pGC->pCompositeClip->extents,
drawn != npt - 1 || pGC->capStyle == CapNotLast);
pptInit += drawn;
npt -= drawn;
x1 = x2;
y1 = y2;
}
}
else
{
while (npt > 1)
{
drawn = (*func) (pDrawable, pGC, mode, npt, pptInit, pptInitOrig,
&x1, &y1, &x2, &y2);
if (drawn == -1)
break;
(*clip) (pDrawable, pGC,
pptInit[drawn-1].x, pptInit[drawn-1].y,
pptInit[drawn].x, pptInit[drawn].y,
&pGC->pCompositeClip->extents,
drawn != npt - 1 || pGC->capStyle == CapNotLast);
pptInit += drawn;
npt -= drawn;
}
}
}
#endif
#endif
#if !defined(POLYSEGMENT) && !defined (PREVIOUS)
void
RROP_NAME (cfb8ClippedLine) (pDrawable, pGC, x1, y1, x2, y2, boxp, shorten)
DrawablePtr pDrawable;
GCPtr pGC;
int x1, y1, x2, y2;
BoxPtr boxp;
Bool shorten;
{
int oc1, oc2;
int e, e1, e3, len;
int adx, ady;
PixelType *addr;
int nwidth;
int stepx, stepy;
int xorg, yorg;
int new_x1, new_y1, new_x2, new_y2;
Bool pt1_clipped, pt2_clipped;
int changex, changey, result;
#if PSZ == 24
PixelType *addrLineEnd;
char *addrb;
int stepx3, stepy3;
#endif
int octant;
unsigned int bias = miGetZeroLineBias(pDrawable->pScreen);
cfbGetPixelWidthAndPointer(pDrawable, nwidth, addr);
xorg = pDrawable->x;
yorg = pDrawable->y;
x1 += xorg;
y1 += yorg;
x2 += xorg;
y2 += yorg;
oc1 = 0;
oc2 = 0;
OUTCODES (oc1, x1, y1, boxp);
OUTCODES (oc2, x2, y2, boxp);
if (oc1 & oc2)
return;
CalcLineDeltas(x1, y1, x2, y2, adx, ady, stepx, stepy, 1, nwidth, octant);
if (adx <= ady)
{
int t;
t = adx;
adx = ady;
ady = t;
t = stepx;
stepx = stepy;
stepy = t;
SetYMajorOctant(octant);
}
e = - adx;
e1 = ady << 1;
e3 = - (adx << 1);
FIXUP_ERROR(e, octant, bias);
new_x1 = x1;
new_y1 = y1;
new_x2 = x2;
new_y2 = y2;
pt1_clipped = 0;
pt2_clipped = 0;
if (IsXMajorOctant(octant))
{
result = miZeroClipLine(boxp->x1, boxp->y1, boxp->x2 - 1, boxp->y2 - 1,
&new_x1, &new_y1, &new_x2, &new_y2,
adx, ady,
&pt1_clipped, &pt2_clipped,
octant, bias, oc1, oc2);
if (result == -1)
return;
len = abs(new_x2 - new_x1) - 1;
if (pt2_clipped || !shorten)
len++;
if (pt1_clipped)
{
changex = abs(new_x1 - x1);
changey = abs(new_y1 - y1);
e = e + changey * e3 + changex * e1;
}
}
else
{
result = miZeroClipLine(boxp->x1, boxp->y1, boxp->x2 - 1, boxp->y2 - 1,
&new_x1, &new_y1, &new_x2, &new_y2,
ady, adx,
&pt1_clipped, &pt2_clipped,
octant, bias, oc1, oc2);
if (result == -1)
return;
len = abs(new_y2 - new_y1) - 1;
if (pt2_clipped || !shorten)
len++;
if (pt1_clipped)
{
changex = abs(new_x1 - x1);
changey = abs(new_y1 - y1);
e = e + changex * e3 + changey * e1;
}
}
x1 = new_x1;
y1 = new_y1;
{
register PixelType *addrp;
RROP_DECLARE
RROP_FETCH_GC(pGC);
#if PSZ == 24
addrLineEnd = addr + (y1 * nwidth);
addrb = (char *)addrLineEnd + x1 * 3;
if (stepx == 1 || stepx == -1){
stepx3 = stepx * 3;
stepy3 = stepy * sizeof (CfbBits);
} else {
stepx3 = stepx * sizeof (CfbBits);
stepy3 = stepy * 3;
}
#else
addrp = addr + (y1 * nwidth) + x1;
#endif
#ifndef REARRANGE
if (!ady)
{
#if PSZ == 24
#define body {\
body_rop \
addrb += stepx3; \
}
#else
#define body { RROP_SOLID(addrp); addrp += stepx; }
#endif
while (len >= PGSZB)
{
body body body body
#if PGSZ == 64
body body body body
#endif
len -= PGSZB;
}
switch (len)
{
#if PGSZ == 64
case 7: body case 6: body case 5: body case 4: body
#endif
case 3: body case 2: body case 1: body
}
#undef body
}
else
#endif
{
#if PSZ == 24
#define body {\
body_rop \
addrb += stepx3; \
e += e1; \
if (e >= 0) \
{ \
addrb += stepy3; \
e += e3; \
} \
}
#else
#define body {\
RROP_SOLID(addrp); \
addrp += stepx; \
e += e1; \
if (e >= 0) \
{ \
addrp += stepy; \
e += e3; \
} \
}
#endif
#ifdef LARGE_INSTRUCTION_CACHE
while ((len -= PGSZB) >= 0)
{
body body body body
#if PGSZ == 64
body body body body
#endif
}
switch (len)
{
case -1: body case -2: body case -3: body
#if PGSZ == 64
case -4: body case -5: body case -6: body case -7: body
#endif
}
#else
IMPORTANT_START;
while ((len -= 2) >= 0)
{
body body;
}
if (len & 1)
body;
IMPORTANT_END;
#endif
}
#if PSZ == 24
body_rop
#else
RROP_SOLID(addrp);
#endif
#undef body
RROP_UNDECLARE
}
}
#endif
#endif