X-Git-Url: https://git.ucc.asn.au/?a=blobdiff_plain;f=KernelLand%2FKernel%2Fdrvutil_video.c;h=2bffb1ae92f0b932eccaf4bda790c02964c55db3;hb=9eadc33399e705035c33e8434a9644d91e44ed44;hp=6e6338697dbd4b0e46f6a844898e611c65d8590f;hpb=15235fb0b42c91513c30117155dc1b5a020baf76;p=tpg%2Facess2.git diff --git a/KernelLand/Kernel/drvutil_video.c b/KernelLand/Kernel/drvutil_video.c index 6e633869..2bffb1ae 100644 --- a/KernelLand/Kernel/drvutil_video.c +++ b/KernelLand/Kernel/drvutil_video.c @@ -58,6 +58,9 @@ int DrvUtil_Video_2DStream(void *Ent, const void *Buffer, int Length, const Uint8 *stream = Buffer; int rem = Length; int op; + + Uint16 tmp[6]; + while( rem ) { rem --; @@ -83,7 +86,8 @@ int DrvUtil_Video_2DStream(void *Ent, const void *Buffer, int Length, case VIDEO_2DOP_NOP: break; case VIDEO_2DOP_FILL: - if(rem < 10) return Length-rem; + if(rem < 12) return Length-rem; + memcpy(tmp, stream, 6*2); if(!Handlers->Fill) { Log_Warning("DrvUtil", "DrvUtil_Video_2DStream: Driver" @@ -92,18 +96,18 @@ int DrvUtil_Video_2DStream(void *Ent, const void *Buffer, int Length, } Handlers->Fill( - Ent, - ((const Uint16*)stream)[0], ((const Uint16*)stream)[1], - ((const Uint16*)stream)[2], ((const Uint16*)stream)[3], - ((const Uint32*)stream)[4] + Ent, + tmp[0], tmp[1], tmp[2], tmp[3], + tmp[4] | ((Uint32)tmp[5] << 16) ); - rem -= 10; - stream += 10; + rem -= 12; + stream += 12; break; case VIDEO_2DOP_BLIT: if(rem < 12) return Length-rem; + memcpy(tmp, stream, 6*2); if(!Handlers->Blit) { Log_Warning("DrvUtil", "DrvUtil_Video_2DStream: Driver" @@ -113,9 +117,8 @@ int DrvUtil_Video_2DStream(void *Ent, const void *Buffer, int Length, Handlers->Blit( Ent, - ((const Uint16*)stream)[0], ((const Uint16*)stream)[1], - ((const Uint16*)stream)[2], ((const Uint16*)stream)[3], - ((const Uint16*)stream)[4], ((const Uint16*)stream)[5] + tmp[0], tmp[1], tmp[2], tmp[3], + tmp[4], tmp[5] ); rem -= 12; @@ -134,12 +137,18 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t int csr_x, csr_y; int x, y; int bytes_per_px = (FBInfo->Depth + 7) / 8; + size_t ofs; ENTER("pFBInfo xOffset xLength pBuffer", FBInfo, Offset, Length, Buffer); csr_x = FBInfo->CursorX; csr_y = FBInfo->CursorY; + if( FBInfo->BackBuffer ) + dest = FBInfo->BackBuffer; + else + dest = FBInfo->Framebuffer; + DrvUtil_Video_RemoveCursor(FBInfo); switch( FBInfo->BufferFormat ) @@ -168,10 +177,9 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t Length = heightInChars*widthInChars - Offset; } - dest = FBInfo->Framebuffer; - LOG("dest = %p", dest); - dest += y * giVT_CharHeight * FBInfo->Pitch; LOG("dest = %p", dest); + ofs = y * giVT_CharHeight * FBInfo->Pitch; + dest += ofs; for( i = 0; i < Length; i++ ) { @@ -198,9 +206,11 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t LOG("dest = %p", dest); } } + if( x > 0 ) + dest += FBInfo->Pitch*giVT_CharHeight; Length = i * sizeof(tVT_Char); - } - break; + + break; } case VIDEO_BUFFMT_FRAMEBUFFER: if(FBInfo->Width*FBInfo->Height*4 < Offset+Length) @@ -214,11 +224,13 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t case 15: case 16: Log_Warning("DrvUtil", "TODO: Support 15/16 bpp modes in LFB write"); + dest = NULL; break; case 24: x = Offset % FBInfo->Width; y = Offset / FBInfo->Width; - dest = (Uint8*)FBInfo->Framebuffer + y*FBInfo->Pitch; + ofs = y*FBInfo->Pitch; + dest += ofs; for( ; Length >= 4; Length -= 4 ) { dest[x*3+0] = *src & 0xFF; @@ -240,25 +252,34 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t x = Offset % FBInfo->Width; y = Offset / FBInfo->Height; - px = (Uint32*)FBInfo->Framebuffer + y*FBInfo->Pitch/4; + ofs = y*FBInfo->Pitch; + dest += ofs; + px = (void*)dest; - for( ; Length >= 4; Length -= 4, x ) + for( ; Length >= 4; Length -= 4 ) { px[x++] = *src ++; if( x == FBInfo->Width ) { x = 0; - px += FBInfo->Pitch; + dest += FBInfo->Pitch; + px = (void*)dest; } } + if( x > 0 ) { + dest += FBInfo->Pitch; + } } else { - dest = (Uint8 *)FBInfo->Framebuffer + Offset; + ofs = Offset; + dest += ofs; memcpy(dest, Buffer, Length); + dest += Length; } break; default: - Log_Warning("DrvUtil", "DrvUtil_Video_WriteLFB - Unknown bit depthn %i", FBInfo->Depth); + Log_Warning("DrvUtil", "DrvUtil_Video_WriteLFB - Unknown bit depth %i", FBInfo->Depth); + dest = NULL; break; } break; @@ -268,12 +289,20 @@ int DrvUtil_Video_WriteLFB(tDrvUtil_Video_BufInfo *FBInfo, size_t Offset, size_t FBInfo, Buffer, Length, &gDrvUtil_Stub_2DFunctions, sizeof(gDrvUtil_Stub_2DFunctions) ); + dest = NULL; break; default: LEAVE('i', -1); return -1; } + if( FBInfo->BackBuffer && dest ) { + void *_dst = (char*)FBInfo->Framebuffer + ofs; + void *_src = (char*)FBInfo->BackBuffer + ofs; + size_t len = ((tVAddr)dest - (tVAddr)FBInfo->BackBuffer) - ofs; + // Log_Debug("DrvUtil", "Copy from BB %p to FB %p 0x%x bytes", _src, _dst, len); + memcpy(_dst, _src, len); + } DrvUtil_Video_DrawCursor(FBInfo, csr_x, csr_y); @@ -321,6 +350,12 @@ int DrvUtil_Video_SetCursor(tDrvUtil_Video_BufInfo *Buf, tVideo_IOCtl_Bitmap *Bi LEAVE('i', -1); return -1; } + ASSERTCR(Bitmap->W, >, 0, -1); + ASSERTCR(Bitmap->H, >, 0, -1); + ASSERTCR(Bitmap->XOfs, <, Bitmap->W, -1); + ASSERTCR(Bitmap->XOfs, >, -Bitmap->W, -1); + ASSERTCR(Bitmap->YOfs, <, Bitmap->H, -1); + ASSERTCR(Bitmap->YOfs, >, -Bitmap->H, -1); // Don't take a copy of the DrvUtil provided cursor if( Bitmap == &gDrvUtil_TextModeCursor ) @@ -378,8 +413,18 @@ void DrvUtil_Video_DrawCursor(tDrvUtil_Video_BufInfo *Buf, int X, int Y) Y -= Buf->CursorBitmap->YOfs; // Get the width of the cursor on screen (clipping to right/bottom edges) - render_w = X > Buf->Width - Buf->CursorBitmap->W ? Buf->Width - X : Buf->CursorBitmap->W; - render_h = Y > Buf->Height - Buf->CursorBitmap->H ? Buf->Height - Y : Buf->CursorBitmap->H; + ASSERTC(Buf->Width, >, 0); + ASSERTC(Buf->Height, >, 0); + ASSERTC(Buf->CursorBitmap->W, >, 0); + ASSERTC(Buf->CursorBitmap->H, >, 0); + + render_w = MIN(Buf->Width - X, Buf->CursorBitmap->W); + render_h = MIN(Buf->Height - Y, Buf->CursorBitmap->H); + //render_w = X > Buf->Width - Buf->CursorBitmap->W ? Buf->Width - X : Buf->CursorBitmap->W; + //render_h = Y > Buf->Height - Buf->CursorBitmap->H ? Buf->Height - Y : Buf->CursorBitmap->H; + + ASSERTC(render_w, >=, 0); + ASSERTC(render_h, >=, 0); // Clipp to left/top edges if(X < 0) { render_ox = -X; X = 0; } @@ -418,6 +463,9 @@ void DrvUtil_Video_RenderCursor(tDrvUtil_Video_BufInfo *Buf) if( !Buf->CursorSaveBuf ) Buf->CursorSaveBuf = malloc( Buf->CursorBitmap->W*Buf->CursorBitmap->H*bytes_per_px ); + ASSERTC(render_w, >=, 0); + ASSERTC(render_h, >=, 0); + LOG("Saving back"); // Save behind the cursor for( y = 0; y < render_h; y ++ ) @@ -432,7 +480,8 @@ void DrvUtil_Video_RenderCursor(tDrvUtil_Video_BufInfo *Buf) { case 15: case 16: - Log_Warning("DrvUtil", "TODO: Support 15/16 bpp modes in cursor draw"); + //Log_Warning("DrvUtil", "TODO: Support 15/16 bpp modes in cursor draw"); + //Proc_PrintBacktrace(); break; case 24: LOG("24-bit render"); @@ -487,8 +536,6 @@ void DrvUtil_Video_RenderCursor(tDrvUtil_Video_BufInfo *Buf) void DrvUtil_Video_RemoveCursor(tDrvUtil_Video_BufInfo *Buf) { int bytes_per_px = (Buf->Depth + 7) / 8; - int y, save_pitch; - Uint8 *dest, *src; // Just a little sanity if( !Buf->CursorBitmap || Buf->CursorX == -1 ) return ; @@ -497,16 +544,21 @@ void DrvUtil_Video_RemoveCursor(tDrvUtil_Video_BufInfo *Buf) // Debug("DrvUtil_Video_RemoveCursor: (Buf=%p) dest_x=%i, dest_y=%i", Buf, Buf->CursorDestX, Buf->CursorDestY); // Set up - save_pitch = Buf->CursorBitmap->W * bytes_per_px; - dest = (Uint8*)Buf->Framebuffer + Buf->CursorDestY * Buf->Pitch + Buf->CursorDestX*bytes_per_px; - src = Buf->CursorSaveBuf; - + size_t save_pitch = Buf->CursorBitmap->W * bytes_per_px; + Uint8 *dst = (Uint8*)Buf->Framebuffer + Buf->CursorDestY * Buf->Pitch + Buf->CursorDestX*bytes_per_px; + const Uint8 *src = Buf->CursorSaveBuf; + + ASSERT(Buf->Framebuffer); + ASSERT(src); + ASSERT(CheckMem(dst, Buf->CursorRenderH*Buf->Pitch)); + ASSERT(CheckMem(src, Buf->CursorRenderH*save_pitch)); + // Copy each line back - for( y = 0; y < Buf->CursorRenderH; y ++ ) + for( int y = 0; y < Buf->CursorRenderH; y ++ ) { - memcpy( dest, src, Buf->CursorRenderW * bytes_per_px ); + memcpy( dst, src, Buf->CursorRenderW * bytes_per_px ); src += save_pitch; - dest += Buf->Pitch; + dst += Buf->Pitch; } // Set the cursor as removed @@ -517,18 +569,35 @@ void DrvUtil_Video_2D_Fill(void *Ent, Uint16 X, Uint16 Y, Uint16 W, Uint16 H, Ui { tDrvUtil_Video_BufInfo *FBInfo = Ent; - // TODO: Handle non-32bit modes - if( FBInfo->Depth != 32 ) return; - - // TODO: Be less hacky - int pitch = FBInfo->Pitch/4; - Uint32 *buf = (Uint32*)FBInfo->Framebuffer + Y*pitch + X; - while( H -- ) { - Uint32 *tmp; - int i; - tmp = buf; - for(i=W;i--;tmp++) *tmp = Colour; - buf += pitch; + switch( FBInfo->Depth ) + { + case 32: { + // TODO: Be less hacky + size_t pitch = FBInfo->Pitch/4; + size_t ofs = Y*pitch + X; + Uint32 *buf = (Uint32*)FBInfo->Framebuffer + ofs; + Uint32 *cbuf = NULL; + if( FBInfo->BackBuffer ) + cbuf = (Uint32*)FBInfo->BackBuffer + ofs; + while( H -- ) + { + Uint32 *line; + line = buf; + for(int i = W; i--; line++) + *line = Colour; + buf += pitch; + if( cbuf ) { + line = cbuf; + for(int i = W; i--; line++ ) + *line = Colour; + cbuf += pitch; + } + } + break; } + default: + // TODO: Handle non-32bit modes + Log_Warning("DrvUtil", "TODO: <32bpp _Fill"); + break; } } @@ -540,6 +609,9 @@ void DrvUtil_Video_2D_Blit(void *Ent, Uint16 DstX, Uint16 DstY, Uint16 SrcX, Uin int dst = DstY*scrnpitch + DstX; int src = SrcY*scrnpitch + SrcX; int tmp; + Uint8 *framebuffer = FBInfo->Framebuffer; + Uint8 *backbuffer = FBInfo->BackBuffer; + Uint8 *sourcebuffer = (FBInfo->BackBuffer ? FBInfo->BackBuffer : FBInfo->Framebuffer); //Log("Vesa_2D_Blit: (Ent=%p, DstX=%i, DstY=%i, SrcX=%i, SrcY=%i, W=%i, H=%i)", // Ent, DstX, DstY, SrcX, SrcY, W, H); @@ -551,26 +623,39 @@ void DrvUtil_Video_2D_Blit(void *Ent, Uint16 DstX, Uint16 DstY, Uint16 SrcX, Uin //Debug("W = %i, H = %i", W, H); - if( dst > src ) { + if(W == FBInfo->Width && FBInfo->Pitch == FBInfo->Width*bytes_per_px) + { + memmove(framebuffer + dst, sourcebuffer + src, H*FBInfo->Pitch); + if( backbuffer ) + memmove(backbuffer + dst, sourcebuffer + src, H*FBInfo->Pitch); + } + else if( dst > src ) + { // Reverse copy dst += H*scrnpitch; src += H*scrnpitch; - while( H -- ) { + while( H -- ) + { dst -= scrnpitch; src -= scrnpitch; tmp = W*bytes_per_px; - for( tmp = W; tmp --; ) { - *((Uint8*)FBInfo->Framebuffer + dst + tmp) = *((Uint8*)FBInfo->Framebuffer + src + tmp); + for( tmp = W; tmp --; ) + { + size_t src_o = src + tmp; + size_t dst_o = src + tmp; + framebuffer[dst_o] = sourcebuffer[src_o]; + if( backbuffer ) + backbuffer[dst_o] = sourcebuffer[src_o]; } } } - else if(W == FBInfo->Width && FBInfo->Pitch == FBInfo->Width*bytes_per_px) { - memmove((Uint8*)FBInfo->Framebuffer + dst, (Uint8*)FBInfo->Framebuffer + src, H*FBInfo->Pitch); - } else { // Normal copy is OK - while( H -- ) { - memcpy((Uint8*)FBInfo->Framebuffer + dst, (Uint8*)FBInfo->Framebuffer + src, W*bytes_per_px); + while( H -- ) + { + memcpy(framebuffer + dst, sourcebuffer + src, W*bytes_per_px); + if( backbuffer ) + memcpy(backbuffer + dst, sourcebuffer + src, W*bytes_per_px); dst += scrnpitch; src += scrnpitch; }