Annotation of researchv9/X11/src/X.V11R1/server/ddx/cfb/cfbfillsp.c, revision 1.1

1.1     ! root        1: /************************************************************
        !             2: Copyright 1987 by Sun Microsystems, Inc. Mountain View, CA.
        !             3: 
        !             4:                     All Rights Reserved
        !             5: 
        !             6: Permission  to  use,  copy,  modify,  and  distribute   this
        !             7: software  and  its documentation for any purpose and without
        !             8: fee is hereby granted, provided that the above copyright no-
        !             9: tice  appear  in all copies and that both that copyright no-
        !            10: tice and this permission notice appear in  supporting  docu-
        !            11: mentation,  and  that the names of Sun or MIT not be used in
        !            12: advertising or publicity pertaining to distribution  of  the
        !            13: software  without specific prior written permission. Sun and
        !            14: M.I.T. make no representations about the suitability of this
        !            15: software for any purpose. It is provided "as is" without any
        !            16: express or implied warranty.
        !            17: 
        !            18: SUN DISCLAIMS ALL WARRANTIES WITH REGARD TO  THIS  SOFTWARE,
        !            19: INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FIT-
        !            20: NESS FOR A PARTICULAR PURPOSE. IN NO EVENT SHALL SUN BE  LI-
        !            21: ABLE  FOR  ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
        !            22: ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,  DATA  OR
        !            23: PROFITS,  WHETHER  IN  AN  ACTION OF CONTRACT, NEGLIGENCE OR
        !            24: OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION  WITH
        !            25: THE USE OR PERFORMANCE OF THIS SOFTWARE.
        !            26: 
        !            27: ********************************************************/
        !            28: 
        !            29: /***********************************************************
        !            30: Copyright 1987 by Digital Equipment Corporation, Maynard, Massachusetts,
        !            31: and the Massachusetts Institute of Technology, Cambridge, Massachusetts.
        !            32: 
        !            33:                         All Rights Reserved
        !            34: 
        !            35: Permission to use, copy, modify, and distribute this software and its 
        !            36: documentation for any purpose and without fee is hereby granted, 
        !            37: provided that the above copyright notice appear in all copies and that
        !            38: both that copyright notice and this permission notice appear in 
        !            39: supporting documentation, and that the names of Digital or MIT not be
        !            40: used in advertising or publicity pertaining to distribution of the
        !            41: software without specific, written prior permission.  
        !            42: 
        !            43: DIGITAL DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
        !            44: ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
        !            45: DIGITAL BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
        !            46: ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
        !            47: WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
        !            48: ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
        !            49: SOFTWARE.
        !            50: 
        !            51: ******************************************************************/
        !            52: #include "X.h"
        !            53: #include "Xmd.h"
        !            54: #include "servermd.h"
        !            55: #include "gcstruct.h"
        !            56: #include "window.h"
        !            57: #include "pixmapstr.h"
        !            58: #include "scrnintstr.h"
        !            59: 
        !            60: #include "cfb.h"
        !            61: #include "cfbmskbits.h"
        !            62: 
        !            63: /* scanline filling for color frame buffer
        !            64:    written by drewry, oct 1986 modified by smarks
        !            65:    changes for compatibility with Little-endian systems Jul 1987; MIT:yba.
        !            66: 
        !            67:    these routines all clip.  they assume that anything that has called
        !            68: them has already translated the points (i.e. pGC->miTranslate is
        !            69: non-zero, which is howit gets set in cfbCreateGC().)
        !            70: 
        !            71:    the number of new scnalines created by clipping ==
        !            72: MaxRectsPerBand * nSpans.
        !            73: 
        !            74:     FillSolid is overloaded to be used for OpaqueStipple as well,
        !            75: if fgPixel == bgPixel.  
        !            76: Note that for solids, PrivGC.rop == PrivGC.ropOpStip
        !            77: 
        !            78: 
        !            79:     FillTiled is overloaded to be used for OpaqueStipple, if
        !            80: fgPixel != bgPixel.  based on the fill style, it uses
        !            81: {RotatedTile, gc.alu} or {RotatedStipple, PrivGC.ropOpStip}
        !            82: */
        !            83: 
        !            84: #ifdef notdef
        !            85: #include       <stdio.h>
        !            86: static
        !            87: dumpspans(n, ppt, pwidth)
        !            88:     int        n;
        !            89:     DDXPointPtr ppt;
        !            90:     int *pwidth;
        !            91: {
        !            92:     fprintf(stderr,"%d spans\n", n);
        !            93:     while (n--) {
        !            94:        fprintf(stderr, "[%d,%d] %d\n", ppt->x, ppt->y, *pwidth);
        !            95:        ppt++;
        !            96:        pwidth++;
        !            97:     }
        !            98:     fprintf(stderr, "\n");
        !            99: }
        !           100: #endif
        !           101: 
        !           102: void
        !           103: cfbSolidFS(pDrawable, pGC, nInit, pptInit, pwidthInit, fSorted)
        !           104:     DrawablePtr pDrawable;
        !           105:     GCPtr      pGC;
        !           106:     int                nInit;                  /* number of spans to fill */
        !           107:     DDXPointPtr pptInit;               /* pointer to list of start points */
        !           108:     int                *pwidthInit;            /* pointer to list of n widths */
        !           109:     int        fSorted;
        !           110: {
        !           111:                                /* next three parameters are post-clip */
        !           112:     int n;                     /* number of spans to fill */
        !           113:     register DDXPointPtr ppt;  /* pointer to list of start points */
        !           114:     register int *pwidth;      /* pointer to list of n widths */
        !           115:     int *addrlBase;            /* pointer to start of bitmap */
        !           116:     int nlwidth;               /* width in longwords of bitmap */
        !           117:     register int *addrl;       /* pointer to current longword in bitmap */
        !           118:     register int startmask;
        !           119:     register int endmask;
        !           120:     register int nlmiddle;
        !           121:     int rop;                   /* reduced rasterop */
        !           122:     int *pwidthFree;           /* copies of the pointers to free */
        !           123:     DDXPointPtr pptFree;
        !           124:     int fill, rrop;
        !           125: 
        !           126:     switch (pDrawable->depth) {
        !           127:        case 1:
        !           128:            rrop = ReduceRop( pGC->alu, pGC->fgPixel );
        !           129:            switch ( rrop ) {
        !           130:                case RROP_BLACK:
        !           131:                    mfbBlackSolidFS(pDrawable, pGC, nInit, pptInit, 
        !           132:                        pwidthInit, fSorted);
        !           133:                    break;
        !           134:                case RROP_WHITE:
        !           135:                    mfbWhiteSolidFS(pDrawable, pGC, nInit, pptInit, 
        !           136:                        pwidthInit, fSorted);
        !           137:                    break;
        !           138:                case RROP_NOP:
        !           139:                    return;
        !           140:                case RROP_INVERT:
        !           141:                    mfbInvertSolidFS(pDrawable, pGC, nInit, pptInit, 
        !           142:                        pwidthInit, fSorted);
        !           143:                    break;
        !           144:            }
        !           145:            return;
        !           146:        case 8:
        !           147:            break;
        !           148:        default:
        !           149:            FatalError("cfbSolidFS: invalid depth\n");
        !           150:     }
        !           151: 
        !           152:     if (!(pGC->planemask))
        !           153:        return;
        !           154: 
        !           155:     n = nInit * miFindMaxBand(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip);
        !           156:     pwidth = (int *)ALLOCATE_LOCAL(n * sizeof(int));
        !           157:     ppt = (DDXPointRec *)ALLOCATE_LOCAL(n * sizeof(DDXPointRec));
        !           158:     if(!ppt || !pwidth)
        !           159:     {
        !           160:        DEALLOCATE_LOCAL(ppt);
        !           161:        DEALLOCATE_LOCAL(pwidth);
        !           162:        return;
        !           163:     }
        !           164: #ifdef notdef
        !           165:     dumpspans(n, pptInit, pwidthInit);
        !           166: #endif
        !           167:     pwidthFree = pwidth;
        !           168:     pptFree = ppt;
        !           169:     n = miClipSpans(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip,
        !           170:                     pptInit, pwidthInit, nInit,
        !           171:                     ppt, pwidth, fSorted);
        !           172: 
        !           173: #ifdef notdef
        !           174:     dumpspans(n, ppt, pwidth);
        !           175: #endif
        !           176:     if (pDrawable->type == DRAWABLE_WINDOW)
        !           177:     {
        !           178:        addrlBase = (int *)
        !           179:                (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devPrivate);
        !           180:        nlwidth = (int)
        !           181:                  (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devKind) >> 2;
        !           182:     }
        !           183:     else
        !           184:     {
        !           185:        addrlBase = (int *)(((PixmapPtr)pDrawable)->devPrivate);
        !           186:        nlwidth = (int)(((PixmapPtr)pDrawable)->devKind) >> 2;
        !           187:     }
        !           188: 
        !           189:     rop = pGC->alu;
        !           190:     fill = PFILL(pGC->fgPixel);
        !           191: 
        !           192:     while (n--)
        !           193:     {
        !           194:         addrl = addrlBase + (ppt->y * nlwidth) + (ppt->x >> PWSH);
        !           195: 
        !           196:        if (*pwidth)
        !           197:        {
        !           198:            if ( ((ppt->x & PIM) + *pwidth) <= PPW)
        !           199:            {
        !           200:                /* all bits inside same longword */
        !           201:                putbitsrop( fill, ppt->x & PIM, *pwidth,
        !           202:                    addrl, pGC->planemask, rop );
        !           203:            }
        !           204:            else
        !           205:            {
        !           206:                maskbits(ppt->x, *pwidth, startmask, endmask, nlmiddle);
        !           207:                if ( startmask ) {
        !           208:                    putbitsrop( fill, ppt->x & PIM,
        !           209:                        PPW-(ppt->x&PIM), addrl, pGC->planemask, rop);
        !           210:                    ++addrl;
        !           211:                }
        !           212:                while ( nlmiddle-- ) {
        !           213:                    putbitsrop( fill, 0, PPW,
        !           214:                        addrl, pGC->planemask, rop );
        !           215:                    ++addrl;
        !           216:                }
        !           217:                if ( endmask ) {
        !           218:                    putbitsrop( fill, 0, 
        !           219:                        ((ppt->x + *pwidth)&PIM), addrl, pGC->planemask, rop );
        !           220:                }
        !           221:            }
        !           222:        }
        !           223:        pwidth++;
        !           224:        ppt++;
        !           225:     }
        !           226:     DEALLOCATE_LOCAL(pptFree);
        !           227:     DEALLOCATE_LOCAL(pwidthFree);
        !           228: }
        !           229: 
        !           230: 
        !           231: /* Fill spans with tiles that aren't 32 bits wide */
        !           232: void
        !           233: cfbUnnaturalTileFS(pDrawable, pGC, nInit, pptInit, pwidthInit, fSorted)
        !           234: DrawablePtr pDrawable;
        !           235: GC             *pGC;
        !           236: int            nInit;          /* number of spans to fill */
        !           237: DDXPointPtr pptInit;           /* pointer to list of start points */
        !           238: int *pwidthInit;               /* pointer to list of n widths */
        !           239: int fSorted;
        !           240: {
        !           241:     int                iline;          /* first line of tile to use */
        !           242:                                /* next three parameters are post-clip */
        !           243:     int n;                     /* number of spans to fill */
        !           244:     register DDXPointPtr ppt;  /* pointer to list of start points */
        !           245:     register int *pwidth;      /* pointer to list of n widths */
        !           246:     int                *addrlBase;     /* pointer to start of bitmap */
        !           247:     int                 nlwidth;       /* width in longwords of bitmap */
        !           248:     register int *pdst;                /* pointer to current word in bitmap */
        !           249:     register int *psrc;                /* pointer to current word in tile */
        !           250:     register int startmask;
        !           251:     register int nlMiddle;
        !           252:     PixmapPtr  pTile;          /* pointer to tile we want to fill with */
        !           253:     int                w, width, x, tmpSrc, srcStartOver, nstart, nend;
        !           254:     int        endmask, tlwidth, rem, tileWidth, *psrcT, rop;
        !           255:     int *pwidthFree;           /* copies of the pointers to free */
        !           256:     DDXPointPtr pptFree;
        !           257: 
        !           258:     switch (pDrawable->depth) {
        !           259:        case 1:
        !           260:            mfbUnnaturalTileFS(pDrawable, pGC, nInit, pptInit, pwidthInit, fSorted);
        !           261:            return;
        !           262:        case 8:
        !           263:            break;
        !           264:        default:
        !           265:            FatalError("cfbUnnaturalTileFS: invalid depth\n");
        !           266:     }
        !           267: 
        !           268:     if (!(pGC->planemask))
        !           269:        return;
        !           270: 
        !           271:     n = nInit * miFindMaxBand(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip);
        !           272:     pwidth = (int *)ALLOCATE_LOCAL(n * sizeof(int));
        !           273:     ppt = (DDXPointRec *)ALLOCATE_LOCAL(n * sizeof(DDXPointRec));
        !           274:     if(!ppt || !pwidth)
        !           275:     {
        !           276:        DEALLOCATE_LOCAL(ppt);
        !           277:        DEALLOCATE_LOCAL(pwidth);
        !           278:        return;
        !           279:     }
        !           280:     pwidthFree = pwidth;
        !           281:     pptFree = ppt;
        !           282:     n = miClipSpans(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip,
        !           283:                     pptInit, pwidthInit, nInit, 
        !           284:                     ppt, pwidth, fSorted);
        !           285: 
        !           286:     if (pGC->fillStyle == FillTiled)
        !           287:     {
        !           288:        pTile = ((cfbPrivGC *)(pGC->devPriv))->pRotatedTile;
        !           289:        tlwidth = pTile->devKind >> 2;
        !           290:        rop = pGC->alu;
        !           291:     }
        !           292:     else
        !           293:     {
        !           294:        pTile = ((cfbPrivGC *)(pGC->devPriv))->pRotatedStipple;
        !           295:        tlwidth = pTile->devKind >> 2;
        !           296:        rop = pGC->alu;
        !           297:     }
        !           298: 
        !           299:     if (pDrawable->type == DRAWABLE_WINDOW)
        !           300:     {
        !           301:        addrlBase = (int *)
        !           302:                (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devPrivate);
        !           303:        nlwidth = (int)
        !           304:                  (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devKind) >> 2;
        !           305:     }
        !           306:     else
        !           307:     {
        !           308:        addrlBase = (int *)(((PixmapPtr)pDrawable)->devPrivate);
        !           309:        nlwidth = (int)(((PixmapPtr)pDrawable)->devKind) >> 2;
        !           310:     }
        !           311: 
        !           312:     tileWidth = pTile->width;
        !           313:     while (n--)
        !           314:     {
        !           315:        iline = ppt->y % pTile->height;
        !           316:         pdst = addrlBase + (ppt->y * nlwidth) + (ppt->x >> PWSH);
        !           317:         psrcT = (int *) pTile->devPrivate + (iline * tlwidth);
        !           318:        x = ppt->x;
        !           319: 
        !           320:        if (*pwidth)
        !           321:        {
        !           322:            width = *pwidth;
        !           323:            while(width > 0)
        !           324:            {
        !           325:                rem = x % tileWidth;
        !           326:                psrc = psrcT + rem / PPW;
        !           327:                w = min(tileWidth, width);
        !           328:                w = min(w,tileWidth-rem);
        !           329: #ifdef notdef
        !           330:                if((rem = x % tileWidth) != 0)
        !           331:                {
        !           332:                    w = min(min(tileWidth - rem, width), PPW);
        !           333:                    /* we want to grab from the end of the tile.  Figure
        !           334:                     * out where that is.  In general, the start of the last
        !           335:                     * word of data on this scanline is tlwidth -1 words 
        !           336:                     * away. But if we want to grab more bits than we'll
        !           337:                     * find on that line, we have to back up 1 word further.
        !           338:                     * On the other hand, if the whole tile fits in 1 word,
        !           339:                     * let's skip the work */ 
        !           340:                    endinc = tlwidth - 1 - (tileWidth-rem) / PPW;
        !           341: 
        !           342:                    if(endinc)
        !           343:                    {
        !           344:                        if((rem & PIM) + w > tileWidth % PPW)
        !           345:                            endinc--;
        !           346:                    }
        !           347: 
        !           348:                    getbits(psrc + endinc, rem & PIM, w, tmpSrc);
        !           349:                    putbitsrop(tmpSrc, (x & PIM), w, pdst, 
        !           350:                        pGC->planemask, rop);
        !           351:                    if((x & PIM) + w >= PPW)
        !           352:                        pdst++;
        !           353:                }
        !           354:                else
        !           355: #endif notdef
        !           356:                if(((rem & PIM) + w) <= PPW)
        !           357:                {
        !           358:                    getbits(psrc, (rem & PIM), w, tmpSrc);
        !           359:                    putbitsrop(tmpSrc, x & PIM, w, pdst, 
        !           360:                        pGC->planemask, rop);
        !           361:                    ++pdst;
        !           362:                }
        !           363:                else
        !           364:                {
        !           365:                    maskbits(x, w, startmask, endmask, nlMiddle);
        !           366: 
        !           367:                    if (startmask)
        !           368:                        nstart = PPW - (x & PIM);
        !           369:                    else
        !           370:                        nstart = 0;
        !           371:                    if (endmask)
        !           372:                        nend = (x + w)  & PIM;
        !           373:                    else
        !           374:                        nend = 0;
        !           375: 
        !           376:                    srcStartOver = nstart > PLST;
        !           377: 
        !           378:                    if(startmask)
        !           379:                    {
        !           380:                        getbits(psrc, rem & PIM, nstart, tmpSrc);
        !           381:                        putbitsrop(tmpSrc, x & PIM, nstart, pdst, 
        !           382:                            pGC->planemask, rop);
        !           383:                        pdst++;
        !           384:                        psrc++;
        !           385:                    }
        !           386:                     
        !           387:                    while(nlMiddle--)
        !           388:                    {
        !           389:                            getbits(psrc, 0, PPW, tmpSrc);
        !           390:                            putbitsrop( tmpSrc, 0, PPW,
        !           391:                                pdst, pGC->planemask, rop );
        !           392:                            pdst++;
        !           393:                            psrc++;
        !           394:                    }
        !           395:                    if(endmask)
        !           396:                    {
        !           397:                        getbits(psrc, 0, nend, tmpSrc);
        !           398:                        putbitsrop(tmpSrc, 0, nend, pdst, 
        !           399:                            pGC->planemask, rop);
        !           400:                    }
        !           401:                 }
        !           402:                 x += w;
        !           403:                 width -= w;
        !           404:            }
        !           405:        }
        !           406:        ppt++;
        !           407:        pwidth++;
        !           408:     }
        !           409:     DEALLOCATE_LOCAL(pptFree);
        !           410:     DEALLOCATE_LOCAL(pwidthFree);
        !           411: }
        !           412: 
        !           413: 
        !           414: /*
        !           415:  * QuartetBitsTable contains four masks whose binary values are masks in the 
        !           416:  * low order quartet that contain the number of bits specified in the 
        !           417:  * index.  This table is used by getstipplepixels.
        !           418:  */
        !           419: static unsigned int QuartetBitsTable[5] = {
        !           420: #if (BITMAP_BIT_ORDER == MSBFirst)
        !           421:     0x00000000,                                /* 0 - 0000 */
        !           422:     0x00000008,                                /* 1 - 1000 */
        !           423:     0x0000000C,                                /* 2 - 1100 */
        !           424:     0x0000000E,                                /* 3 - 1110 */
        !           425:     0x0000000F                         /* 4 - 1111 */
        !           426: #else /* (BITMAP_BIT_ORDER == LSBFirst */
        !           427:     0x00000000,                                /* 0 - 0000 */
        !           428:     0x00000001,                                /* 1 - 0001 */
        !           429:     0x00000003,                                /* 2 - 0011 */
        !           430:     0x00000007,                                /* 3 - 0111 */
        !           431:     0x0000000F                         /* 4 - 1111 */
        !           432: #endif (BITMAP_BIT_ORDER == MSBFirst)
        !           433: };
        !           434: 
        !           435: /*
        !           436:  * QuartetPixelMaskTable is used by getstipplepixels to get a pixel mask 
        !           437:  * corresponding to a quartet of bits.
        !           438:  */
        !           439: static unsigned int QuartetPixelMaskTable[16] = {
        !           440:     0x00000000,
        !           441:     0x000000FF,
        !           442:     0x0000FF00,
        !           443:     0x0000FFFF,
        !           444:     0x00FF0000,
        !           445:     0x00FF00FF,
        !           446:     0x00FFFF00,
        !           447:     0x00FFFFFF,
        !           448:     0xFF000000,
        !           449:     0xFF0000FF,
        !           450:     0xFF00FF00,
        !           451:     0xFF00FFFF,
        !           452:     0xFFFF0000,
        !           453:     0xFFFF00FF,
        !           454:     0xFFFFFF00,
        !           455:     0xFFFFFFFF
        !           456: };
        !           457: 
        !           458: 
        !           459: /*
        !           460:  * getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix )
        !           461:  * 
        !           462:  * Converts bits to pixels in a reasonable way.  Takes w (1 <= w <= 4)
        !           463:  * bits from *psrcstip, starting at bit x; call this a quartet of bits.
        !           464:  * Then, takes the pixels from *psrcpix corresponding to the one-bits (if
        !           465:  * ones is TRUE) or the zero-bits (if ones is FALSE) of the quartet
        !           466:  * and puts these pixels into destpix.
        !           467:  *
        !           468:  * Example:
        !           469:  * 
        !           470:  *     getstipplepixels( &(0x08192A3B), 17, 4, 1, &(0x4C5D6E7F), dest )
        !           471:  *
        !           472:  * 0x08192A3B = 0000 1000 0001 1001 0010 1010 0011 1011
        !           473:  *
        !           474:  * This will take 4 bits starting at bit 17, so the quartet is 0x5 = 0101.
        !           475:  * It will take pixels from 0x4C5D6E7F corresponding to the one-bits in this 
        !           476:  * quartet, so dest = 0x005D007F.
        !           477:  *
        !           478:  * XXX This should be turned into a macro after it is debugged.
        !           479:  * XXX Has byte order dependencies.
        !           480:  * XXX This works for all values of x and w within a doubleword, depending
        !           481:  *     on the compiler to generate proper code for negative shifts.
        !           482:  */
        !           483: 
        !           484: void getstipplepixels( psrcstip, x, w, ones, psrcpix, destpix )
        !           485: unsigned int *psrcstip, *psrcpix, *destpix;
        !           486: int x, w, ones;
        !           487: {
        !           488:     unsigned int q;
        !           489: 
        !           490: #if (BITMAP_BIT_ORDER == MSBFirst)
        !           491:     q = ((*psrcstip) >> (28-x)) & 0x0F;
        !           492:     if ( x+w > 32 )
        !           493:        q |= *(psrcstip+1) >> (64-x-w); /* & 0xF ? ****XXX*/
        !           494: #else
        !           495:     q = (*psrcstip) >> x;
        !           496:     if ( x+w > 32 )
        !           497:        q |= *(psrcstip+1) << (32-x);
        !           498:     q &= 0xf;
        !           499: #endif
        !           500:     q = QuartetBitsTable[w] & (ones ? q : ~q);
        !           501:     *destpix = (*(psrcpix)) & QuartetPixelMaskTable[q];
        !           502: }
        !           503:     
        !           504: 
        !           505: /* Fill spans with stipples that aren't 32 bits wide */
        !           506: void
        !           507: cfbUnnaturalStippleFS(pDrawable, pGC, nInit, pptInit, pwidthInit, fSorted)
        !           508: DrawablePtr pDrawable;
        !           509: GC             *pGC;
        !           510: int            nInit;          /* number of spans to fill */
        !           511: DDXPointPtr pptInit;           /* pointer to list of start points */
        !           512: int *pwidthInit;               /* pointer to list of n widths */
        !           513: int fSorted;
        !           514: {
        !           515:                                /* next three parameters are post-clip */
        !           516:     int n;                     /* number of spans to fill */
        !           517:     int xrem; 
        !           518:     register DDXPointPtr ppt;  /* pointer to list of start points */
        !           519:     register int *pwidth;      /* pointer to list of n widths */
        !           520:     int                iline;          /* first line of tile to use */
        !           521:     int                *addrlBase;     /* pointer to start of bitmap */
        !           522:     int                 nlwidth;       /* width in longwords of bitmap */
        !           523:     register int *pdst;                /* pointer to current word in bitmap */
        !           524:     PixmapPtr  pStipple;       /* pointer to stipple we want to fill with */
        !           525:     int                w, width,  x;
        !           526:     unsigned int tmpSrc, tmpDst1, tmpDst2;
        !           527:     int        stwidth, stippleWidth, *psrcS, rop;
        !           528:     int *pwidthFree;           /* copies of the pointers to free */
        !           529:     DDXPointPtr pptFree;
        !           530:     unsigned int fgfill, bgfill;
        !           531: 
        !           532:     switch (pDrawable->depth) {
        !           533:        case 1:
        !           534:            mfbUnnaturalStippleFS(pDrawable, pGC, nInit, pptInit, 
        !           535:                pwidthInit, fSorted);
        !           536:            return;
        !           537:        case 8:
        !           538:            break;
        !           539:        default:
        !           540:            FatalError("cfbUnnaturalStippleFS: invalid depth\n");
        !           541:     }
        !           542: 
        !           543:     if (!(pGC->planemask))
        !           544:        return;
        !           545: 
        !           546:     n = nInit * miFindMaxBand(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip);
        !           547:     pwidth = (int *)ALLOCATE_LOCAL(n * sizeof(int));
        !           548:     ppt = (DDXPointRec *)ALLOCATE_LOCAL(n * sizeof(DDXPointRec));
        !           549:     if(!ppt || !pwidth)
        !           550:     {
        !           551:        DEALLOCATE_LOCAL(ppt);
        !           552:        DEALLOCATE_LOCAL(pwidth);
        !           553:        return;
        !           554:     }
        !           555:     pwidthFree = pwidth;
        !           556:     pptFree = ppt;
        !           557:     n = miClipSpans(((cfbPrivGC *)(pGC->devPriv))->pCompositeClip,
        !           558:                     pptInit, pwidthInit, nInit, 
        !           559:                     ppt, pwidth, fSorted);
        !           560:     rop = ((cfbPrivGC *)(pGC->devPriv))->rop;
        !           561:     fgfill = PFILL(pGC->fgPixel);
        !           562:     bgfill = PFILL(pGC->bgPixel);
        !           563: 
        !           564:     /*
        !           565:      *  OK,  so what's going on here?  We have two Drawables:
        !           566:      *
        !           567:      *  The Stipple:
        !           568:      *         Depth = 1
        !           569:      *         Width = stippleWidth
        !           570:      *         Words per scanline = stwidth
        !           571:      *         Pointer to pixels = pStipple->devPrivate
        !           572:      */
        !           573:     pStipple = ((cfbPrivGC *)(pGC->devPriv))->pRotatedStipple;
        !           574: 
        !           575:     if (pStipple->drawable.depth != 1) {
        !           576:        FatalError( "Stipple depth not equal to 1!\n" );
        !           577:     }
        !           578: 
        !           579:     stwidth = pStipple->devKind >> 2;
        !           580:     stippleWidth = pStipple->width;
        !           581: 
        !           582:     /*
        !           583:      * The Target:
        !           584:      *         Depth = PSZ
        !           585:      *         Width = determined from *pwidth
        !           586:      *         Words per scanline = nlwidth
        !           587:      *         Pointer to pixels = addrlBase
        !           588:      */
        !           589:     if (pDrawable->type == DRAWABLE_WINDOW)
        !           590:     {
        !           591:        addrlBase = (int *)
        !           592:                (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devPrivate);
        !           593:        nlwidth = (int)
        !           594:                (((PixmapPtr)(pDrawable->pScreen->devPrivate))->devKind) >> 2;
        !           595:     }
        !           596:     else
        !           597:     {
        !           598:        addrlBase = (int *)(((PixmapPtr)pDrawable)->devPrivate);
        !           599:        nlwidth = (int)(((PixmapPtr)pDrawable)->devKind) >> 2;
        !           600:     }
        !           601: 
        !           602:     while (n--)
        !           603:     {
        !           604:        iline = ppt->y % pStipple->height;
        !           605:        x = ppt->x;
        !           606:        pdst = addrlBase + (ppt->y * nlwidth);
        !           607:         psrcS = (int *) pStipple->devPrivate + (iline * stwidth);
        !           608: 
        !           609:        if (*pwidth)
        !           610:        {
        !           611:            width = *pwidth;
        !           612:            while(width > 0)
        !           613:            {
        !           614:                /*
        !           615:                 *  Do a stripe through the stipple & destination w pixels
        !           616:                 *  wide.  w is not more than:
        !           617:                 *      -       the width of the destination
        !           618:                 *      -       the width of the stipple
        !           619:                 *      -       the distance between x and the next word 
        !           620:                 *              boundary in the destination
        !           621:                 *      -       the distance between x and the next word
        !           622:                 *              boundary in the stipple
        !           623:                 */
        !           624: 
        !           625:                /* width of dest/stipple */
        !           626:                 xrem = x % stippleWidth;
        !           627:                w = min((stippleWidth - (x % stippleWidth)), width);
        !           628:                /* dist to word bound in dest */
        !           629:                w = min(w, PPW - (x & PIM));
        !           630:                /* dist to word bound in stip */
        !           631:                w = min(w, 32 - (x & 0x1f));
        !           632: 
        !           633:                /* Fill tmpSrc with the source pixels */
        !           634:                tmpSrc = *(pdst + (x >> PWSH));
        !           635:                switch ( pGC->fillStyle ) {
        !           636:                    case FillOpaqueStippled:
        !           637:                        getstipplepixels(psrcS + (xrem>>5), (x&0x1f), w, 0, 
        !           638:                            &bgfill, &tmpDst1);
        !           639:                        getstipplepixels(psrcS + (xrem>>5), (x&0x1f), w, 1,
        !           640:                            &fgfill, &tmpDst2);
        !           641:                        break;
        !           642:                    case FillStippled:
        !           643:                        getstipplepixels(psrcS + (xrem>>5), (x&0x1f), w, 0,
        !           644:                            &tmpSrc, &tmpDst1);
        !           645:                        getstipplepixels(psrcS + (xrem>>5), (x&0x1f), w, 1,
        !           646:                            &fgfill, &tmpDst2);
        !           647:                        break;
        !           648:                }
        !           649: #ifdef notdef
        !           650:                putbitsrop(tmpDst1 | tmpDst2, x & PIM, w, pdst + (x>>PWSH), 
        !           651:                    pGC->planemask, rop);
        !           652: #else
        !           653:                {
        !           654:                    /*
        !           655:                     * Ultrix cc hasn't enough expression stack to compile
        !           656:                     * these values in the putbitsrop call.  (MIT:yba)
        !           657:                     */
        !           658:                    int tmpDst = tmpDst1 | tmpDst2, tmpx = x & PIM;
        !           659:                    int * pdsttmp = pdst + (x>>PWSH);
        !           660:                    putbitsrop(tmpDst, tmpx, w, pdsttmp, pGC->planemask, rop);
        !           661:                }
        !           662: #endif notdef
        !           663:                x += w;
        !           664:                width -= w;
        !           665:            }
        !           666:        }
        !           667: #ifdef notdef
        !           668:        if (*pwidth)
        !           669:        {
        !           670:            width = *pwidth;
        !           671:            while(width > 0)
        !           672:            {
        !           673:                psrc = psrcS;
        !           674:                w = min(min(stippleWidth, width), PPW);
        !           675:                if((rem = x % stippleWidth) != 0)
        !           676:                {
        !           677:                    w = min(min(stippleWidth - rem, width), PPW);
        !           678:                    /* we want to grab from the end of the tile.  Figure
        !           679:                     * out where that is.  In general, the start of the last
        !           680:                     * word of data on this scanline is stwidth -1 words 
        !           681:                     * away. But if we want to grab more bits than we'll
        !           682:                     * find on that line, we have to back up 1 word further.
        !           683:                     * On the other hand, if the whole tile fits in 1 word,
        !           684:                     * let's skip the work */ 
        !           685:                    endinc = stwidth - 1 - w / PPW;
        !           686: 
        !           687:                    if(endinc)
        !           688:                    {
        !           689:                        if((rem & 0x1f) + w > stippleWidth % PPW)
        !           690:                            endinc--;
        !           691:                    }
        !           692: 
        !           693:                    getbits(psrc + endinc, rem & PIM, w, tmpSrc);
        !           694:                    putbitsrop(tmpSrc, (x & PIM), w, pdst, 
        !           695:                        pGC->planemask, rop);
        !           696:                    if((x & PIM) + w >= PPW)
        !           697:                        pdst++;
        !           698:                }
        !           699: 
        !           700:                else if(((x & PIM) + w) < PPW)
        !           701:                {
        !           702:                    getbits(psrc, 0, w, tmpSrc);
        !           703:                    putbitsrop(tmpSrc, x & PIM, w, pdst, 
        !           704:                        pGC->planemask, rop);
        !           705:                }
        !           706:                else
        !           707:                {
        !           708:                    maskbits(x, w, startmask, endmask, nlMiddle);
        !           709: 
        !           710:                    if (startmask)
        !           711:                        nstart = PPW - (x & PIM);
        !           712:                    else
        !           713:                        nstart = 0;
        !           714:                    if (endmask)
        !           715:                        nend = (x + w)  & PIM;
        !           716:                    else
        !           717:                        nend = 0;
        !           718: 
        !           719:                    srcStartOver = nstart > PLST;
        !           720: 
        !           721:                    if(startmask)
        !           722:                    {
        !           723:                        getbits(psrc, 0, nstart, tmpSrc);
        !           724:                        putbitsrop(tmpSrc, (x & PIM), nstart, pdst, 
        !           725:                            pGC->planemask, rop);
        !           726:                        pdst++;
        !           727:                        if(srcStartOver)
        !           728:                            psrc++;
        !           729:                    }
        !           730:                     
        !           731:                    while(nlMiddle--)
        !           732:                    {
        !           733:                        /*
        !           734:                            getbits(psrc, nstart, PPW, tmpSrc);
        !           735:                            putbitsrop( tmpSrc, 0, PPW,
        !           736:                                pdst, pGC->planemask, rop );
        !           737:                        */
        !           738:                        switch ( pGC->fillStyle ) {
        !           739:                            case FillStippled:
        !           740:                                getstipplepixels( psrc, j, 4, 1, pdst, tmp1 );
        !           741:                                break;
        !           742:                            case FillOpaqueStippled:
        !           743:                                getstipplepixels( psrc, j, 4, 1, pdst, tmp1 );
        !           744:                                break;
        !           745:                        }
        !           746:                        pdst++;
        !           747:                        psrc++;
        !           748:                    }
        !           749:                    if(endmask)
        !           750:                    {
        !           751:                        getbits(psrc, nstart, nend, tmpSrc);
        !           752:                        putbitsrop(tmpSrc, 0, nend, pdst, 
        !           753:                            pGC->planemask, rop);
        !           754:                    }
        !           755:                 }
        !           756:                 x += w;
        !           757:                 width -= w;
        !           758:            }
        !           759:        }
        !           760: #endif
        !           761:        ppt++;
        !           762:        pwidth++;
        !           763:     }
        !           764:     DEALLOCATE_LOCAL(pptFree);
        !           765:     DEALLOCATE_LOCAL(pwidthFree);
        !           766: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.