1fc5a983dSmrg/* 2fc5a983dSmrg Copyright (c) 1999, The XFree86 Project Inc. 3fc5a983dSmrg Written by Mark Vojkovich <markv@valinux.com> 4fc5a983dSmrg*/ 5fc5a983dSmrg 6fc5a983dSmrg#ifdef HAVE_CONFIG_H 7fc5a983dSmrg#include "config.h" 8fc5a983dSmrg#endif 9fc5a983dSmrg 10fc5a983dSmrg#include "nv_local.h" 11fc5a983dSmrg#include "nv_include.h" 12fc5a983dSmrg#include "nv_type.h" 13fc5a983dSmrg#include "shadowfb.h" 14fc5a983dSmrg#include "servermd.h" 15fc5a983dSmrg 166257f37dSmrgvoid 176257f37dSmrgNVShadowUpdate (ScreenPtr pScreen, shadowBufPtr pBuf) 186257f37dSmrg{ 196257f37dSmrg RegionPtr damage = DamageRegion(pBuf->pDamage); 206257f37dSmrg ScrnInfoPtr pScrn; 216257f37dSmrg pScrn = xf86ScreenToScrn(pScreen); 226257f37dSmrg 236257f37dSmrg (NVPTR(pScrn))->refreshArea (pScrn, REGION_NUM_RECTS(damage), 246257f37dSmrg REGION_RECTS(damage)); 256257f37dSmrg} 266257f37dSmrg 27fc5a983dSmrg 28fc5a983dSmrgvoid 29fc5a983dSmrgNVRefreshArea(ScrnInfoPtr pScrn, int num, BoxPtr pbox) 30fc5a983dSmrg{ 31fc5a983dSmrg NVPtr pNv = NVPTR(pScrn); 32fc5a983dSmrg int width, height, Bpp, FBPitch; 33fc5a983dSmrg unsigned char *src, *dst; 34fc5a983dSmrg 35fc5a983dSmrg Bpp = pScrn->bitsPerPixel >> 3; 36fc5a983dSmrg FBPitch = BitmapBytePad(pScrn->displayWidth * pScrn->bitsPerPixel); 37fc5a983dSmrg 38fc5a983dSmrg while(num--) { 39fc5a983dSmrg width = (pbox->x2 - pbox->x1) * Bpp; 40fc5a983dSmrg height = pbox->y2 - pbox->y1; 41fc5a983dSmrg src = pNv->ShadowPtr + (pbox->y1 * pNv->ShadowPitch) + 42fc5a983dSmrg (pbox->x1 * Bpp); 43fc5a983dSmrg dst = pNv->FbStart + (pbox->y1 * FBPitch) + (pbox->x1 * Bpp); 44fc5a983dSmrg 45fc5a983dSmrg while(height--) { 46fc5a983dSmrg memcpy(dst, src, width); 47fc5a983dSmrg dst += FBPitch; 48fc5a983dSmrg src += pNv->ShadowPitch; 49fc5a983dSmrg } 50fc5a983dSmrg 51fc5a983dSmrg pbox++; 52fc5a983dSmrg } 53fc5a983dSmrg} 54fc5a983dSmrg 55fc5a983dSmrgvoid 56bd304fc0SmrgNVPointerMoved(SCRN_ARG_TYPE arg, int x, int y) 57fc5a983dSmrg{ 58bd304fc0Smrg SCRN_INFO_PTR(arg); 59fc5a983dSmrg NVPtr pNv = NVPTR(pScrn); 60fc5a983dSmrg int newX, newY; 61fc5a983dSmrg 62fc5a983dSmrg if(pNv->Rotate == 1) { 63fc5a983dSmrg newX = pScrn->pScreen->height - y - 1; 64fc5a983dSmrg newY = x; 65fc5a983dSmrg } else { 66fc5a983dSmrg newX = y; 67fc5a983dSmrg newY = pScrn->pScreen->width - x - 1; 68fc5a983dSmrg } 69fc5a983dSmrg 70bd304fc0Smrg (*pNv->PointerMoved)(arg, newX, newY); 71fc5a983dSmrg} 72fc5a983dSmrg 73fc5a983dSmrgvoid 74fc5a983dSmrgNVRefreshArea8(ScrnInfoPtr pScrn, int num, BoxPtr pbox) 75fc5a983dSmrg{ 76fc5a983dSmrg NVPtr pNv = NVPTR(pScrn); 77fc5a983dSmrg int count, width, height, y1, y2, dstPitch, srcPitch; 78fc5a983dSmrg CARD8 *dstPtr, *srcPtr, *src; 79fc5a983dSmrg CARD32 *dst; 80fc5a983dSmrg 81fc5a983dSmrg if(!pNv->Rotate) { 82fc5a983dSmrg NVRefreshArea(pScrn, num, pbox); 83fc5a983dSmrg return; 84fc5a983dSmrg } 85fc5a983dSmrg 86fc5a983dSmrg dstPitch = pScrn->displayWidth; 87fc5a983dSmrg srcPitch = -pNv->Rotate * pNv->ShadowPitch; 88fc5a983dSmrg 89fc5a983dSmrg while(num--) { 90fc5a983dSmrg width = pbox->x2 - pbox->x1; 91fc5a983dSmrg y1 = pbox->y1 & ~3; 92fc5a983dSmrg y2 = (pbox->y2 + 3) & ~3; 93fc5a983dSmrg height = (y2 - y1) >> 2; /* in dwords */ 94fc5a983dSmrg 95fc5a983dSmrg if(pNv->Rotate == 1) { 96fc5a983dSmrg dstPtr = pNv->FbStart + 97fc5a983dSmrg (pbox->x1 * dstPitch) + pScrn->virtualX - y2; 98fc5a983dSmrg srcPtr = pNv->ShadowPtr + ((1 - y2) * srcPitch) + pbox->x1; 99fc5a983dSmrg } else { 100fc5a983dSmrg dstPtr = pNv->FbStart + 101fc5a983dSmrg ((pScrn->virtualY - pbox->x2) * dstPitch) + y1; 102fc5a983dSmrg srcPtr = pNv->ShadowPtr + (y1 * srcPitch) + pbox->x2 - 1; 103fc5a983dSmrg } 104fc5a983dSmrg 105fc5a983dSmrg while(width--) { 106fc5a983dSmrg src = srcPtr; 107fc5a983dSmrg dst = (CARD32*)dstPtr; 108fc5a983dSmrg count = height; 109fc5a983dSmrg while(count--) { 110fc5a983dSmrg *(dst++) = src[0] | (src[srcPitch] << 8) | 111fc5a983dSmrg (src[srcPitch * 2] << 16) | 112fc5a983dSmrg (src[srcPitch * 3] << 24); 113fc5a983dSmrg src += srcPitch * 4; 114fc5a983dSmrg } 115fc5a983dSmrg srcPtr += pNv->Rotate; 116fc5a983dSmrg dstPtr += dstPitch; 117fc5a983dSmrg } 118fc5a983dSmrg 119fc5a983dSmrg pbox++; 120fc5a983dSmrg } 121fc5a983dSmrg} 122fc5a983dSmrg 123fc5a983dSmrg 124fc5a983dSmrgvoid 125fc5a983dSmrgNVRefreshArea16(ScrnInfoPtr pScrn, int num, BoxPtr pbox) 126fc5a983dSmrg{ 127fc5a983dSmrg NVPtr pNv = NVPTR(pScrn); 128fc5a983dSmrg int count, width, height, y1, y2, dstPitch, srcPitch; 129fc5a983dSmrg CARD16 *dstPtr, *srcPtr, *src; 130fc5a983dSmrg CARD32 *dst; 131fc5a983dSmrg 132fc5a983dSmrg if(!pNv->Rotate) { 133fc5a983dSmrg NVRefreshArea(pScrn, num, pbox); 134fc5a983dSmrg return; 135fc5a983dSmrg } 136fc5a983dSmrg 137fc5a983dSmrg dstPitch = pScrn->displayWidth; 138fc5a983dSmrg srcPitch = -pNv->Rotate * pNv->ShadowPitch >> 1; 139fc5a983dSmrg 140fc5a983dSmrg while(num--) { 141fc5a983dSmrg width = pbox->x2 - pbox->x1; 142fc5a983dSmrg y1 = pbox->y1 & ~1; 143fc5a983dSmrg y2 = (pbox->y2 + 1) & ~1; 144fc5a983dSmrg height = (y2 - y1) >> 1; /* in dwords */ 145fc5a983dSmrg 146fc5a983dSmrg if(pNv->Rotate == 1) { 147fc5a983dSmrg dstPtr = (CARD16*)pNv->FbStart + 148fc5a983dSmrg (pbox->x1 * dstPitch) + pScrn->virtualX - y2; 149fc5a983dSmrg srcPtr = (CARD16*)pNv->ShadowPtr + 150fc5a983dSmrg ((1 - y2) * srcPitch) + pbox->x1; 151fc5a983dSmrg } else { 152fc5a983dSmrg dstPtr = (CARD16*)pNv->FbStart + 153fc5a983dSmrg ((pScrn->virtualY - pbox->x2) * dstPitch) + y1; 154fc5a983dSmrg srcPtr = (CARD16*)pNv->ShadowPtr + 155fc5a983dSmrg (y1 * srcPitch) + pbox->x2 - 1; 156fc5a983dSmrg } 157fc5a983dSmrg 158fc5a983dSmrg while(width--) { 159fc5a983dSmrg src = srcPtr; 160fc5a983dSmrg dst = (CARD32*)dstPtr; 161fc5a983dSmrg count = height; 162fc5a983dSmrg while(count--) { 163fc5a983dSmrg *(dst++) = src[0] | (src[srcPitch] << 16); 164fc5a983dSmrg src += srcPitch * 2; 165fc5a983dSmrg } 166fc5a983dSmrg srcPtr += pNv->Rotate; 167fc5a983dSmrg dstPtr += dstPitch; 168fc5a983dSmrg } 169fc5a983dSmrg 170fc5a983dSmrg pbox++; 171fc5a983dSmrg } 172fc5a983dSmrg} 173fc5a983dSmrg 174fc5a983dSmrg 175fc5a983dSmrgvoid 176fc5a983dSmrgNVRefreshArea32(ScrnInfoPtr pScrn, int num, BoxPtr pbox) 177fc5a983dSmrg{ 178fc5a983dSmrg NVPtr pNv = NVPTR(pScrn); 179fc5a983dSmrg int count, width, height, dstPitch, srcPitch; 180fc5a983dSmrg CARD32 *dstPtr, *srcPtr, *src, *dst; 181fc5a983dSmrg 182fc5a983dSmrg if(!pNv->Rotate) { 183fc5a983dSmrg NVRefreshArea(pScrn, num, pbox); 184fc5a983dSmrg return; 185fc5a983dSmrg } 186fc5a983dSmrg 187fc5a983dSmrg dstPitch = pScrn->displayWidth; 188fc5a983dSmrg srcPitch = -pNv->Rotate * pNv->ShadowPitch >> 2; 189fc5a983dSmrg 190fc5a983dSmrg while(num--) { 191fc5a983dSmrg width = pbox->x2 - pbox->x1; 192fc5a983dSmrg height = pbox->y2 - pbox->y1; 193fc5a983dSmrg 194fc5a983dSmrg if(pNv->Rotate == 1) { 195fc5a983dSmrg dstPtr = (CARD32*)pNv->FbStart + 196fc5a983dSmrg (pbox->x1 * dstPitch) + pScrn->virtualX - pbox->y2; 197fc5a983dSmrg srcPtr = (CARD32*)pNv->ShadowPtr + 198fc5a983dSmrg ((1 - pbox->y2) * srcPitch) + pbox->x1; 199fc5a983dSmrg } else { 200fc5a983dSmrg dstPtr = (CARD32*)pNv->FbStart + 201fc5a983dSmrg ((pScrn->virtualY - pbox->x2) * dstPitch) + pbox->y1; 202fc5a983dSmrg srcPtr = (CARD32*)pNv->ShadowPtr + 203fc5a983dSmrg (pbox->y1 * srcPitch) + pbox->x2 - 1; 204fc5a983dSmrg } 205fc5a983dSmrg 206fc5a983dSmrg while(width--) { 207fc5a983dSmrg src = srcPtr; 208fc5a983dSmrg dst = dstPtr; 209fc5a983dSmrg count = height; 210fc5a983dSmrg while(count--) { 211fc5a983dSmrg *(dst++) = *src; 212fc5a983dSmrg src += srcPitch; 213fc5a983dSmrg } 214fc5a983dSmrg srcPtr += pNv->Rotate; 215fc5a983dSmrg dstPtr += dstPitch; 216fc5a983dSmrg } 217fc5a983dSmrg 218fc5a983dSmrg pbox++; 219fc5a983dSmrg } 220fc5a983dSmrg} 221