📄 gpeaccel.cpp
字号:
//
if (!pBltParms->xPositive)
{
// dstX += (width - 1);
// DstCntl &= ~DST_X_LEFT_TO_RIGHT;
DebugBreak();
}
if (!pBltParms->yPositive)
{
// dstY += (height - 1);
// DstCntl &= ~DST_Y_TOP_TO_BOTTOM;
DebugBreak();
}
//
// Calculate the number of bytes from the start of the line.
//
ulRightByteCount = right * BytesPerPixel;
ulLeftByteCount = left * BytesPerPixel;
//
// Start of the Physical buffer.
//
ulPhyStart = top * stride + ulLeftByteCount + pDst->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY;
ulPhyEnd = bottom * stride + ulRightByteCount + pDst->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY;
#ifdef DD_ENABLE
FlushDCache();
#endif
WaitForNotBusy();
//
// Height in line of the block to be Filled.
//
*GRAPHICS_BLKDESTHEIGHT = bottom - top - 1 ;
//
// Starting Physical address of the the block to be filled.
//
*GRAPHICS_BLKDESTSTRT = ulPhyStart ;
//
// Starting and ending offset within a 32 bit word.
//
*GRAPHICS_DESTPIXELSTRT = ((ulPhyStart & 3) << 3) |
//(((ulPhyEnd - BytesPerPixel) & 3) <<(DESTPIXELSTRT_EPEL_SHIFT + 3));
(((prclDst->right * BytesPerPixel - BytesPerPixel) & 3) <<(DESTPIXELSTRT_EPEL_SHIFT + 3));
//
//
// BLKDESTWIDTH is the number of full and partial words - 1.
//
//
// 0 1 2 3 | 4 5 6 7 | 8 9 10 11| 12 13
// +---+---+---+---+---+---+---+---+---+---+---+---+---+---+
// | | | | X | X | X | X | X | X | X | X | X | X | X |
// +---+---+---+---+---+---+---+---+---+---+---+---+---+---+
// | | |
//
// |<--- (ulRightByteCount>>2) --->|
// - (ulLeftByteCount>>2)
// +1 ->| |<- +1
//
//
*GRAPHICS_BLKDESTWIDTH = (ulRightByteCount>>2) +
((ulRightByteCount & 3)?1:0) +
((ulLeftByteCount & 3)?1:0) -
((ulLeftByteCount + 3)>>2) - 1;
//
// Number of words per line.
//
*GRAPHICS_DESTLINELENGTH = stride>>2;
//
// These values are all zero.
//
*GRAPHICS_BLKSRCSTRT = 0;
*GRAPHICS_SRCPIXELSTRT = 0;
*GRAPHICS_BLKSRCWIDTH = 0;
*GRAPHICS_SRCLINELENGTH = 0;
*GRAPHICS_LINEINC = 0;
*GRAPHICS_LINEINIT = 0;
*GRAPHICS_LINEPATTRN = 0;
*GRAPHICS_TRANSPATTRN = 0;
//
// I don't think that this is used.
//
*GRAPHICS_BACKGROUND = 0;
//
// I am not sure if the solid color has to be converted to
//
*GRAPHICS_BLOCKMASK = pBltParms->solidColor;
//
// Set up the block control register.
//
//*GRAPHICS_BLOCKCTRL = 0;
//*GRAPHICS_BLOCKCTRL = ulBlockControl = BLOCKCTRL_FILL;
//
// This calculation doesn't work for 32 bits per pixel.
//
//*GRAPHICS_BLOCKCTRL = ulBlockControl |= (BytesPerPixel << (BLOCKCTRL_PIXEL_SHIFT + 1));
ulBlockControl = BLOCKCTRL_FILL | (BytesPerPixel << (BLOCKCTRL_PIXEL_SHIFT + 1));
//
// Start the graphics process.
//
*GRAPHICS_BLOCKCTRL = ulBlockControl | BLOCKCTRL_ENABLE ;
return S_OK;
}
//****************************************************************************
// GPEAccel::AcceleratedSrcCopyBlt
//****************************************************************************
// Use the accelerated block copy.
//
SCODE GPEAccel::AcceleratedSrcCopyBlt (GPEBltParms *pBltParms)
{
DWORD oldMode;
oldMode = SetKMode(TRUE);
GPE93xxSurf *pSrc = (GPE93xxSurf*)pBltParms->pSrc;
GPE93xxSurf *pDst = (GPE93xxSurf*)pBltParms->pDst;
int srcX, srcY;
int dstX = pBltParms->prclDst->left; // left of dest rect
int dstY = pBltParms->prclDst->top; // top of dest rect
int width = pBltParms->prclDst->right - pBltParms->prclDst->left; // Rectangle Width Data Store
int height = pBltParms->prclDst->bottom - pBltParms->prclDst->top; // Rectangle Height Data Store
int BytesPerPixelDst = EGPEFormatToBpp[pDst->Format()] >> 3;
int BytesPerPixelSrc = EGPEFormatToBpp[pSrc->Format()] >> 3;
int swidth = pBltParms->prclSrc->right - pBltParms->prclSrc->left; // Rectangle Width Data Store
int sheight = pBltParms->prclSrc->bottom - pBltParms->prclSrc->top; // Rectangle Height Data Store
int iDstScanStride, iSrcScanStride;
unsigned long value = BytesPerPixelDst << (BLOCKCTRL_PIXEL_SHIFT + 1) ;
unsigned long dx1, dx2, dy1;
unsigned long sx1, sx2, sy1;
LPVOID pPhysicalStart;
ULONG ulRightByteCount;
ULONG ulLeftByteCount;
DWORD dwBlockMask = pBltParms->solidColor;
//DEBUGMSG (GPE_ZONE_LINE, (TEXT("(%d , %d), (%d , %d), (%d , %d)\r\n"),srcX ,srcY ,dstX ,dstY ,width ,height));
int sl = pBltParms->prclSrc->left;
int sr = pBltParms->prclSrc->right;
int st = pBltParms->prclSrc->top;
int sb = pBltParms->prclSrc->bottom;
int dl = pBltParms->prclDst->left;
int dr = pBltParms->prclDst->right;
int dt = pBltParms->prclDst->top;
int db = pBltParms->prclDst->bottom;
if ( (pSrc->OffsetInVideoMemory() == pDst->OffsetInVideoMemory() ) &&
((sl<dl && dl<sr)||(dl<sl && sl<dr)||(dl==sl && dr==sr)) &&
((st<dt && dt<sb)||(dt<st && st<db )||(dt==st && db==sb)))
{
//RETAILMSG(1, (TEXT("!!!Dst and Src overlaps!\r\n")));
return EmulatedBlt(pBltParms);
}
//RETAILMSG(1, (TEXT("phy address 0x%08x sl %3d sr %3d st %3d sb %3d dl %3d dr %3d dt %3d db %3d \r\n"),
// pDst->AddressPhy(), sl,sr,st,sb, dl,dr,dt,db));
//
// Protection against the following cases.
//
if ((dstX >= m_nScreenWidth) ||
(dstY >= m_nScreenHeight) ||
((dstX + width - 1) >= m_nScreenWidth) ||
((dstY + height - 1) >= m_nScreenHeight))
{
DEBUGMSG (GPE_ZONE_LINE, (TEXT("!!!error: Out of screen!\r\n")));
return EmulatedBlt(pBltParms);
}
if( BytesPerPixelDst!= BytesPerPixelSrc )
{
//DEBUGMSG (GPE_ZONE_LINE, (TEXT("!!!BytesPerPixelDst %d != BytesPerPixelSrc %d! error: have not supported!\r\n"),BytesPerPixelDst, BytesPerPixelSrc));
return EmulatedBlt(pBltParms);
}
switch (pBltParms->rop4)
{
case 0x6666: // SRCINVERT
value |= BLOCKCTRL_DMODE_XOR;
break;
case 0x8888: // SRCAND
value |= BLOCKCTRL_DMODE_AND;
break;
case 0xCCCC: // SRCCOPY
value |= BLOCKCTRL_DMODE_DISABLED;
break;
case 0xEEEE: // SRCPAINT
value |= BLOCKCTRL_DMODE_OR;
break;
case 0x3333: // NOTSRCCOPY
dwBlockMask = 0xFFFFFF;
value |= BLOCKCTRL_MMODE_XOR ;
break;
default:
//RETAILMSG(1, (TEXT("!!!Unsupported ROP4!\r\n")));
return EmulatedBlt(pBltParms);
}
//
// Prepare parameters.
//
srcX = pBltParms->prclSrc->left; // left of source rect
srcY = pBltParms->prclSrc->top; // top of source rect
iDstScanStride = pDst->Stride();
iSrcScanStride = pSrc->Stride();
dx1 = dstX;
dy1 = dstY;
dx2 = dstX + width - 1;
ULONG ulSrcRightByteCount = pBltParms->prclSrc->right * BytesPerPixelSrc;
ULONG ulSrcLeftByteCount = pBltParms->prclSrc->left * BytesPerPixelSrc;
ulRightByteCount = pBltParms->prclDst->right * BytesPerPixelDst;
ulLeftByteCount = pBltParms->prclDst->left * BytesPerPixelDst;
sx1 = srcX;
sy1 = srcY;
sx2 = srcX + swidth - 1;
if(iSrcScanStride<0)
{
pPhysicalStart = (LPVOID)( pSrc->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY + ( sheight -srcY -1 ) * abs(iSrcScanStride) + srcX * BytesPerPixelDst );
value |= BLOCKCTRL_SYDIR;
}
else
{
pPhysicalStart = (LPVOID) ( pSrc->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY + srcY * iSrcScanStride + srcX * BytesPerPixelDst );
}
ULONG ulDstPhyStart = pDst->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY + pBltParms->prclDst->top * iDstScanStride + pBltParms->prclDst->left * BytesPerPixelDst;
ULONG ulDstPhyEnd = pDst->OffsetInVideoMemory() + FRAMEBUF_PHYSICAL_MEMORY + pBltParms->prclDst->bottom * iDstScanStride + pBltParms->prclDst->right * BytesPerPixelDst;
#ifdef DD_ENABLE
FlushDCache();
#endif
WaitForNotBusy();
//
// Set accelerator registers.
//
*GRAPHICS_SRCPIXELSTRT = ((ULONG)pPhysicalStart & 3) << 3;
*GRAPHICS_SRCLINELENGTH = iSrcScanStride >> 2;
*GRAPHICS_BLKSRCWIDTH = ( ulSrcRightByteCount>>2) +
((ulSrcRightByteCount & 3)?1:0) +
((ulSrcLeftByteCount & 3)?1:0) -
((ulSrcLeftByteCount + 3)>>2);// - 1; !!! Different from what the user guide says.
*GRAPHICS_BLKSRCSTRT = (DWORD)pPhysicalStart;
*GRAPHICS_DESTPIXELSTRT = ((ulDstPhyStart & 3) << 3) |
(((pBltParms->prclDst->right * BytesPerPixelDst - BytesPerPixelDst) & 3)
<<(DESTPIXELSTRT_EPEL_SHIFT + 3));// EPEL relates to the line instead of block.
*GRAPHICS_BLKDESTSTRT = ulDstPhyStart;
*GRAPHICS_DESTLINELENGTH = iDstScanStride >> 2;
*GRAPHICS_BLKDESTWIDTH = (ulRightByteCount>>2) +
((ulRightByteCount & 3)?1:0) +
((ulLeftByteCount & 3)?1:0) -
((ulLeftByteCount + 3)>>2) - 1;
*GRAPHICS_BLKDESTHEIGHT = height - 1;
*GRAPHICS_BLOCKMASK = dwBlockMask;
*GRAPHICS_TRANSPATTRN = 0;
*GRAPHICS_BLOCKCTRL = 0;
*GRAPHICS_LINEINC = 0;
*GRAPHICS_LINEINIT = 0;
*GRAPHICS_LINEPATTRN = 0;
*GRAPHICS_BACKGROUND = 0;
*GRAPHICS_BLOCKCTRL = value | 0x3;
SetKMode(oldMode);
return S_OK;
}
SCODE GPEAccel::AllocSurface(GPESurf **ppSurf, int width, int height, EGPEFormat format, int surfaceFlags)
{
#ifdef DD_ENABLE
return AllocSurface ((DDGPESurf**)ppSurf,
width,
height,
format,
EGPEFormatToEDDGPEPixelFormat[format],
surfaceFlags);
}
SCODE GPEAccel::AllocSurface(DDGPESurf **ppSurf, int width, int height, EGPEFormat format, EDDGPEPixelFormat pixelFormat, int surfaceFlags)
{
#endif // DD_ENABLE
//
// Try to allocate all types of surface memory in videomemory.
//
DWORD bpp = EGPEFormatToBpp[format];
DWORD stride = ((bpp * width + 31) >> 5) << 2;
unsigned int nSizeNeed = stride * height;
if( ( nSizeNeed <= m_pSurfHeap->Available() ) && (bpp == m_ulColorDepth) && (bpp !=4))
{
GPE93xxSurf* pSurf = new GPE93xxSurf(width, height, m_pSurfHeap, m_VideoMemPhyOffet, nSizeNeed, stride, format);
if( pSurf != NULL )
{
*ppSurf = pSurf;
if(pSurf->pNode != NULL )
{
return S_OK;
}
else
{
delete *ppSurf;
}
}
}
else
{
if(surfaceFlags & GPE_REQUIRE_VIDEO_MEMORY)
{
return E_OUTOFMEMORY;
}
}
// Allocate from system memory
#ifdef DD_ENABLE
*ppSurf = new DDGPESurf(width, height, stride, format, pixelFormat);
#else // DD_ENABLE
*ppSurf = new GPESurf(width, height, format);
#endif // DD_ENABLE
if (*ppSurf != NULL)
{{
DWORD dwbuffer=(DWORD)(*ppSurf)->Buffer();
// check we allocated bits succesfully
if (dwbuffer == 0)
{
delete *ppSurf;
}
else
{
return S_OK;
}
}}
DEBUGMSG (GPE_ZONE_LINE, (L"AllocSurface - Out of Memory\n"));
return E_OUTOFMEMORY;
}
#ifdef DD_ENABLE
void GPEAccel::SetVisibleSurface( GPESurf *pTempSurf, BOOL bWaitForVBlank)
{
}
#endif // DD_ENABLE
//****************************************************************************
// GPEAccel::PowerHandler
//****************************************************************************
// Routine that powers up and down the video clocks.
//
//
VOID GPEAccel::PowerHandler( BOOL bOff)
{
ULONG ulTemp;
//
// Unlock the video attributes register.
//
*RASTER_REALITI_SWLOCK = 0xaa;
//
// See if we are power up the system or shutting down the system.
//
if(bOff)
{
//
// Clear the Sleep signal. This turns off the LCD.
//
if( m_Registry.fSleepSignalActive )
{
ulTemp = *GPIO_PADR;
*GPIO_PADR = ulTemp & ~0x2;
}
*RASTER_VIDEOATTRIBS = ~VIDEOATTRIBS_EN & m_ulVideoAttrib ;
}
else
{
//
// Set the Sleep Signal. This turns on the LCD.
//
if( m_Registry.fSleepSignalActive )
{
ulTemp = *GPIO_PADR;
*GPIO_PADR = ulTemp | 0x2;
}
*RASTER_VIDEOATTRIBS = m_ulVideoAttrib ;
}
}
//****************************************************************************
// EightBitTestPattern
//****************************************************************************
// Displays the following colors:
//
// Lt Gray, Red, Green, Yellow, Blue, Violet, Cyan, White.
//
//
void EightBitTestPattern(void)
{
unsigned char *puc = (unsigned char *)FRAMEBUF_VIRTUAL_MEMORY;
int i,j;
for(j = 0; j<240 ;j++)
{
for(i =0 ; i<320; i++)
{
puc[i + j * 320] = 234 + i/40;
}
}
}
//****************************************************************************
// FourBitTestPattern
//****************************************************************************
//
//
//
void FourBitTestPattern(void)
{
unsigned char *puc = (unsigned char *)FRAMEBUF_VIRTUAL_MEMORY;
unsigned char color;
int i,j;
for(j = 0; j<480 ;j++)
{
for(i =0 ; i<320; i++)
{
color = (i/20);
color = color | (color <<4);
puc[i + j * 320] = color;
}
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -