xserver

xserver with xephyr scale patch
git clone https://git.neptards.moe/u3shit/xserver.git
Log | Files | Refs | README | LICENSE

fbimage.c (8218B)


      1 /*
      2  * Copyright © 1998 Keith Packard
      3  *
      4  * Permission to use, copy, modify, distribute, and sell this software and its
      5  * documentation for any purpose is hereby granted without fee, provided that
      6  * the above copyright notice appear in all copies and that both that
      7  * copyright notice and this permission notice appear in supporting
      8  * documentation, and that the name of Keith Packard not be used in
      9  * advertising or publicity pertaining to distribution of the software without
     10  * specific, written prior permission.  Keith Packard makes no
     11  * representations about the suitability of this software for any purpose.  It
     12  * is provided "as is" without express or implied warranty.
     13  *
     14  * KEITH PACKARD DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE,
     15  * INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO
     16  * EVENT SHALL KEITH PACKARD BE LIABLE FOR ANY SPECIAL, INDIRECT OR
     17  * CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE,
     18  * DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
     19  * TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
     20  * PERFORMANCE OF THIS SOFTWARE.
     21  */
     22 
     23 #ifdef HAVE_DIX_CONFIG_H
     24 #include <dix-config.h>
     25 #endif
     26 
     27 #include <string.h>
     28 
     29 #include "fb.h"
     30 
     31 void
     32 fbPutImage(DrawablePtr pDrawable,
     33            GCPtr pGC,
     34            int depth,
     35            int x, int y, int w, int h, int leftPad, int format, char *pImage)
     36 {
     37     FbGCPrivPtr pPriv = fbGetGCPrivate(pGC);
     38     unsigned long i;
     39     FbStride srcStride;
     40     FbStip *src = (FbStip *) pImage;
     41 
     42     x += pDrawable->x;
     43     y += pDrawable->y;
     44 
     45     switch (format) {
     46     case XYBitmap:
     47         srcStride = BitmapBytePad(w + leftPad) / sizeof(FbStip);
     48         fbPutXYImage(pDrawable,
     49                      fbGetCompositeClip(pGC),
     50                      pPriv->fg,
     51                      pPriv->bg,
     52                      pPriv->pm,
     53                      pGC->alu, TRUE, x, y, w, h, src, srcStride, leftPad);
     54         break;
     55     case XYPixmap:
     56         srcStride = BitmapBytePad(w + leftPad) / sizeof(FbStip);
     57         for (i = (unsigned long) 1 << (pDrawable->depth - 1); i; i >>= 1) {
     58             if (i & pGC->planemask) {
     59                 fbPutXYImage(pDrawable,
     60                              fbGetCompositeClip(pGC),
     61                              FB_ALLONES,
     62                              0,
     63                              fbReplicatePixel(i, pDrawable->bitsPerPixel),
     64                              pGC->alu,
     65                              TRUE, x, y, w, h, src, srcStride, leftPad);
     66             }
     67             src += srcStride * h;
     68         }
     69         break;
     70     case ZPixmap:
     71         srcStride = PixmapBytePad(w, pDrawable->depth) / sizeof(FbStip);
     72         fbPutZImage(pDrawable, fbGetCompositeClip(pGC),
     73                     pGC->alu, pPriv->pm, x, y, w, h, src, srcStride);
     74     }
     75 }
     76 
     77 void
     78 fbPutZImage(DrawablePtr pDrawable,
     79             RegionPtr pClip,
     80             int alu,
     81             FbBits pm,
     82             int x,
     83             int y, int width, int height, FbStip * src, FbStride srcStride)
     84 {
     85     FbStip *dst;
     86     FbStride dstStride;
     87     int dstBpp;
     88     int dstXoff, dstYoff;
     89     int nbox;
     90     BoxPtr pbox;
     91     int x1, y1, x2, y2;
     92 
     93     fbGetStipDrawable(pDrawable, dst, dstStride, dstBpp, dstXoff, dstYoff);
     94 
     95     for (nbox = RegionNumRects(pClip),
     96          pbox = RegionRects(pClip); nbox--; pbox++) {
     97         x1 = x;
     98         y1 = y;
     99         x2 = x + width;
    100         y2 = y + height;
    101         if (x1 < pbox->x1)
    102             x1 = pbox->x1;
    103         if (y1 < pbox->y1)
    104             y1 = pbox->y1;
    105         if (x2 > pbox->x2)
    106             x2 = pbox->x2;
    107         if (y2 > pbox->y2)
    108             y2 = pbox->y2;
    109         if (x1 >= x2 || y1 >= y2)
    110             continue;
    111         fbBltStip(src + (y1 - y) * srcStride,
    112                   srcStride,
    113                   (x1 - x) * dstBpp,
    114                   dst + (y1 + dstYoff) * dstStride,
    115                   dstStride,
    116                   (x1 + dstXoff) * dstBpp,
    117                   (x2 - x1) * dstBpp, (y2 - y1), alu, pm, dstBpp);
    118     }
    119 
    120     fbFinishAccess(pDrawable);
    121 }
    122 
    123 void
    124 fbPutXYImage(DrawablePtr pDrawable,
    125              RegionPtr pClip,
    126              FbBits fg,
    127              FbBits bg,
    128              FbBits pm,
    129              int alu,
    130              Bool opaque,
    131              int x,
    132              int y,
    133              int width, int height, FbStip * src, FbStride srcStride, int srcX)
    134 {
    135     FbBits *dst;
    136     FbStride dstStride;
    137     int dstBpp;
    138     int dstXoff, dstYoff;
    139     int nbox;
    140     BoxPtr pbox;
    141     int x1, y1, x2, y2;
    142     FbBits fgand = 0, fgxor = 0, bgand = 0, bgxor = 0;
    143 
    144     fbGetDrawable(pDrawable, dst, dstStride, dstBpp, dstXoff, dstYoff);
    145 
    146     if (dstBpp == 1) {
    147         if (opaque)
    148             alu = FbOpaqueStipple1Rop(alu, fg, bg);
    149         else
    150             alu = FbStipple1Rop(alu, fg);
    151     }
    152     else {
    153         fgand = fbAnd(alu, fg, pm);
    154         fgxor = fbXor(alu, fg, pm);
    155         if (opaque) {
    156             bgand = fbAnd(alu, bg, pm);
    157             bgxor = fbXor(alu, bg, pm);
    158         }
    159         else {
    160             bgand = fbAnd(GXnoop, (FbBits) 0, FB_ALLONES);
    161             bgxor = fbXor(GXnoop, (FbBits) 0, FB_ALLONES);
    162         }
    163     }
    164 
    165     for (nbox = RegionNumRects(pClip),
    166          pbox = RegionRects(pClip); nbox--; pbox++) {
    167         x1 = x;
    168         y1 = y;
    169         x2 = x + width;
    170         y2 = y + height;
    171         if (x1 < pbox->x1)
    172             x1 = pbox->x1;
    173         if (y1 < pbox->y1)
    174             y1 = pbox->y1;
    175         if (x2 > pbox->x2)
    176             x2 = pbox->x2;
    177         if (y2 > pbox->y2)
    178             y2 = pbox->y2;
    179         if (x1 >= x2 || y1 >= y2)
    180             continue;
    181         if (dstBpp == 1) {
    182             fbBltStip(src + (y1 - y) * srcStride,
    183                       srcStride,
    184                       (x1 - x) + srcX,
    185                       (FbStip *) (dst + (y1 + dstYoff) * dstStride),
    186                       FbBitsStrideToStipStride(dstStride),
    187                       (x1 + dstXoff) * dstBpp,
    188                       (x2 - x1) * dstBpp, (y2 - y1), alu, pm, dstBpp);
    189         }
    190         else {
    191             fbBltOne(src + (y1 - y) * srcStride,
    192                      srcStride,
    193                      (x1 - x) + srcX,
    194                      dst + (y1 + dstYoff) * dstStride,
    195                      dstStride,
    196                      (x1 + dstXoff) * dstBpp,
    197                      dstBpp,
    198                      (x2 - x1) * dstBpp, (y2 - y1), fgand, fgxor, bgand, bgxor);
    199         }
    200     }
    201 
    202     fbFinishAccess(pDrawable);
    203 }
    204 
    205 void
    206 fbGetImage(DrawablePtr pDrawable,
    207            int x,
    208            int y,
    209            int w, int h, unsigned int format, unsigned long planeMask, char *d)
    210 {
    211     FbBits *src;
    212     FbStride srcStride;
    213     int srcBpp;
    214     int srcXoff, srcYoff;
    215     FbStip *dst;
    216     FbStride dstStride;
    217 
    218     /*
    219      * XFree86 DDX empties the root borderClip when the VT is
    220      * switched away; this checks for that case
    221      */
    222     if (!fbDrawableEnabled(pDrawable))
    223         return;
    224 
    225     fbGetDrawable(pDrawable, src, srcStride, srcBpp, srcXoff, srcYoff);
    226 
    227     x += pDrawable->x;
    228     y += pDrawable->y;
    229 
    230     dst = (FbStip *) d;
    231     if (format == ZPixmap || srcBpp == 1) {
    232         FbBits pm;
    233 
    234         pm = fbReplicatePixel(planeMask, srcBpp);
    235         dstStride = PixmapBytePad(w, pDrawable->depth);
    236         dstStride /= sizeof(FbStip);
    237         fbBltStip((FbStip *) (src + (y + srcYoff) * srcStride),
    238                   FbBitsStrideToStipStride(srcStride),
    239                   (x + srcXoff) * srcBpp,
    240                   dst, dstStride, 0, w * srcBpp, h, GXcopy, FB_ALLONES, srcBpp);
    241 
    242         if (pm != FB_ALLONES) {
    243             for (int i = 0; i < dstStride * h; i++)
    244                 dst[i] &= pm;
    245         }
    246     }
    247     else {
    248         dstStride = BitmapBytePad(w) / sizeof(FbStip);
    249         fbBltPlane(src + (y + srcYoff) * srcStride,
    250                    srcStride,
    251                    (x + srcXoff) * srcBpp,
    252                    srcBpp,
    253                    dst,
    254                    dstStride,
    255                    0,
    256                    w * srcBpp, h,
    257                    fbAndStip(GXcopy, FB_STIP_ALLONES, FB_STIP_ALLONES),
    258                    fbXorStip(GXcopy, FB_STIP_ALLONES, FB_STIP_ALLONES),
    259                    fbAndStip(GXcopy, 0, FB_STIP_ALLONES),
    260                    fbXorStip(GXcopy, 0, FB_STIP_ALLONES), planeMask);
    261     }
    262 
    263     fbFinishAccess(pDrawable);
    264 }