Home | History | Annotate | Line # | Download | only in src
      1 
      2 #ifdef HAVE_CONFIG_H
      3 #include "config.h"
      4 #endif
      5 
      6 /* All drivers should typically include these */
      7 #include "xf86.h"
      8 #include "xf86_OSproc.h"
      9 #include "compiler.h"
     10 
     11 /* Drivers that need to access the PCI config space directly need this */
     12 #include "xf86Pci.h"
     13 
     14 /* Drivers that use XAA need this */
     15 #ifdef HAVE_XAA_H
     16 #include "xaalocal.h"
     17 #endif
     18 #include "xf86fbman.h"
     19 
     20 #include "miline.h"
     21 
     22 #include "tdfx.h"
     23 
     24 #ifdef HAVE_XAA_H
     25 #ifdef TDFX_DEBUG_CMDS
     26 static int cmdCnt=0;
     27 static int lastAddr=0;
     28 #endif
     29 
     30 static int TDFXROPCvt[] = {0x00, 0x88, 0x44, 0xCC, 0x22, 0xAA, 0x66, 0xEE,
     31 			   0x11, 0x99, 0x55, 0xDD, 0x33, 0xBB, 0x77, 0xFF,
     32 			   0x00, 0xA0, 0x50, 0xF0, 0x0A, 0xAA, 0x5A, 0xFA,
     33 			   0x05, 0xA5, 0x55, 0xF5, 0x0F, 0xAF, 0x5F, 0xFF};
     34 #define ROP_PATTERN_OFFSET 16
     35 
     36 static void TDFXSetClippingRectangle(ScrnInfoPtr pScrn, int left, int top,
     37 				     int right, int bottom);
     38 static void TDFXDisableClipping(ScrnInfoPtr pScrn);
     39 static void TDFXSetupForMono8x8PatternFill(ScrnInfoPtr pScrn, int patx,
     40 					   int paty, int fg, int bg, int rop,
     41 					   unsigned int planemask);
     42 static void TDFXSubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn, int patx,
     43 						 int pay, int x, int y,
     44 						 int w, int h);
     45 static void TDFXSetupForSolidLine(ScrnInfoPtr pScrn, int color, int rop,
     46 				  unsigned int planemask);
     47 static void TDFXSubsequentSolidTwoPointLine(ScrnInfoPtr pScrn, int srcx,
     48 					    int srcy, int dstx, int dsty,
     49 					    int flags);
     50 static void TDFXSubsequentSolidHorVertLine(ScrnInfoPtr pScrn, int x, int y,
     51 					   int len, int dir);
     52 static void TDFXNonTEGlyphRenderer(ScrnInfoPtr pScrn, int x, int y, int n,
     53 				   NonTEGlyphPtr glyphs, BoxPtr pbox, int fg,
     54 				   int rop, unsigned int planemask);
     55 static void TDFXSetupForDashedLine(ScrnInfoPtr pScrn, int fg, int bg, int rop,
     56                                    unsigned int planemask, int length,
     57 		                   unsigned char *pattern);
     58 static void TDFXSubsequentDashedTwoPointLine(ScrnInfoPtr pScrn, int x1, int y1,
     59                                              int x2, int y2, int flags,
     60                                              int phase);
     61 #ifdef ENABLE_SS_COLOR_EXPAND_FILL
     62 static void TDFXSetupForScreenToScreenColorExpandFill(ScrnInfoPtr pScrn,
     63                                                       int fg, int bg, int rop,
     64                                                       unsigned int planemask);
     65 static void TDFXSubsequentScreenToScreenColorExpandFill(ScrnInfoPtr pScrn,
     66                                                         int x, int y, int w,
     67                                                         int h, int srcx,
     68                                                         int srcy, int offset);
     69 #endif
     70 static void TDFXSetupForCPUToScreenColorExpandFill(ScrnInfoPtr pScrn,
     71                                                    int fg, int bg, int rop,
     72                                                    unsigned int planemask);
     73 static void TDFXSubsequentCPUToScreenColorExpandFill(ScrnInfoPtr pScrn,
     74                                                      int x, int y,
     75                                                      int w, int h,
     76                                                      int skipleft);
     77 static void TDFXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno);
     78 
     79 #endif
     80 void
     81 TDFXNeedSync(ScrnInfoPtr pScrn) {
     82   TDFXPtr pTDFX = TDFXPTR(pScrn);
     83   pTDFX->syncDone=FALSE;
     84 #ifdef HAVE_XAA_H
     85   pTDFX->AccelInfoRec->NeedToSync = TRUE;
     86 #endif
     87 }
     88 
     89 void
     90 TDFXFirstSync(ScrnInfoPtr pScrn) {
     91   TDFXPtr pTDFX = TDFXPTR(pScrn);
     92 
     93   if (!pTDFX->syncDone) {
     94 #ifdef TDFXDRI
     95     if (pTDFX->directRenderingEnabled) {
     96       DRILock(xf86ScrnToScreen(pScrn), 0);
     97       TDFXSwapContextFifo(xf86ScrnToScreen(pScrn));
     98     }
     99 #endif
    100     pTDFX->syncDone=TRUE;
    101     pTDFX->sync(pScrn);
    102   }
    103 }
    104 
    105 void
    106 TDFXCheckSync(ScrnInfoPtr pScrn) {
    107   TDFXPtr pTDFX = TDFXPTR(pScrn);
    108 
    109   if (pTDFX->syncDone) {
    110     pTDFX->sync(pScrn);
    111     pTDFX->syncDone=FALSE;
    112 #ifdef TDFXDRI
    113     if (pTDFX->directRenderingEnabled) {
    114       DRIUnlock(xf86ScrnToScreen(pScrn));
    115     }
    116 #endif
    117   }
    118 }
    119 
    120 void
    121 TDFXSelectBuffer(TDFXPtr pTDFX, int which) {
    122   int fmt;
    123 
    124   TDFXMakeRoom(pTDFX, 4);
    125   DECLARE(SSTCP_SRCBASEADDR|SSTCP_DSTBASEADDR|SSTCP_SRCFORMAT|SSTCP_DSTFORMAT);
    126   switch (which) {
    127   case TDFX_FRONT:
    128     if (pTDFX->cpp==1) fmt=pTDFX->stride|(1<<16);
    129     else fmt=pTDFX->stride|((pTDFX->cpp+1)<<16);
    130     TDFXWriteLong(pTDFX, SST_2D_DSTBASEADDR, pTDFX->fbOffset);
    131     TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    132     pTDFX->sst2DDstFmtShadow = fmt;
    133     TDFXWriteLong(pTDFX, SST_2D_SRCBASEADDR, pTDFX->fbOffset);
    134     TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, fmt);
    135     pTDFX->sst2DSrcFmtShadow = fmt;
    136     break;
    137   case TDFX_BACK:
    138     if (pTDFX->cpp==2)
    139       fmt=((pTDFX->stride+127)/128)|(3<<16); /* Tiled 16bpp */
    140     else
    141       fmt=((pTDFX->stride+127)/128)|(5<<16); /* Tiled 32bpp */
    142     TDFXWriteLong(pTDFX, SST_2D_DSTBASEADDR, pTDFX->backOffset|BIT(31));
    143     TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    144     pTDFX->sst2DDstFmtShadow = fmt;
    145     TDFXWriteLong(pTDFX, SST_2D_SRCBASEADDR, pTDFX->backOffset|BIT(31));
    146     TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, fmt);
    147     pTDFX->sst2DSrcFmtShadow = fmt;
    148     break;
    149   case TDFX_DEPTH:
    150     if (pTDFX->cpp==2)
    151       fmt=((pTDFX->stride+127)/128)|(3<<16); /* Tiled 16bpp */
    152     else
    153       fmt=((pTDFX->stride+127)/128)|(5<<16); /* Tiled 32bpp */
    154     TDFXWriteLong(pTDFX, SST_2D_DSTBASEADDR, pTDFX->depthOffset|BIT(31));
    155     TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    156     pTDFX->sst2DDstFmtShadow = fmt;
    157     TDFXWriteLong(pTDFX, SST_2D_SRCBASEADDR, pTDFX->depthOffset|BIT(31));
    158     TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, fmt);
    159     pTDFX->sst2DSrcFmtShadow = fmt;
    160     break;
    161   default:
    162     ;
    163   }
    164 }
    165 
    166 void
    167 TDFXSetLFBConfig(TDFXPtr pTDFX) {
    168   if (pTDFX->ChipType<=PCI_CHIP_VOODOO3) {
    169 #if X_BYTE_ORDER == X_BIG_ENDIAN
    170     unsigned int lfbmode;
    171     lfbmode=TDFXReadLongMMIO(pTDFX, SST_3D_LFBMODE);
    172 
    173     lfbmode&=~BIT(12); /* 0 bit 12 is byte swizzle */
    174     lfbmode|=BIT(11); /* 1 bit 11 is word swizzle */
    175     lfbmode&=~BIT(10); /* 0 bit 10  ARGB or ABGR */
    176     lfbmode&=~BIT(9); /* 0 bit 9 if bit10 = 0:  ARGB else ABGR */
    177 
    178     TDFXWriteLongMMIO(pTDFX, SST_3D_LFBMODE, lfbmode);
    179 #endif
    180     TDFXWriteLongMMIO(pTDFX, LFBMEMORYCONFIG, (pTDFX->backOffset>>12) |
    181 		      SST_RAW_LFB_ADDR_STRIDE_4K |
    182 		      ((pTDFX->stride+127)/128)<<SST_RAW_LFB_TILE_STRIDE_SHIFT);
    183   } else {
    184     int chip;
    185     int stride, bits;
    186     int TileAperturePitch, lg2TileAperturePitch;
    187     if (pTDFX->cpp==2) stride=pTDFX->stride;
    188     else stride=4*pTDFX->stride/pTDFX->cpp;
    189     bits=pTDFX->backOffset>>12;
    190     for (lg2TileAperturePitch = 0, TileAperturePitch = 1024;
    191          (lg2TileAperturePitch < 5) &&
    192              TileAperturePitch < stride;
    193          lg2TileAperturePitch += 1, TileAperturePitch <<= 1);
    194 #if	0
    195     fprintf(stderr, "Using %d (== lg2(%d)-10) for tile aperture pitch\n",
    196             lg2TileAperturePitch, TileAperturePitch);
    197     fprintf(stderr, "stride == %d\n", stride);
    198 #endif
    199     for (chip=0; chip<pTDFX->numChips; chip++) {
    200       TDFXWriteChipLongMMIO(pTDFX, chip, LFBMEMORYCONFIG, (bits&0x1FFF) |
    201 			    SST_RAW_LFB_ADDR_STRIDE(lg2TileAperturePitch) |
    202 			    ((bits&0x6000)<<10) |
    203 			    ((stride+127)/128)<<SST_RAW_LFB_TILE_STRIDE_SHIFT);
    204     }
    205   }
    206 }
    207 
    208 
    209 Bool
    210 TDFXAccelInit(ScreenPtr pScreen)
    211 {
    212 #ifdef HAVE_XAA_H
    213   XAAInfoRecPtr infoPtr;
    214   ScrnInfoPtr pScrn = xf86ScreenToScrn(pScreen);
    215   TDFXPtr pTDFX = TDFXPTR(pScrn);
    216   CARD32 commonFlags;
    217 
    218   pTDFX->AccelInfoRec = infoPtr = XAACreateInfoRec();
    219   if (!infoPtr) return FALSE;
    220 
    221   infoPtr->Flags = PIXMAP_CACHE | OFFSCREEN_PIXMAPS | LINEAR_FRAMEBUFFER;
    222 
    223   infoPtr->Sync = pTDFX->sync;
    224 
    225   infoPtr->SetClippingRectangle = TDFXSetClippingRectangle;
    226   infoPtr->DisableClipping = TDFXDisableClipping;
    227   infoPtr->ClippingFlags = HARDWARE_CLIP_SCREEN_TO_SCREEN_COLOR_EXPAND |
    228     HARDWARE_CLIP_SCREEN_TO_SCREEN_COPY |
    229     HARDWARE_CLIP_MONO_8x8_FILL |
    230     HARDWARE_CLIP_COLOR_8x8_FILL |
    231     HARDWARE_CLIP_SOLID_FILL |
    232     HARDWARE_CLIP_DASHED_LINE |
    233     HARDWARE_CLIP_SOLID_LINE;
    234 
    235   miSetZeroLineBias(pScreen, OCTANT2 | OCTANT5 | OCTANT7 | OCTANT8);
    236 
    237   commonFlags = BIT_ORDER_IN_BYTE_MSBFIRST | NO_PLANEMASK;
    238 
    239   infoPtr->SetupForSolidFill = TDFXSetupForSolidFill;
    240   infoPtr->SubsequentSolidFillRect = TDFXSubsequentSolidFillRect;
    241   infoPtr->SolidFillFlags = commonFlags;
    242 
    243   infoPtr->SetupForSolidLine = TDFXSetupForSolidLine;
    244   infoPtr->SubsequentSolidTwoPointLine = TDFXSubsequentSolidTwoPointLine;
    245   infoPtr->SubsequentSolidHorVertLine = TDFXSubsequentSolidHorVertLine;
    246   infoPtr->SolidLineFlags = commonFlags;
    247 
    248   infoPtr->SetupForDashedLine = TDFXSetupForDashedLine;
    249   infoPtr->SubsequentDashedTwoPointLine = TDFXSubsequentDashedTwoPointLine;
    250   infoPtr->DashedLineFlags = commonFlags | LINE_PATTERN_LSBFIRST_LSBJUSTIFIED;
    251   infoPtr->DashPatternMaxLength = 32;
    252 
    253   infoPtr->NonTEGlyphRenderer = TDFXNonTEGlyphRenderer;
    254   infoPtr->NonTEGlyphRendererFlags = commonFlags;
    255 
    256   infoPtr->SetupForScreenToScreenCopy = TDFXSetupForScreenToScreenCopy;
    257   infoPtr->SubsequentScreenToScreenCopy = TDFXSubsequentScreenToScreenCopy;
    258   infoPtr->ScreenToScreenCopyFlags = commonFlags;
    259 
    260   /* When we're using the fifo we have to use indirect expansion */
    261   pTDFX->scanlineColorExpandBuffers[0] = malloc((pScrn->virtualX+62)/32*4);
    262   pTDFX->scanlineColorExpandBuffers[1] = malloc((pScrn->virtualX+62)/32*4);
    263   infoPtr->NumScanlineColorExpandBuffers=2;
    264   infoPtr->ScanlineColorExpandBuffers=pTDFX->scanlineColorExpandBuffers;
    265   infoPtr->SetupForScanlineCPUToScreenColorExpandFill =
    266     TDFXSetupForCPUToScreenColorExpandFill;
    267   infoPtr->SubsequentScanlineCPUToScreenColorExpandFill =
    268     TDFXSubsequentCPUToScreenColorExpandFill;
    269   infoPtr->SubsequentColorExpandScanline =
    270     TDFXSubsequentColorExpandScanline;
    271   infoPtr->ScanlineCPUToScreenColorExpandFillFlags = NO_PLANEMASK |
    272 #if X_BYTE_ORDER == X_LITTLE_ENDIAN
    273     BIT_ORDER_IN_BYTE_MSBFIRST |
    274 #endif
    275     CPU_TRANSFER_PAD_DWORD | SCANLINE_PAD_DWORD |
    276     LEFT_EDGE_CLIPPING; /* | LEFT_EDGE_CLIPPING_NEGATIVE_X; */
    277 
    278   infoPtr->SetupForMono8x8PatternFill = TDFXSetupForMono8x8PatternFill;
    279   infoPtr->SubsequentMono8x8PatternFillRect =
    280     TDFXSubsequentMono8x8PatternFillRect;
    281   infoPtr->Mono8x8PatternFillFlags = commonFlags |
    282     HARDWARE_PATTERN_PROGRAMMED_BITS |
    283     HARDWARE_PATTERN_PROGRAMMED_ORIGIN |
    284     HARDWARE_PATTERN_SCREEN_ORIGIN;
    285 
    286 #ifdef ENABLE_SS_COLOR_EXPAND_FILL
    287   /* This causes us to fail compliance */
    288   /* I suspect 1bpp pixmaps are getting written to cache incorrectly */
    289   infoPtr->SetupForScreenToScreenColorExpandFill =
    290     TDFXSetupForScreenToScreenColorExpandFill;
    291   infoPtr->SubsequentScreenToScreenColorExpandFill =
    292     TDFXSubsequentScreenToScreenColorExpandFill;
    293   infoPtr->ScreenToScreenColorExpandFillFlags = commonFlags;
    294 #endif
    295 
    296   pTDFX->PciCnt=TDFXReadLongMMIO(pTDFX, 0)&0x1F;
    297   pTDFX->PrevDrawState=pTDFX->DrawState=0;
    298 
    299   pTDFX->ModeReg.srcbaseaddr=pTDFX->fbOffset;
    300   TDFXWriteLongMMIO(pTDFX, SST_2D_SRCBASEADDR, pTDFX->ModeReg.srcbaseaddr);
    301   pTDFX->ModeReg.dstbaseaddr=pTDFX->fbOffset;
    302   TDFXWriteLongMMIO(pTDFX, SST_2D_DSTBASEADDR, pTDFX->ModeReg.dstbaseaddr);
    303 
    304   pTDFX->sst2DSrcFmtShadow = TDFXReadLongMMIO(pTDFX, SST_2D_SRCFORMAT);
    305   pTDFX->sst2DDstFmtShadow = TDFXReadLongMMIO(pTDFX, SST_2D_DSTFORMAT);
    306 
    307   /* Fill in acceleration functions */
    308   return XAAInit(pScreen, infoPtr);
    309 #else
    310   return FALSE;
    311 #endif
    312 }
    313 
    314 static void TDFXMakeRoomNoProp(TDFXPtr pTDFX, int size) {
    315   int stat;
    316 
    317   pTDFX->PciCnt-=size;
    318   if (pTDFX->PciCnt<1) {
    319     do {
    320       stat=TDFXReadLongMMIO(pTDFX, 0);
    321       pTDFX->PciCnt=stat&0x1F;
    322     } while (pTDFX->PciCnt<size);
    323   }
    324 }
    325 
    326 static void TDFXSendNOPNoProp(ScrnInfoPtr pScrn)
    327 {
    328   TDFXPtr pTDFX;
    329 
    330   pTDFX=TDFXPTR(pScrn);
    331   TDFXMakeRoomNoProp(pTDFX, 1);
    332   TDFXWriteLongMMIO(pTDFX, SST_2D_COMMAND, SST_2D_NOP);
    333 }
    334 
    335 void TDFXSync(ScrnInfoPtr pScrn)
    336 {
    337   TDFXPtr pTDFX;
    338   int i;
    339   int stat;
    340 
    341   TDFXTRACEACCEL("TDFXSync\n");
    342   pTDFX=TDFXPTR(pScrn);
    343 
    344   TDFXSendNOPNoProp(pScrn);
    345   i=0;
    346   do {
    347     stat=TDFXReadLongMMIO(pTDFX, 0);
    348     if (stat&SST_BUSY) i=0; else i++;
    349   } while (i<3);
    350   pTDFX->PciCnt=stat&0x1F;
    351 }
    352 
    353 #ifdef HAVE_XAA_H
    354 
    355 
    356 static void
    357 TDFXMatchState(TDFXPtr pTDFX)
    358 {
    359   if (pTDFX->PrevDrawState==pTDFX->DrawState) return;
    360 
    361   /* Do we need to set a clipping rectangle? */
    362   if (pTDFX->DrawState&DRAW_STATE_CLIPPING)
    363     pTDFX->Cmd |= SST_2D_USECLIP1;
    364   else
    365     pTDFX->Cmd &= ~SST_2D_USECLIP1;
    366 
    367   /* Do we need to set transparency? */
    368   TDFXMakeRoom(pTDFX, 1);
    369   DECLARE(SSTCP_COMMANDEXTRA);
    370   if (pTDFX->DrawState&DRAW_STATE_TRANSPARENT) {
    371     TDFXWriteLong(pTDFX, SST_2D_COMMANDEXTRA, SST_2D_SRC_COLORKEY_EX);
    372   } else {
    373     TDFXWriteLong(pTDFX, SST_2D_COMMANDEXTRA, 0);
    374   }
    375 
    376   /* Has the previous routine left clip1 changed? Reset it. */
    377   if (pTDFX->DrawState&DRAW_STATE_CLIP1CHANGED) {
    378     TDFXMakeRoom(pTDFX, 2);
    379     DECLARE(SSTCP_CLIP1MIN|SSTCP_CLIP1MAX);
    380     TDFXWriteLong(pTDFX, SST_2D_CLIP1MIN, pTDFX->ModeReg.clip1min);
    381     TDFXWriteLong(pTDFX, SST_2D_CLIP1MAX, pTDFX->ModeReg.clip1max);
    382     pTDFX->DrawState&=~DRAW_STATE_CLIP1CHANGED;
    383   }
    384 
    385   pTDFX->PrevDrawState=pTDFX->DrawState;
    386 }
    387 
    388 static void
    389 TDFXClearState(ScrnInfoPtr pScrn)
    390 {
    391   TDFXPtr pTDFX;
    392 
    393   pTDFX=TDFXPTR(pScrn);
    394   pTDFX->Cmd=0;
    395   pTDFX->DrawState&=~DRAW_STATE_TRANSPARENT;
    396   /* Make sure we've done a sync */
    397   TDFXFirstSync(pScrn);
    398 }
    399 
    400 static void
    401 TDFXSetClippingRectangle(ScrnInfoPtr pScrn, int left, int top, int right,
    402 			 int bottom)
    403 {
    404   TDFXPtr pTDFX;
    405 
    406   TDFXTRACEACCEL("TDFXSetClippingRectangle %d,%d to %d,%d\n", left, top,
    407 		 right, bottom);
    408   pTDFX=TDFXPTR(pScrn);
    409 
    410   pTDFX->ModeReg.clip1min=(top&0xFFF)<<16 | (left&0xFFF);
    411   pTDFX->ModeReg.clip1max=((bottom+1)&0xFFF)<<16 | ((right+1)&0xFFF);
    412 
    413   pTDFX->DrawState|=DRAW_STATE_CLIPPING|DRAW_STATE_CLIP1CHANGED;
    414 }
    415 
    416 static void
    417 TDFXDisableClipping(ScrnInfoPtr pScrn)
    418 {
    419   TDFXPtr pTDFX;
    420 
    421   TDFXTRACEACCEL("TDFXDisableClippingRectangle\n");
    422   pTDFX=TDFXPTR(pScrn);
    423 
    424   pTDFX->DrawState&=~DRAW_STATE_CLIPPING;
    425 }
    426 
    427 void
    428 TDFXSetupForScreenToScreenCopy(ScrnInfoPtr pScrn, int xdir, int ydir, int rop,
    429 			       unsigned int planemask, int trans_color)
    430 {
    431   TDFXPtr pTDFX;
    432   int fmt;
    433 
    434   TDFXTRACEACCEL("TDFXSetupForScreenToScreenCopy\n xdir=%d ydir=%d "
    435 		 "rop=%d planemask=%d trans_color=%d\n",
    436 		 xdir, ydir, rop, planemask, trans_color);
    437   pTDFX=TDFXPTR(pScrn);
    438   TDFXClearState(pScrn);
    439 
    440   if (trans_color!=-1) {
    441     TDFXMakeRoom(pTDFX, 3);
    442     DECLARE(SSTCP_SRCCOLORKEYMIN|SSTCP_SRCCOLORKEYMAX|SSTCP_ROP);
    443     TDFXWriteLong(pTDFX, SST_2D_SRCCOLORKEYMIN, trans_color);
    444     TDFXWriteLong(pTDFX, SST_2D_SRCCOLORKEYMAX, trans_color);
    445     TDFXWriteLong(pTDFX, SST_2D_ROP, TDFXROPCvt[GXnoop]<<8);
    446     pTDFX->DrawState|=DRAW_STATE_TRANSPARENT;
    447   }
    448   pTDFX->Cmd = (TDFXROPCvt[rop]<<24) | SST_2D_SCRNTOSCRNBLIT;
    449   if (xdir==-1) pTDFX->Cmd |= SST_2D_X_RIGHT_TO_LEFT;
    450   if (ydir==-1) pTDFX->Cmd |= SST_2D_Y_BOTTOM_TO_TOP;
    451   if (pTDFX->cpp==1) fmt=pTDFX->stride|(1<<16);
    452   else fmt=pTDFX->stride|((pTDFX->cpp+1)<<16);
    453 
    454   TDFXMakeRoom(pTDFX, 2);
    455   DECLARE(SSTCP_SRCFORMAT|SSTCP_DSTFORMAT);
    456   TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    457   pTDFX->sst2DDstFmtShadow = fmt;
    458   TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, fmt);
    459   pTDFX->sst2DSrcFmtShadow = fmt;
    460 }
    461 
    462 void
    463 TDFXSubsequentScreenToScreenCopy(ScrnInfoPtr pScrn, int srcX, int srcY,
    464 				 int dstX, int dstY, int w, int h)
    465 {
    466   TDFXPtr pTDFX;
    467 
    468   TDFXTRACEACCEL("TDFXSubsequentScreenToScreenCopy\n srcX=%d srcY=%d"
    469                  " dstX=%d dstY=%d w=%d h=%d\n", srcX, srcY, dstX, dstY, w, h);
    470   pTDFX=TDFXPTR(pScrn);
    471   TDFXMatchState(pTDFX);
    472 
    473   if (pTDFX->Cmd&SST_2D_Y_BOTTOM_TO_TOP) {
    474     srcY += h-1;
    475     dstY += h-1;
    476   }
    477   if (pTDFX->Cmd&SST_2D_X_RIGHT_TO_LEFT) {
    478     srcX += w-1;
    479     dstX += w-1;
    480   }
    481   if ((srcY>=dstY-32 && srcY<=dstY)||
    482       (srcY>=pTDFX->prevBlitDest.y1-32 && srcY<=pTDFX->prevBlitDest.y1)) {
    483     TDFXSendNOP(pScrn);
    484   }
    485   pTDFX->sync(pScrn);
    486 
    487   TDFXMakeRoom(pTDFX, 4);
    488   DECLARE(SSTCP_DSTSIZE|SSTCP_DSTXY|SSTCP_SRCXY|SSTCP_COMMAND);
    489   TDFXWriteLong(pTDFX, SST_2D_SRCXY, (srcX&0x1FFF) | ((srcY&0x1FFF)<<16));
    490   TDFXWriteLong(pTDFX, SST_2D_DSTSIZE, (w&0x1FFF) | ((h&0x1FFF)<<16));
    491   TDFXWriteLong(pTDFX, SST_2D_DSTXY, (dstX&0x1FFF) | ((dstY&0x1FFF)<<16));
    492   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd|SST_2D_GO);
    493 
    494   pTDFX->prevBlitDest.y1=dstY;
    495 }
    496 
    497 void
    498 TDFXSetupForSolidFill(ScrnInfoPtr pScrn, int color, int rop,
    499 		      unsigned int planemask)
    500 {
    501   TDFXPtr pTDFX;
    502   int fmt;
    503 
    504   TDFXTRACEACCEL("TDFXSetupForSolidFill color=%d rop=%d planemask=%d\n",
    505                  color, rop, planemask);
    506   pTDFX=TDFXPTR(pScrn);
    507   TDFXClearState(pScrn);
    508 
    509   pTDFX->Cmd=TDFXROPCvt[rop]<<24;
    510   if (pTDFX->cpp==1) fmt=(1<<16)|pTDFX->stride;
    511   else fmt=((pTDFX->cpp+1)<<16)|pTDFX->stride;
    512 
    513   TDFXMakeRoom(pTDFX, 3);
    514   DECLARE(SSTCP_DSTFORMAT|SSTCP_COLORFORE|
    515 		 SSTCP_COLORBACK);
    516   TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    517   pTDFX->sst2DDstFmtShadow = fmt;
    518   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, color);
    519   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, color);
    520 }
    521 
    522 void
    523 TDFXSubsequentSolidFillRect(ScrnInfoPtr pScrn, int x, int y, int w, int h)
    524 {
    525   /* Also called by TDFXSubsequentMono8x8PatternFillRect */
    526   TDFXPtr pTDFX;
    527 
    528   TDFXTRACEACCEL("TDFXSubsequentSolidFillRect x=%d y=%d w=%d h=%d\n",
    529 		 x, y, w, h);
    530   pTDFX=TDFXPTR(pScrn);
    531   TDFXMatchState(pTDFX);
    532 
    533   TDFXMakeRoom(pTDFX, 3);
    534   DECLARE(SSTCP_DSTSIZE|SSTCP_DSTXY|SSTCP_COMMAND);
    535   TDFXWriteLong(pTDFX, SST_2D_DSTSIZE, ((h&0x1FFF)<<16) | (w&0x1FFF));
    536   TDFXWriteLong(pTDFX, SST_2D_DSTXY, ((y&0x1FFF)<<16) | (x&0x1FFF));
    537   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd | SST_2D_RECTANGLEFILL |
    538 		SST_2D_GO);
    539 }
    540 
    541 static void
    542 TDFXSetupForMono8x8PatternFill(ScrnInfoPtr pScrn, int patx, int paty,
    543 			       int fg, int bg, int rop, unsigned int planemask)
    544 {
    545   TDFXPtr pTDFX;
    546   int fmt;
    547 
    548   TDFXTRACEACCEL("TDFXSetupForMono8x8PatternFill patx=%x paty=%x fg=%d"
    549                  " bg=%d rop=%d planemask=%d\n", patx, paty, fg, bg, rop,
    550 		 planemask);
    551   pTDFX=TDFXPTR(pScrn);
    552   TDFXClearState(pScrn);
    553 
    554   pTDFX->Cmd = (TDFXROPCvt[rop+ROP_PATTERN_OFFSET]<<24) |
    555     SST_2D_MONOCHROME_PATTERN;
    556   if (bg==-1) {
    557     pTDFX->Cmd |= SST_2D_TRANSPARENT_MONOCHROME;
    558   }
    559   if (pTDFX->cpp==1) fmt=(1<<16)|pTDFX->stride;
    560   else fmt=((pTDFX->cpp+1)<<16)|pTDFX->stride;
    561 
    562   TDFXMakeRoom(pTDFX, 5);
    563   DECLARE(SSTCP_DSTFORMAT|SSTCP_PATTERN0ALIAS
    564 		  |SSTCP_PATTERN1ALIAS|SSTCP_COLORFORE|
    565 		  SSTCP_COLORBACK);
    566   TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    567   pTDFX->sst2DDstFmtShadow = fmt;
    568   TDFXWriteLong(pTDFX, SST_2D_PATTERN0, patx);
    569   TDFXWriteLong(pTDFX, SST_2D_PATTERN1, paty);
    570   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, bg);
    571   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, fg);
    572 }
    573 
    574 static void
    575 TDFXSubsequentMono8x8PatternFillRect(ScrnInfoPtr pScrn, int patx, int paty,
    576 				     int x, int y, int w, int h)
    577 {
    578   TDFXPtr pTDFX;
    579 
    580   TDFXTRACEACCEL("TDFXSubsequentMono8x8PatternFillRect patx=%x paty=%x"
    581                  " x=%d y=%d w=%d h=%d\n", patx, paty, x, y, w, h);
    582   pTDFX=TDFXPTR(pScrn);
    583 
    584   pTDFX->Cmd |= ((patx&0x7)<<SST_2D_X_PATOFFSET_SHIFT) |
    585     ((paty&0x7)<<SST_2D_Y_PATOFFSET_SHIFT);
    586 
    587   TDFXSubsequentSolidFillRect(pScrn, x, y, w, h);
    588 }
    589 
    590 static void
    591 TDFXSetupForSolidLine(ScrnInfoPtr pScrn, int color, int rop,
    592 		      unsigned int planemask)
    593 {
    594   TDFXPtr pTDFX;
    595 
    596   TDFXTRACEACCEL("TDFXSetupForSolidLine\n");
    597   pTDFX=TDFXPTR(pScrn);
    598   TDFXClearState(pScrn);
    599 
    600   pTDFX->Cmd = (TDFXROPCvt[rop]<<24);
    601 
    602   TDFXMakeRoom(pTDFX, 2);
    603   DECLARE(SSTCP_COLORFORE|SSTCP_COLORBACK);
    604   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, color);
    605   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, color);
    606 }
    607 
    608 static void
    609 TDFXSubsequentSolidTwoPointLine(ScrnInfoPtr pScrn, int srcx, int srcy,
    610 				int dstx, int dsty, int flags)
    611 {
    612   /* Also used by TDFXSubsequentDashedTwoPointLine */
    613   TDFXPtr pTDFX;
    614 
    615   TDFXTRACEACCEL("TDFXSubsequentSolidTwoPointLine "
    616 		 "srcx=%d srcy=%d dstx=%d dsty=%d flags=%d\n",
    617 		 srcx, srcy, dstx, dsty, flags);
    618   pTDFX=TDFXPTR(pScrn);
    619   TDFXMatchState(pTDFX);
    620 
    621   if (flags&OMIT_LAST) pTDFX->Cmd|=SST_2D_POLYLINE;
    622   else pTDFX->Cmd|=SST_2D_LINE;
    623 
    624   TDFXMakeRoom(pTDFX, 3);
    625   DECLARE(SSTCP_SRCXY|SSTCP_DSTXY|SSTCP_COMMAND);
    626   TDFXWriteLong(pTDFX, SST_2D_SRCXY, (srcy&0x1FFF)<<16 | (srcx&0x1FFF));
    627   TDFXWriteLong(pTDFX, SST_2D_DSTXY, (dsty&0x1FFF)<<16 | (dstx&0x1FFF));
    628   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd|SST_2D_GO);
    629 }
    630 
    631 static void
    632 TDFXSubsequentSolidHorVertLine(ScrnInfoPtr pScrn, int x, int y, int len,
    633 			       int dir)
    634 {
    635   TDFXPtr pTDFX;
    636 
    637   TDFXTRACEACCEL("TDFXSubsequentSolidHorVertLine\n");
    638   pTDFX=TDFXPTR(pScrn);
    639   TDFXMatchState(pTDFX);
    640 
    641   TDFXMakeRoom(pTDFX, 3);
    642   DECLARE(SSTCP_SRCXY|SSTCP_DSTXY|SSTCP_COMMAND);
    643   TDFXWriteLong(pTDFX, SST_2D_SRCXY, (y&0x1FFF)<<16 | (x&0x1FFF));
    644   if (dir == DEGREES_0)
    645     TDFXWriteLong(pTDFX, SST_2D_DSTXY, (y&0x1FFF)<<16 | ((x+len)&0x1FFF));
    646   else
    647     TDFXWriteLong(pTDFX, SST_2D_DSTXY, ((y+len)&0x1FFF)<<16 | (x&0x1FFF));
    648   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd|SST_2D_POLYLINE|SST_2D_GO);
    649 }
    650 
    651 static void
    652 TDFXNonTEGlyphRenderer(ScrnInfoPtr pScrn, int x, int y, int n,
    653 		       NonTEGlyphPtr glyphs, BoxPtr pbox, int fg, int rop,
    654 		       unsigned int planemask)
    655 {
    656   TDFXPtr pTDFX;
    657   int ndwords;
    658   int g;
    659   NonTEGlyphPtr glyph;
    660 
    661   TDFXTRACEACCEL("TDFXNonTEGlyphRenderer\n");
    662   pTDFX=TDFXPTR(pScrn);
    663   TDFXClearState(pScrn);
    664   /* Don't bother fixing clip1, we're going to change it anyway */
    665   pTDFX->DrawState&=~DRAW_STATE_CLIP1CHANGED;
    666   TDFXMatchState(pTDFX);
    667   /* We're changing clip1 so make sure we use it and flag it */
    668   pTDFX->Cmd|=SST_2D_USECLIP1;
    669   pTDFX->DrawState|=DRAW_STATE_CLIP1CHANGED;
    670 
    671   pTDFX->Cmd|=(TDFXROPCvt[rop]<<24)|SST_2D_TRANSPARENT_MONOCHROME;
    672   pTDFX->Cmd|=SST_2D_HOSTTOSCRNBLIT;
    673 
    674   TDFXMakeRoom(pTDFX, 6);
    675   DECLARE(SSTCP_CLIP1MIN|SSTCP_CLIP1MAX|SSTCP_SRCFORMAT|
    676 	  SSTCP_SRCXY|SSTCP_COLORFORE|SSTCP_COMMAND);
    677   TDFXWriteLong(pTDFX, SST_2D_CLIP1MIN, ((pbox->y1&0x1FFF)<<16) |
    678 		(pbox->x1&0x1FFF));
    679   TDFXWriteLong(pTDFX, SST_2D_CLIP1MAX, ((pbox->y2&0x1FFF)<<16) |
    680 		(pbox->x2&0x1FFF));
    681 #if X_BYTE_ORDER == X_BIG_ENDIAN
    682   TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, SST_2D_PIXFMT_1BPP |
    683 		SST_2D_SOURCE_PACKING_DWORD | BIT(20));
    684 #else
    685   TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, SST_2D_PIXFMT_1BPP |
    686 		SST_2D_SOURCE_PACKING_DWORD);
    687 #endif
    688   pTDFX->sst2DSrcFmtShadow = SST_2D_PIXFMT_1BPP | SST_2D_SOURCE_PACKING_DWORD;
    689   TDFXWriteLong(pTDFX, SST_2D_SRCXY, 0);
    690   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, fg);
    691   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd);
    692 
    693   for (g=0, glyph=glyphs; g<n; g++, glyph++) {
    694     int dx = x+glyph->start;
    695     int dy = y-glyph->yoff;
    696     int w = glyph->end - glyph->start;
    697     int *glyph_data = (int*)glyph->bits;
    698 
    699     if (!glyph->srcwidth) continue;
    700     ndwords = (glyph->srcwidth+3)>>2;
    701     ndwords *= glyph->height;
    702 
    703     TDFXMakeRoom(pTDFX, 2);
    704     DECLARE(SSTCP_DSTSIZE|SSTCP_DSTXY);
    705     TDFXWriteLong(pTDFX, SST_2D_DSTSIZE, ((glyph->height&0x1FFF)<<16) |
    706 		  (w&0x1FFF));
    707     TDFXWriteLong(pTDFX, SST_2D_DSTXY, ((dy&0x1FFF)<<16) | (dx&0x1FFF));
    708 
    709     do {
    710       int i = ndwords;
    711       int j;
    712 
    713       if (i>30) i=30;
    714       TDFXMakeRoom(pTDFX, i);
    715       DECLARE_LAUNCH(i, 0);
    716       for (j=0; j<i; j++) {
    717 #if X_BYTE_ORDER == X_BIG_ENDIAN
    718 	TDFXWriteLong(pTDFX, SST_2D_LAUNCH, *glyph_data);
    719 #else
    720 	TDFXWriteLong(pTDFX, SST_2D_LAUNCH, XAAReverseBitOrder(*glyph_data));
    721 #endif
    722 	glyph_data++;
    723       }
    724       ndwords -= i;
    725     } while (ndwords);
    726   }
    727 }
    728 
    729 static void
    730 TDFXSetupForDashedLine(ScrnInfoPtr pScrn, int fg, int bg, int rop,
    731                        unsigned int planemask, int length,
    732 		       unsigned char *pattern)
    733 {
    734   TDFXPtr pTDFX;
    735 #if X_BYTE_ORDER == X_BIG_ENDIAN
    736   unsigned int pat = *(unsigned int *)pattern;
    737 #endif
    738 
    739   TDFXTRACEACCEL("TDFXSetupForDashedLine\n");
    740   pTDFX=TDFXPTR(pScrn);
    741 
    742 #if X_BYTE_ORDER == X_BIG_ENDIAN
    743   pat=((pat & 0xAAAAAAAA) >> 1) | ((pat & 0x55555555) << 1);
    744   pat=((pat & 0xCCCCCCCC) >> 2) | ((pat & 0x33333333) << 2);
    745   pat=((pat & 0xF0F0F0F0) >> 4) | ((pat & 0x0F0F0F0F) << 4);
    746   pat=((pat & 0xFF00FF00) >> 8) | ((pat & 0x00FF00FF) << 8);
    747   pat=((pat & 0xFFFF0000) >> 16) | ((pat & 0x0000FFFF) << 16);
    748 #endif
    749 
    750   TDFXClearState(pScrn);
    751 
    752   pTDFX->Cmd = (TDFXROPCvt[rop]<<24) | SST_2D_STIPPLE_LINE;
    753   if(bg == -1) {
    754     pTDFX->Cmd |= SST_2D_TRANSPARENT_MONOCHROME;
    755   }
    756   pTDFX->DashedLineSize = ((length-1)&0xFF)+1;
    757 
    758   TDFXMakeRoom(pTDFX, 3);
    759   DECLARE(SSTCP_COLORFORE|SSTCP_COLORBACK|SSTCP_LINESTIPPLE);
    760 #if X_BYTE_ORDER == X_BIG_ENDIAN
    761   TDFXWriteLong(pTDFX, SST_2D_LINESTIPPLE, pat);
    762 #else
    763   TDFXWriteLong(pTDFX, SST_2D_LINESTIPPLE, *(int *)pattern);
    764 #endif
    765   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, bg);
    766   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, fg);
    767 }
    768 
    769 static void
    770 TDFXSubsequentDashedTwoPointLine(ScrnInfoPtr pScrn, int x1, int y1,
    771                                  int x2, int y2, int flags, int phase)
    772 {
    773   TDFXPtr pTDFX;
    774   int linestyle;
    775 
    776   TDFXTRACEACCEL("TDFXSubsequentDashedTwoPointLine\n");
    777   pTDFX=TDFXPTR(pScrn);
    778 
    779   linestyle = ((pTDFX->DashedLineSize-1)<<8) |
    780               (((phase%pTDFX->DashedLineSize)&0x1F)<<24);
    781 
    782   TDFXMakeRoom(pTDFX, 1);
    783   DECLARE(SSTCP_LINESTYLE);
    784   TDFXWriteLong(pTDFX, SST_2D_LINESTYLE, linestyle);
    785 
    786   TDFXSubsequentSolidTwoPointLine(pScrn, x1, y1, x2, y2, flags);
    787 }
    788 
    789 #ifdef ENABLE_SS_COLOR_EXPAND_FILL
    790 static void
    791 TDFXSetupForScreenToScreenColorExpandFill(ScrnInfoPtr pScrn, int fg, int bg,
    792                                           int rop, unsigned int planemask)
    793 {
    794   TDFXPtr pTDFX;
    795 
    796   TDFXTRACEACCEL("TDFXSetupForScreenToScreenColorExpandFill\n");
    797   pTDFX=TDFXPTR(pScrn);
    798   TDFXClearState(pScrn);
    799 
    800   TDFXMatchState(pTDFX);
    801   pTDFX->Cmd|=SST_2D_SCRNTOSCRNBLIT|(TDFXROPCvt[rop]<<24);
    802 
    803   if (bg==-1) {
    804     pTDFX->Cmd |= SST_2D_TRANSPARENT_MONOCHROME;
    805   }
    806   TDFXMakeRoom(pTDFX, 2);
    807   DECLARE(SSTCP_COLORFORE|SSTCP_COLORBACK);
    808   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, bg);
    809   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, fg);
    810 }
    811 
    812 static void
    813 TDFXSubsequentScreenToScreenColorExpandFill(ScrnInfoPtr pScrn, int x, int y,
    814                                             int w, int h, int srcx, int srcy,
    815                                             int offset)
    816 {
    817   TDFXPtr pTDFX;
    818   int fmt;
    819 
    820   TDFXTRACEACCEL("TDFXSubsequentScreenToScreenColorExpandFill "
    821 		 "x=%d y=%d w=%d h=%d srcx=%d srcy=%d offset=%d\n",
    822 		 x, y, w, h, srcx, srcy, offset);
    823   pTDFX=TDFXPTR(pScrn);
    824   /* Don't bother resetting clip1 since we're changing it anyway */
    825   pTDFX->DrawState&=~DRAW_STATE_CLIP1CHANGED;
    826   TDFXMatchState(pTDFX);
    827   /* We're changing clip1 so make sure we use it and flag it */
    828   pTDFX->Cmd|=SST_2D_USECLIP1;
    829   pTDFX->DrawState|=DRAW_STATE_CLIP1CHANGED;
    830 
    831   if (srcy>=pTDFX->prevBlitDest.y1-8 && srcy<=pTDFX->prevBlitDest.y1) {
    832     TDFXSendNOP(pScrn);
    833   }
    834 
    835   if (pTDFX->cpp==1) fmt=(1<<16)|pTDFX->stride;
    836   else fmt=(pTDFX->cpp+1)<<16|pTDFX->stride;
    837 
    838   TDFXMakeRoom(pTDFX, 8);
    839   DECLARE(SSTCP_SRCFORMAT|SSTCP_SRCXY|SSTCP_DSTFORMAT |
    840 	  SSTCP_DSTSIZE|SSTCP_DSTXY|SSTCP_COMMAND |
    841 	  SSTCP_CLIP1MIN|SSTCP_CLIP1MAX);
    842   TDFXWriteLong(pTDFX,SST_2D_DSTFORMAT, fmt);
    843   pTDFX->sst2DDstFmtShadow = fmt;
    844   TDFXWriteLong(pTDFX,SST_2D_CLIP1MIN, (x&0x1FFF) | ((y&0x1FFF)<<16));
    845   TDFXWriteLong(pTDFX,SST_2D_CLIP1MAX, ((x+w)&0x1FFF) | (((y+h)&0x1FFF)<<16));
    846   TDFXWriteLong(pTDFX,SST_2D_SRCFORMAT, pTDFX->stride);
    847   pTDFX->sst2DSrcFmtShadow = pTDFX->stride;
    848   TDFXWriteLong(pTDFX,SST_2D_SRCXY, (srcx&0x1FFF) | ((srcy&0x1FFF)<<16));
    849   TDFXWriteLong(pTDFX,SST_2D_DSTSIZE, ((w+offset)&0x1FFF) | ((h&0x1FFF)<<16));
    850   TDFXWriteLong(pTDFX,SST_2D_DSTXY, ((x-offset)&0x1FFF) | ((y&0x1FFF)<<16));
    851   TDFXWriteLong(pTDFX,SST_2D_COMMAND, pTDFX->Cmd|SST_2D_GO);
    852 
    853   pTDFX->prevBlitDest.y1=y;
    854 }
    855 #endif
    856 
    857 static void
    858 TDFXSetupForCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int fg, int bg,
    859                                        int rop, unsigned int planemask)
    860 {
    861   TDFXPtr pTDFX;
    862 
    863   TDFXTRACEACCEL("SetupForCPUToScreenColorExpandFill bg=%x fg=%x rop=%d\n",
    864                  bg, fg, rop);
    865   pTDFX=TDFXPTR(pScrn);
    866   TDFXClearState(pScrn);
    867 
    868   pTDFX->Cmd|=SST_2D_HOSTTOSCRNBLIT|(TDFXROPCvt[rop]<<24);
    869 
    870   if (bg == -1) {
    871     pTDFX->Cmd |= SST_2D_TRANSPARENT_MONOCHROME;
    872   }
    873 
    874   TDFXMakeRoom(pTDFX, 2);
    875   DECLARE(SSTCP_COLORBACK|SSTCP_COLORFORE);
    876   TDFXWriteLong(pTDFX, SST_2D_COLORBACK, bg);
    877   TDFXWriteLong(pTDFX, SST_2D_COLORFORE, fg);
    878 }
    879 
    880 static void
    881 TDFXSubsequentCPUToScreenColorExpandFill(ScrnInfoPtr pScrn, int x, int y,
    882                                          int w, int h, int skipleft)
    883 {
    884   TDFXPtr pTDFX;
    885   int fmt;
    886 
    887   TDFXTRACEACCEL("SubsequentCPUToScreenColorExpandFill x=%d y=%d w=%d h=%d"
    888                  " skipleft=%d\n", x, y, w, h, skipleft);
    889   pTDFX = TDFXPTR(pScrn);
    890 
    891   /* We're changing clip1 anyway, so don't bother to reset it */
    892   pTDFX->DrawState&=~DRAW_STATE_CLIP1CHANGED;
    893   TDFXMatchState(pTDFX);
    894   /* Make sure we use clip1 and flag it */
    895   pTDFX->Cmd|=SST_2D_USECLIP1;
    896   pTDFX->DrawState|=DRAW_STATE_CLIP1CHANGED;
    897 
    898   if (pTDFX->cpp==1) fmt=(1<<16)|pTDFX->stride;
    899   else fmt=((pTDFX->cpp+1)<<16)|pTDFX->stride;
    900   pTDFX->scanlineWidth=w;
    901 
    902   TDFXMakeRoom(pTDFX, 8);
    903   DECLARE(SSTCP_CLIP1MIN|SSTCP_CLIP1MAX|SSTCP_SRCFORMAT|
    904 	  SSTCP_DSTFORMAT|SSTCP_DSTSIZE|SSTCP_SRCXY|
    905 	  SSTCP_DSTXY|SSTCP_COMMAND);
    906   TDFXWriteLong(pTDFX, SST_2D_DSTFORMAT, fmt);
    907   pTDFX->sst2DDstFmtShadow = fmt;
    908   TDFXWriteLong(pTDFX, SST_2D_CLIP1MIN, ((y&0x1FFF)<<16)|(x&0x1FFF));
    909   TDFXWriteLong(pTDFX, SST_2D_CLIP1MAX, (((y+h)&0x1FFF)<<16)|((x+w)&0x1FFF));
    910 #if X_BYTE_ORDER == X_BIG_ENDIAN
    911   /* bit 20 byte swizzle */
    912   TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT, ((((w+31)/32)*4) & 0x3FFF) | BIT(20));
    913 #else
    914   TDFXWriteLong(pTDFX, SST_2D_SRCFORMAT,  (((w+31)/32)*4) & 0x3FFF);
    915 #endif
    916   pTDFX->sst2DSrcFmtShadow = (((w+31)/32)*4) & 0x3FFF;
    917   TDFXWriteLong(pTDFX, SST_2D_SRCXY, skipleft&0x1F);
    918   TDFXWriteLong(pTDFX, SST_2D_DSTSIZE, ((w-skipleft)&0x1FFF)|((h&0x1FFF)<<16));
    919   TDFXWriteLong(pTDFX, SST_2D_DSTXY, ((x+skipleft)&0x1FFF) | ((y&0x1FFF)<<16));
    920   TDFXWriteLong(pTDFX, SST_2D_COMMAND, pTDFX->Cmd|SST_2D_GO);
    921 }
    922 
    923 static void TDFXSubsequentColorExpandScanline(ScrnInfoPtr pScrn, int bufno)
    924 {
    925   TDFXPtr pTDFX;
    926   int i, size, cnt;
    927   CARD32 *pos;
    928 
    929   TDFXTRACEACCEL("SubsequentColorExpandScanline bufno=%d\n", bufno);
    930   pTDFX = TDFXPTR(pScrn);
    931 
    932   cnt=(pTDFX->scanlineWidth+31)/32;
    933   pos=(CARD32 *)pTDFX->scanlineColorExpandBuffers[bufno];
    934   while (cnt>0) {
    935     if (cnt>64) size=64;
    936     else size=cnt;
    937     TDFXMakeRoom(pTDFX, size);
    938     DECLARE_LAUNCH(size, 0);
    939     for (i=0; i<size; i++, pos++) {
    940       TDFXWriteLong(pTDFX, SST_2D_LAUNCH, *pos);
    941     }
    942     cnt-=size;
    943   }
    944 }
    945 
    946 #endif
    947