Browse Source

+ UseLFB and UseNoSelector vars to force LinearFrameBuffer use
with or without specific selector.

pierre 25 years ago
parent
commit
47a02cf8d3
2 changed files with 120 additions and 25 deletions
  1. 3 2
      rtl/go32v2/graphh.inc
  2. 117 23
      rtl/go32v2/vesa.inc

+ 3 - 2
rtl/go32v2/graphh.inc

@@ -30,5 +30,6 @@ CONST
   m1280x1024x64k    = $11A;
   m1280x1024x64k    = $11A;
 
 
 const
 const
-  ForceVesa : boolean = false;
-
+  UseLFB : boolean = false;
+  UseNoSelector : boolean = false;
+  LFBPointer : pointer = nil;

+ 117 - 23
rtl/go32v2/vesa.inc

@@ -1178,6 +1178,10 @@ end;
  {*                    256 colors VESA mode routines  Linear mode        *}
  {*                    256 colors VESA mode routines  Linear mode        *}
  {************************************************************************}
  {************************************************************************}
 {$ifdef FPC}
 {$ifdef FPC}
+type
+  pbyte = ^byte;
+  pword = ^word;
+
   procedure DirectPutPixVESA256Linear(x, y : integer); {$ifndef fpc}far;{$endif fpc}
   procedure DirectPutPixVESA256Linear(x, y : integer); {$ifndef fpc}far;{$endif fpc}
   var
   var
      offs : longint;
      offs : longint;
@@ -1187,17 +1191,26 @@ end;
      Case CurrentWriteMode of
      Case CurrentWriteMode of
        XorPut:
        XorPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
+           if UseNoSelector then
+             col:=pbyte(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
            col := col xor byte(CurrentColor);
            col := col xor byte(CurrentColor);
          End;
          End;
        AndPut:
        AndPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
+           if UseNoSelector then
+             col:=pbyte(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
            col := col and byte(CurrentColor);
            col := col and byte(CurrentColor);
          End;
          End;
        OrPut:
        OrPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
+           if UseNoSelector then
+             col:=pbyte(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
            col := col or byte(CurrentColor);
            col := col or byte(CurrentColor);
          End
          End
        else
        else
@@ -1207,7 +1220,10 @@ end;
            else col := Not(Byte(CurrentColor));
            else col := Not(Byte(CurrentColor));
          End
          End
      End;
      End;
-     seg_move(get_ds,longint(@col),WinWriteSeg,offs+LinearPageOfs,1);
+     if UseNoSelector then
+       pbyte(LFBPointer+offs+LinearPageOfs)^:=col
+     else
+       seg_move(get_ds,longint(@col),WinWriteSeg,offs+LinearPageOfs,1);
   end;
   end;
 
 
   procedure PutPixVESA256Linear(x, y : integer; color : word); {$ifndef fpc}far;{$endif fpc}
   procedure PutPixVESA256Linear(x, y : integer; color : word); {$ifndef fpc}far;{$endif fpc}
@@ -1225,7 +1241,10 @@ end;
          exit;
          exit;
      end;
      end;
      offs := longint(y) * BytesPerLine + x;
      offs := longint(y) * BytesPerLine + x;
-     seg_move(get_ds,longint(@color),WinWriteSeg,offs+LinearPageOfs,1);
+     if UseNoSelector then
+       pbyte(LFBPointer+offs+LinearPageOfs)^:=color
+     else
+       seg_move(get_ds,longint(@color),WinWriteSeg,offs+LinearPageOfs,1);
   end;
   end;
 
 
   function GetPixVESA256Linear(x, y : integer): word; {$ifndef fpc}far;{$endif fpc}
   function GetPixVESA256Linear(x, y : integer): word; {$ifndef fpc}far;{$endif fpc}
@@ -1236,7 +1255,10 @@ end;
      X:= X + StartXViewPort;
      X:= X + StartXViewPort;
      Y:= Y + StartYViewPort;
      Y:= Y + StartYViewPort;
      offs := longint(y) * BytesPerLine + x;
      offs := longint(y) * BytesPerLine + x;
-     seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
+     if UseNoSelector then
+       col:=pbyte(LFBPointer+offs+LinearPageOfs)^
+     else
+       seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),1);
      GetPixVESA256Linear:=col;
      GetPixVESA256Linear:=col;
   end;
   end;
 (*
 (*
@@ -1360,7 +1382,10 @@ end;
          exit;
          exit;
      end;
      end;
      offs := longint(y) * BytesPerLine + 2*x;
      offs := longint(y) * BytesPerLine + 2*x;
-     seg_move(get_ds,longint(@color),WinWriteSeg,offs+LinearPageOfs,2);
+     if UseNoSelector then
+       pword(LFBPointer+offs+LinearPageOfs)^:=color
+     else
+       seg_move(get_ds,longint(@color),WinWriteSeg,offs+LinearPageOfs,2);
   end;
   end;
 
 
   function GetPixVESA32kor64kLinear(x, y : integer): word; {$ifndef fpc}far;{$endif fpc}
   function GetPixVESA32kor64kLinear(x, y : integer): word; {$ifndef fpc}far;{$endif fpc}
@@ -1371,7 +1396,10 @@ end;
      X:= X + StartXViewPort;
      X:= X + StartXViewPort;
      Y:= Y + StartYViewPort;
      Y:= Y + StartYViewPort;
      offs := longint(y) * BytesPerLine + 2*x;
      offs := longint(y) * BytesPerLine + 2*x;
-     seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@color),2);
+     if UseNoSelector then
+       color:=pword(LFBPointer+offs+LinearPageOfs)^
+     else
+       seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@color),2);
      GetPixVESA32kor64kLinear:=color;
      GetPixVESA32kor64kLinear:=color;
   end;
   end;
 
 
@@ -1384,17 +1412,26 @@ end;
      Case CurrentWriteMode of
      Case CurrentWriteMode of
        XorPut:
        XorPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
+           if UseNoSelector then
+             col:=pword(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
            col := col xor currentcolor;
            col := col xor currentcolor;
          End;
          End;
        AndPut:
        AndPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
+           if UseNoSelector then
+             col:=pword(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
            col := col and currentcolor;
            col := col and currentcolor;
          End;
          End;
        OrPut:
        OrPut:
          Begin
          Begin
-           seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
+           if UseNoSelector then
+             col:=pword(LFBPointer+offs+LinearPageOfs)^
+           else
+             seg_move(WinReadSeg,offs+LinearPageOfs,get_ds,longint(@col),2);
            col := col or currentcolor;
            col := col or currentcolor;
          End
          End
        else
        else
@@ -1404,7 +1441,10 @@ end;
            Else col := Not(CurrentColor);
            Else col := Not(CurrentColor);
          End
          End
      End;
      End;
-     seg_move(get_ds,longint(@col),WinWriteSeg,offs+LinearPageOfs,2);
+     if UseNoSelector then
+       pword(LFBPointer+offs+LinearPageOfs)^:=col
+     else
+       seg_move(get_ds,longint(@col),WinWriteSeg,offs+LinearPageOfs,2);
   end;
   end;
 
 
 {$endif FPC}
 {$endif FPC}
@@ -1785,7 +1825,47 @@ end;
 
 
    end;
    end;
 {$ENDIF}
 {$ENDIF}
+type
+  heaperrorproc=function(size:longint):integer;
+
+Const
+  HeapErrorIsHooked : boolean = false;
+  OldHeapError : HeapErrorProc = nil;
+  DsLimit : dword = 0;
+
+  function NewHeapError(size : longint) : integer;
+  var
+    res : integer;
+    begin
+      set_segment_limit(get_ds,DsLimit);
+      NewHeapError:=OldHeapError(size);
+      DsLimit:=get_segment_limit(get_ds);
+      { The base of ds can be changed
+        we need to compute the address again PM }
+      LFBPointer:=pointer(FrameBufferLinearAddress-get_segment_base_address(get_ds));
+      if dword(LFBPointer)+(VESAInfo.TotalMem shl 16)-1 > DsLimit then
+        set_segment_limit(get_ds,dword(LFBPointer)+(VESAInfo.TotalMem shl 16)-1);
+    end;
 
 
+  procedure HookHeapError;
+    begin
+      if HeapErrorIsHooked then
+        exit;
+      DsLimit:=get_segment_limit(get_ds);
+      OldHeapError:=HeapErrorProc(HeapError);
+      HeapError:=@NewHeapError;
+      HeapErrorIsHooked:=true;
+    end;
+
+  procedure UnHookHeapError;
+    begin
+      if not HeapErrorIsHooked then
+        exit;
+      LFBPointer:=nil;
+      set_segment_limit(get_ds,DsLimit);
+      HeapError:=OldHeapError;
+      HeapErrorIsHooked:=false;
+    end;
 
 
   function SetupLinear(var ModeInfo: TVESAModeInfo;mode : word) : boolean;
   function SetupLinear(var ModeInfo: TVESAModeInfo;mode : word) : boolean;
    begin
    begin
@@ -1838,16 +1918,26 @@ end;
          writeln(stderr,'Unable to get linear address for ',hexstr(VESAModeInfo.PhysAddress,8));
          writeln(stderr,'Unable to get linear address for ',hexstr(VESAModeInfo.PhysAddress,8));
          exit;
          exit;
        end;
        end;
-     WinWriteSeg:=allocate_ldt_descriptors(1);
-     WinReadSeg:=allocate_ldt_descriptors(1);
-     set_segment_base_address(WinWriteSeg,FrameBufferLinearAddress);
-     set_segment_limit(WinWriteSeg,(VESAInfo.TotalMem shl 16)-1);
-     set_segment_base_address(WinReadSeg,FrameBufferLinearAddress);
-     set_segment_limit(WinReadSeg,(VESAInfo.TotalMem shl 16)-1);
-     if int31error<>0 then
+     if UseNoSelector then
        begin
        begin
-         writeln(stderr,'Error in linear memory selectors creation');
-         exit;
+         HookHeapError;
+         LFBPointer:=pointer(FrameBufferLinearAddress-get_segment_base_address(get_ds));
+         if dword(LFBPointer)+(VESAInfo.TotalMem shl 16)-1 > get_segment_limit(get_ds) then
+           set_segment_limit(get_ds,dword(LFBPointer)+(VESAInfo.TotalMem shl 16)-1);
+       end
+     else
+       begin
+         WinWriteSeg:=allocate_ldt_descriptors(1);
+         WinReadSeg:=allocate_ldt_descriptors(1);
+         set_segment_base_address(WinWriteSeg,FrameBufferLinearAddress);
+         set_segment_limit(WinWriteSeg,(VESAInfo.TotalMem shl 16)-1);
+         set_segment_base_address(WinReadSeg,FrameBufferLinearAddress);
+         set_segment_limit(WinReadSeg,(VESAInfo.TotalMem shl 16)-1);
+         if int31error<>0 then
+           begin
+             writeln(stderr,'Error in linear memory selectors creation');
+             exit;
+           end;
        end;
        end;
      InLinear:=true;
      InLinear:=true;
      SetUpLinear:=true;
      SetUpLinear:=true;
@@ -2020,7 +2110,7 @@ end;
 
 
      { VBE 2.0 and higher supports >= non VGA linear buffer types...}
      { VBE 2.0 and higher supports >= non VGA linear buffer types...}
      { this is backward compatible.                                 }
      { this is backward compatible.                                 }
-     if (((VESAModeInfo.Attr and ModeNoWindowed) <> 0) or ForceVesa) and
+     if (((VESAModeInfo.Attr and ModeNoWindowed) <> 0) or UseLFB) and
           ((VESAModeInfo.Attr and ModeLinearBuffer) <> 0) then
           ((VESAModeInfo.Attr and ModeLinearBuffer) <> 0) then
         begin
         begin
           if not SetupLinear(VESAModeInfo,mode) then
           if not SetupLinear(VESAModeInfo,mode) then
@@ -2509,7 +2599,11 @@ end;
 
 
 (*
 (*
 $Log$
 $Log$
-Revision 1.20  2000-03-09 22:32:22  pierre
+Revision 1.21  2000-03-12 22:32:22  pierre
+  + UseLFB and UseNoSelector vars to force LinearFrameBuffer use
+    with or without specific selector.
+
+Revision 1.20  2000/03/09 22:32:22  pierre
  * fixes for LFB mode
  * fixes for LFB mode
 
 
 Revision 1.19  2000/02/12 13:39:19  jonas
 Revision 1.19  2000/02/12 13:39:19  jonas