diff --git a/src/driver/video/video.pas b/src/driver/video/video.pas index 511f7646..0c6f3db4 100644 --- a/src/driver/video/video.pas +++ b/src/driver/video/video.pas @@ -3,29 +3,59 @@ unit video; interface uses - multiboot, lmemorymanager, tracer, color, rand; + multiboot, lmemorymanager, tracer, color, rand, console; procedure init(); procedure DrawPixel(X : uint32; Y : uint32; Pixel : TRGB32); +procedure Flush(); type + VideoBuffer = uint64; TVESALinearBuffer = record - Location : uint64; + Initialized : Boolean; + Location : VideoBuffer; + BitsPerPixel : uint8; + Width : uint32; + Height : uint32; + end; + TBackBuffer = record + Initialized : Boolean; + Location : VideoBuffer; BitsPerPixel : uint8; Width : uint32; Height : uint32; end; TVESA = record - initialized : Boolean; - Framebuffer : TVESALinearBuffer; + DefaultBuffer : VideoBuffer; + Framebuffer : TVESALinearBuffer; + BackBuffer : TBackBuffer; end; + PVESA = ^TVESA; implementation var VESA : TVESA; -procedure allocateFrameBuffer(Address : uint32; Width : uint32; Height : uint32); +function allocateBackBuffer(Width : uint32; Height : uint32; BitsPerPixel : uint8) : uint64; +begin + Outputln('VIDEO','Start Kalloc Backbuffer'); + //This doesn't currently work... Needs a rework of lmemorymanager + allocateBackBuffer:= uint64(kalloc((Width * Height) * BitsPerPixel)); + Outputln('VIDEO','End Kalloc Backbuffer'); +end; + +procedure initBackBuffer(VESAInfo : PVESA; Width : uint32; Height : uint32; BitsPerPixel : uint8); +begin + VESAInfo^.BackBuffer.Width:= Width; + VESAInfo^.BackBuffer.Height:= Height; + VESAInfo^.BackBuffer.BitsPerPixel:= BitsPerPixel; + VESAInfo^.BackBuffer.Location:= allocateBackBuffer(VESAInfo^.BackBuffer.Width, VESAInfo^.BackBuffer.Height, VESAInfo^.BackBuffer.BitsPerPixel); + VESAInfo^.DefaultBuffer:= VESAInfo^.BackBuffer.Location; + VESAInfo^.BackBuffer.Initialized:= True; +end; + +procedure allocateVESAFrameBuffer(Address : uint32; Width : uint32; Height : uint32); var LowerAddress, UpperAddress : uint32; Block : uint32; @@ -40,6 +70,19 @@ begin tracer.push_trace('video.allocateFrameBuffer.enter'); end; +procedure initVESAFrameBuffer(VESAInfo : PVESA; Location : uint64; Width : uint32; Height : uint32; BitsPerPixel : uint8); +begin + if not(VESAInfo^.Framebuffer.Initialized) then begin + VESAInfo^.Framebuffer.Location:= Location; + VESAInfo^.Framebuffer.BitsPerPixel:= BitsPerPixel; + VESAInfo^.Framebuffer.Width:= Width; + VESAInfo^.Framebuffer.Height:= Height; + allocateVESAFrameBuffer(VESAInfo^.Framebuffer.Location, VESAInfo^.Framebuffer.Width, VESAInfo^.Framebuffer.Height); + VESAInfo^.DefaultBuffer:= VESAInfo^.Framebuffer.Location; + VESAInfo^.Framebuffer.Initialized:= True; + end; +end; + procedure init(); var RGB : TRGB32; @@ -47,14 +90,12 @@ var begin tracer.push_trace('video.init.enter'); - If not(VESA.initialized) then begin - VESA.Framebuffer.Location:= multiboot.multibootinfo^.framebuffer_addr; - VESA.Framebuffer.BitsPerPixel:= multiboot.multibootinfo^.framebuffer_bpp; - VESA.Framebuffer.Width:= multiboot.multibootinfo^.framebuffer_width; - VESA.Framebuffer.Height:= multiboot.multibootinfo^.framebuffer_height; - allocateFrameBuffer(VESA.Framebuffer.Location, VESA.Framebuffer.Width, VESA.Framebuffer.Height); - VESA.initialized:= true; - end; + console.Outputln('VIDEO', 'Init VESA Framebuffer'); + initVESAFrameBuffer(@VESA, multiboot.multibootinfo^.framebuffer_addr, multiboot.multibootinfo^.framebuffer_width, multiboot.multibootinfo^.framebuffer_height, multiboot.multibootinfo^.framebuffer_bpp); + console.Outputln('VIDEO', 'Init VESA Backbuffer'); + //initBackBuffer(@VESA, multiboot.multibootinfo^.framebuffer_width, multiboot.multibootinfo^.framebuffer_height, multiboot.multibootinfo^.framebuffer_bpp); + + console.Outputln('VIDEO', 'Start Test Draw Loop'); srand(98354754397); while true do begin Inc(RGB.R); @@ -65,19 +106,40 @@ begin Inc(RGB.B); end; end; + console.Outputln('VIDEO', 'Call flush'); + Flush(); end; + tracer.push_trace('video.init.exit'); end; procedure DrawPixel(X : uint32; Y : uint32; Pixel : TRGB32); var Location : PuInt32; - Increment : Uint32; + LocationIndex : Uint32; begin - Location:= Puint32(VESA.Framebuffer.Location); - Increment:= (Y * VESA.Framebuffer.Width) + X; - Location[Increment]:= uint32(Pixel); + Location:= Puint32(VESA.DefaultBuffer); + LocationIndex:= (Y * VESA.Framebuffer.Width) + X; + Location[LocationIndex]:= uint32(Pixel); +end; + +procedure Flush(); +var + x,y : uint32; + Back,Front : PuInt32; + +begin + writestringln('Flush Start'); + if not(VESA.BackBuffer.Initialized) then exit; + Back:= PUint32(VESA.BackBuffer.Location); + Front:= PuInt32(VESA.Framebuffer.Location); + for x:=0 to VESA.Framebuffer.Width-1 do begin + for y:=0 to VESA.Framebuffer.Height-1 do begin + Front[(Y * VESA.Framebuffer.Width)+X]:= Back[(Y * VESA.Framebuffer.Width)+X]; + end; + end; + writestringln('Flush End'); end; end. \ No newline at end of file diff --git a/src/include/color.pas b/src/include/color.pas index 4b81efe3..ce5b50f6 100644 --- a/src/include/color.pas +++ b/src/include/color.pas @@ -10,6 +10,12 @@ type A : uint8; end; + TRGB24 = bitpacked record + B : uint8; + G : uint8; + R : uint8; + end; + TRGB16 = bitpacked record B : UBit5; G : UBit6; @@ -22,6 +28,10 @@ type R : UBit2; end; +const + black : TRGB32 = (B: 000; G: 000; R: 000; A: 000); + white : TRGB32 = (B: 255; G: 255; R: 255; A: 000); + implementation end. \ No newline at end of file diff --git a/src/kernel.pas b/src/kernel.pas index 462c13e0..daeef516 100644 --- a/src/kernel.pas +++ b/src/kernel.pas @@ -203,6 +203,8 @@ begin { Call Tracer } tracer.init(); + video.init(); + { VFS Init } vfs.init(); @@ -264,8 +266,6 @@ begin rand.srand((getDateTime.Seconds SHL 24) OR (getDateTime.Minutes SHL 16) OR (getDateTime.Hours SHL 8) OR (getDateTime.Day)); tracer.push_trace('kmain.TICK'); - - video.init(); while true do begin tracer.push_trace('kmain.RedrawWindows');