UNIT Tdb;

{ RWI 950804: Added file locking                                    }
{ RWI 950810: TdbCloseAndErase en TdbCloseAndRename gebruiken nu    }
{             TdbLastIOResult                                       }
{ RWI 960113: TdbWrite was overwriting the first byte of the next   }
{             cached record when the IOSize was not an even number. }
{ RWI 961128: Added OS/2 support and TdbSeemsLocked.                }

INTERFACE

{$DEFINE Caching}

{$IFNDEF DPMI}
{$IFNDEF OS2}
{$DEFINE DOS}
{$ENDIF}
{$ENDIF}

CONST MaxTdbs = 10;            { maximaal 10 databases tegelijkertijd open }
      TdbHeaderLen = 25;         { lengte van de header voor de .TDB files }
      TdbClosedNr = 0;

TYPE TdbNrType = 0..MaxTdbs;

     TdbResultType = (_TdbOk,           { actie gelukt }
                      _TdbNotFound,     { file niet gevonden }
                      _TdbTableFull,    { interne tabel zit vol }
                      _TdbCannotCreate  { kan geen database file aanmaken }
                     );

     TdbHeaderString = STRING[TdbHeaderLen];


VAR TdbLastResult   : TdbResultType;
    TdbLastIOResult : INTEGER;
    TdbLastRawSize  : LONGINT;
    TdbCacheMem     : LONGINT;  { amount used for caching }

FUNCTION  TdbOpen (TdbPath : STRING; VAR TdbNr : TdbNrType) : TdbResultType;
FUNCTION  TdbCreate (TdbPath : STRING; Header : TdbHeaderString; VAR TdbNr : TdbNrType) : TdbResultType;

PROCEDURE TdbClose (TdbNr : TdbNrType);
FUNCTION  TdbCloseAndErase (TdbNr : TdbNrType) : BOOLEAN;
FUNCTION  TdbCloseAndRename (TdbNr : TdbNrType; FileName : STRING) : BOOLEAN;

FUNCTION  TdbReadHeader (TdbNr : TdbNrType) : TdbHeaderString;
PROCEDURE TdbSetHeader (TdbNr : TdbNrType; Header : TdbHeaderString);
PROCEDURE TdbSetIO (TdbNr : TdbNrType; IOBufferSize : WORD);
FUNCTION  TdbRecCount (TdbNr : TdbNrType) : LONGINT;
FUNCTION  TdbRead (TdbNr : TdbNrType; Position : LONGINT; VAR Buffer) : BOOLEAN;
FUNCTION  TdbWrite (TdbNr : TdbNrType; Position : LONGINT; VAR Buffer) : BOOLEAN;
PROCEDURE TdbCut (TdbNr : TdbNrType; Position : LONGINT);
FUNCTION  TdbCache (TdbNr : TdbNrType) : BOOLEAN;
FUNCTION  TdbGetFilename (TdbNr : TdbNrType) : STRING;

FUNCTION  TdbLockFile (TdbNr : TdbNrType) : BOOLEAN;
PROCEDURE TdbUnLockFile (TdbNr : TdbNrType);
FUNCTION  TdbSeemsLocked (TdbNr : TdbNrType) : BOOLEAN;
PROCEDURE TdbDone;


IMPLEMENTATION

USES {$IFDEF DOS}
     XmsLib,
     {$ENDIF}
     {$IFDEF LogFileIO}
     Globals,
     {$ENDIF}
     Ramon;

CONST MAX_CBUFS = 505;       { Genoeg voor 65535 areabase records }

TYPE TdbStatusType = (Open,Closed);

     TdbCacheArray = ARRAY[0..1] OF BYTE;
     TdbCachePtr   = ^TdbCacheArray;

     TdbInfoRecord = RECORD
                           Status      : TdbStatusType;
                           Path        : STRING[128];
                           IOFile      : FILE;
                           IOBufSize   : WORD;
                           CurrPos     : LONGINT;

                           {$IFDEF Caching}
                           Cached      : BOOLEAN;
                           CachedRecNr : LONGINT;
                           {$IFDEF DOS}
                           XmbHandle   : WORD;
                           XmsIOSize   : WORD;
                           {$ELSE}
                           CBufCount   : 0..MAX_CBUFS;
                           CBufSize    : ARRAY[1..MAX_CBUFS] OF WORD;
                           CBufPtr     : ARRAY[1..MAX_CBUFS] OF TdbCachePtr;
                           {$ENDIF}
                           {$ENDIF}
                     END;

     TdbInfoArray = ARRAY[TdbNrType] OF TdbInfoRecord;



VAR TdbInfoPtr     : ^TdbInfoArray;
    {$IFDEF DOS}
    CacheBufje     : POINTER;
    CacheBufjeSize : WORD;
    {$ENDIF}


{--------------------------------------------------------------------------}
{ TdbGetFilename                                                           }
{                                                                          }
FUNCTION TdbGetFilename (TdbNr : TdbNrType) : STRING;
BEGIN
     TdbGetFilename:=TdbInfoPtr^[TdbNr].Path;
END;


{--------------------------------------------------------------------------}
{ TdbOpen                                                                  }
{                                                                          }
{ Open de file waarvan het pad is opgegeven, als de file niet aanwezig is, }
{ geef dan de foutcode _TdbNotFound terug.                                 }
{                                                                          }
FUNCTION TdbOpen (TdbPath : STRING; VAR TdbNr : TdbNrType) : TdbResultType;

VAR Lp : TdbNrType;

BEGIN
     FOR Lp:=1 TO MaxTdbs DO
         WITH TdbInfoPtr^[Lp] DO
              IF (Status = Closed) THEN
              BEGIN
                   Path:=TdbPath;
                   Assign (IOFile,Path);
                   {$I-} Reset (IOFile,1); {$I+}
                   TdbLastIOResult:=IOResult;

                   IF (TdbLastIOResult <> 0) THEN
                   BEGIN
                        TdbOpen:=_TdbNotFound; { resultaat: file not found }
                        TdbLastResult:=_TdbNotFound;
                        Exit;
                   END;

                   {$IFDEF LogFileIO}PostOpenF (IOFile);{$ENDIF}

                   Status:=Open;                    { nu is ie wel geopend }
                   CurrPos:=-1;

                   {$IFDEF Caching}
                   Cached:=FALSE;
                   {$IFNDEF DOS}
                   CBufCount:=0;
                   {$ENDIF}
                   {$ENDIF}

                   TdbNr:=Lp;                    { tabel index terug geven }
                   TdbOpen:=_TdbOk;                       { resultaat: oke }
                   TdbLastResult:=_TdbOk;
                   TdbLastRawSize:=FileSize (IOFile);
                   Exit;
              END;

     TdbOpen:=_TdbTableFull;                   { resultaat: max tdb's open }
     TdbLastResult:=_TdbTableFull;
END;


{--------------------------------------------------------------------------}
{ TdbSeemsLocked                                                           }
{                                                                          }
{ Deze routine controleert of de database benadert kan worden.             }
{                                                                          }
FUNCTION TdbSeemsLocked (TdbNr : TdbNrType) : BOOLEAN;

VAR AByte: BYTE;

BEGIN
     TdbSeemsLocked:=TRUE;

     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          {$I-} Seek (IOFile,0); {$I+}
          IF (IOResult <> 0) THEN
             Exit;

          {$I-} BlockRead (IOFile,AByte,1); {$I+}
          IF (IOResult <> 0) THEN
             Exit;
     END; { with }

     TdbSeemsLocked:=FALSE;
END;


{--------------------------------------------------------------------------}
{ TdbReadHeader                                                            }
{                                                                          }
{ Deze routine leest de header uit de .TDB file en geeft deze terug.       }
{                                                                          }
FUNCTION TdbReadHeader (TdbNr : TdbNrType) : TdbHeaderString;

VAR Header : TdbHeaderString;

BEGIN
     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          IF (FileSize (IOFile) < TdbHeaderLen) THEN
             TdbReadHeader:='NO HEADER INSTALLED'
          ELSE BEGIN
               Seek (IOFile,0);
               BlockRead (IOFile,Header,TdbHeaderLen);
               TdbReadHeader:=Header;
               CurrPos:=-1; { ivm read/write optimalisaties }
          END;
     END; { with }
END;


{--------------------------------------------------------------------------}
{ TdbSetHeader                                                             }
{                                                                          }
{ Met deze routine kan de header van een database vervangen worden.        }
{                                                                          }
PROCEDURE TdbSetHeader (TdbNr : TdbNrType; Header : TdbHeaderString);

VAR Lp : BYTE;

BEGIN
     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          IF (Length (Header) < TdbHeaderLen) THEN
             FOR Lp:=Length (Header)+1 TO TdbHeaderLen DO
                 Header[Lp]:=#26; { ctrl-z }
          Seek (IOFile,0);
          BlockWrite (IOFile,Header,TdbHeaderLen);
     END;
END;


{--------------------------------------------------------------------------}
{ TdbCreate                                                                }
{                                                                          }
{ Maak een nieuwe database aan.                                            }
{                                                                          }
FUNCTION TdbCreate (TdbPath : STRING; Header : TdbHeaderString; VAR TdbNr : TdbNrType) : TdbResultType;

VAR Lp  : TdbNrType;

BEGIN
     FOR Lp:=1 TO MaxTdbs DO
         WITH TdbInfoPtr^[Lp] DO
              IF (Status = Closed) THEN
              BEGIN
                   Path:=TdbPath;
                   Assign (IOFile,Path);
                   {$I-} ReWrite (IOFile,1); {$I+}
                   TdbLastIOResult:=IOResult;

                   IF (TdbLastIOResult <> 0) THEN
                   BEGIN
                        TdbCreate:=_TdbCannotCreate;
                        TdbLastResult:=_TdbCannotCreate;
                        Exit;
                   END;

                   {$IFDEF LogFileIO}PostOpenF (IOFile);{$ENDIF}

                   Status:=Open;
                   CurrPos:=-1;

                   {$IFDEF Caching}
                   Cached:=FALSE;
                   {$IFNDEF DOS}
                   CBufCount:=0;
                   {$ENDIF}
                   {$ENDIF}

                   TdbNr:=Lp;
                   TdbCreate:=_TdbOk;
                   TdbLastResult:=_TdbOk;

                   TdbSetHeader (TdbNr,Header);

                   Exit;
              END; { with }

     TdbCreate:=_TdbTableFull;
     TdbLastResult:=_TdbTableFull;
END;


{--------------------------------------------------------------------------}
{ TdbClose                                                                 }
{                                                                          }
{ Sluit de opgegeven Tdb file.                                             }
{                                                                          }
PROCEDURE TdbClose (TdbNr : TdbNrType);

VAR AnyCached : BOOLEAN;
    Lp        : TdbNrType;
    CLp       : 0..MAX_CBUFS;

BEGIN
     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          IF (Status = Open) THEN
          BEGIN
               {$IFDEF LogFileIO}PreCloseF (IOFile);{$ENDIF}
               Close (IOFile);
          END;

          Status:=Closed;

          {$IFDEF Caching}
          IF Cached THEN
          BEGIN
               {$IFDEF DOS}
               FreeXmb (XmbHandle);
               {$ELSE}
               FOR CLp:=1 TO CBufCount DO
                   FreeMem (CBufPtr[CLp],CBufSize[CLp]);

               CBufCount:=0;
               {$ENDIF}
               Cached:=FALSE;
          END;
          {$ENDIF}
     END; { with }

     {$IFDEF DOS}
     AnyCached:=FALSE;
     FOR Lp:=1 TO MaxTdbs DO
         IF (TdbInfoPtr^[Lp].Status = Open) THEN
            AnyCached:=AnyCached OR TdbInfoPtr^[Lp].Cached;

     IF (NOT AnyCached) THEN
     BEGIN
          FreeMem (CacheBufje,CacheBufjeSize);
          CacheBufje:=NIL;
          CacheBufjeSize:=0;
     END;
     {$ENDIF}
END;


{--------------------------------------------------------------------------}
{ TdbSetIO                                                                 }
{                                                                          }
{ Zet de specifieke zaken voor deze tdb.                                   }
{                                                                          }
PROCEDURE TdbSetIO (TdbNr : TdbNrType; IOBufferSize : WORD);
BEGIN
     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          IOBufSize:=IOBufferSize;

          {$IFDEF DOS}
          IF ((IOBufSize AND 1) > 0) THEN
             XmsIOSize:=IOBufSize+1 { moet altijd een even waarde zijn }
          ELSE
              XmsIOSize:=IOBufSize;
          {$ENDIF}
     END; { with }
END;


{--------------------------------------------------------------------------}
{ TdbRecCount                                                              }
{                                                                          }
{ Geef het aantal records dat in de file is opgeslagen terug.              }
{                                                                          }
FUNCTION TdbRecCount (TdbNr : TdbNrType) : LONGINT;
BEGIN
     WITH TdbInfoPtr^[TdbNr] DO
          TdbRecCount:=((FileSize (IOFile) - (TdbHeaderLen +1)) DIV IOBufSize);
END;


{--------------------------------------------------------------------------}
{ TdbRead                                                                  }
{                                                                          }
{ Lees een record uit de tdb vanaf de opgegeven positie en sla deze op in  }
{ het IO window.                                                           }
{                                                                          }
FUNCTION TdbRead (TdbNr : TdbNrType; Position : LONGINT; VAR Buffer) : BOOLEAN;

VAR Block  : WORD;
    Offset : WORD;

BEGIN
     TdbRead:=TRUE;
     Dec (Position);

     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          {$IFDEF Caching}
          IF Cached AND (Position < CachedRecNr) THEN
          BEGIN
               {$IFDEF DOS}
               CopyFromXmb (XmsIOSize,CacheBufje,XmbHandle,Position*IOBufSize);
               Move (CacheBufje^,Buffer,IOBufSize);
               {$ELSE}
               { zoek het blok waarin het record staat en geef die terug }
               Block:=(Position*IOBufSize) DIV CBufSize[1];
               Offset:=(Position*IOBufSize)-(Block*CBufSize[1]);
               Move (CBufPtr[Block+1]^[Offset],Buffer,IOBufSize);
               {$ENDIF}
          END ELSE
          {$ENDIF}
          BEGIN
               {$I-}
               IF (CurrPos <> Position) THEN
                  Seek (IOFile,Position*IOBufSize+TdbHeaderLen+1);

               BlockRead (IOFile,Buffer,IOBufSize);
               CurrPos:=Position+1;
               {$I+}

               IF (IOResult <> 0) THEN
                  TdbRead:=FALSE;

          END; { if not cached }
     END; { with }
END;


{--------------------------------------------------------------------------}
{ TdbWrite                                                                 }
{                                                                          }
{ Sla het record in het IO window op in de tdb op de opgegeven positie.    }
{                                                                          }
FUNCTION TdbWrite (TdbNr : TdbNrType; Position : LONGINT; VAR Buffer) : Boolean;

VAR HelpBuf : ARRAY[0..2] OF BYTE;
    Block   : WORD;
    Offset  : WORD;

BEGIN
     Dec (Position);
     TdbWrite:=TRUE;

     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          {$IFDEF Caching}
          IF Cached AND (Position < CachedRecNr) THEN
          BEGIN
               {$IFDEF DOS}
               { RWI 960113: Gaat mis als XmsIOSize > IOBufSize en er     }
               {             nog records volgen op dit record, want dan   }
               {             wordt de eerste byte van het volgende record }
               {             overschreven!!                               }
               IF (XmsIOSize > IOBufSize) THEN
               BEGIN
                    { read first two bytes from next record }
                    CopyFromXmb (2,@HelpBuf[1],XmbHandle,(Position+1)*IOBufSize);

                    { write the current record, except the last byte }
                    CopyToXmb (XmsIOSize-2,@Buffer,XmbHandle,Position*IOBufSize);

                    { copy the last byte from this record }
                    HelpBuf[0]:=TdbCacheArray (Buffer)[IOBufSize];

                    { write the last byte of this record and the first }
                    { byte of the next record again.                   }
                    CopyToXmb (2,@HelpBuf,XmbHandle,Position*IOBufSize+XmsIOSize-2);
               END ELSE
                   CopyToXmb (XmsIOSize,@Buffer,XmbHandle,Position*IOBufSize);

               {$ELSE (not DOS, thus OS2 or DPMI) }

               { zoek het juiste block en update die }
               Block:=(Position*IOBufSize) DIV CBufSize[1];
               Offset:=(Position*IOBufSize)-(Block*CBufSize[1]);
               Move (Buffer,CBufPtr[Block+1]^[Offset],IOBufSize);
               {$ENDIF}
          END;
          {$ENDIF}

          { altijd naar disk schrijven }

          {$I-}
          IF (CurrPos <> Position) THEN
             Seek (IOFile,Position*IOBufSize+TdbHeaderLen+1);

          BlockWrite (IOFile,Buffer,IOBufSize);
          CurrPos:=Position+1;
          {$I+}

          IF (IOResult <> 0) THEN
             TdbWrite:=FALSE;
     END; { with }
END;


{--------------------------------------------------------------------------}
{ TdbCut                                                                   }
{                                                                          }
{ Deze routine kapt de database file op de opgegeven positie af en wist    }
{ daarmee alle records inclusief de opgegeven positie.                     }
{                                                                          }
PROCEDURE TdbCut (TdbNr : TdbNrType; Position : LONGINT);
BEGIN
     Dec (Position);

     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          {$IFDEF Caching}
          IF Cached THEN
          BEGIN
               { eh..., tja... }
          END;
          {$ENDIF}

          IF (CurrPos <> Position) THEN
             Seek (IOFile,Position*IOBufSize+TdbHeaderLen+1);

          Truncate (IOFile);
          CurrPos:=-1; { zekerheid, waar zal ie nu staan? Nou? Nou?!! }
     END; { with }
END;


{--------------------------------------------------------------------------}
{ TdbCache                                                                 }
{                                                                          }
{ Deze routine zet een cache op voor een geopende Tdb. Bij het sluiten     }
{ verdwijnt de cache automatisch. Alle records worden gecached en meteen   }
{ ingelezen zodra het geheugen is aangevraagd. Moet aangeroepen worden na  }
{ een Open of Create en SetIO, nooit voor een van deze calls.              }
{                                                                          }
FUNCTION TdbCache (TdbNr : TdbNrType) : BOOLEAN;
{$IFDEF Caching}

{$IFDEF DOS}
VAR BufferPtr   : POINTER;
    BufferSize  : WORD;
    BytesRead   : WORD;
    MoveCount   : WORD;
    StorePos    : LONGINT;
    BytesNeeded : LONGINT;
    KBNeeded    : WORD;
{$ELSE}
VAR FileLeft    : LONGINT;
{$ENDIF}

BEGIN
     TdbCache:=TRUE; { assume error }

     WITH TdbInfoPtr^[TdbNr] DO
     BEGIN
          IF (NOT Cached) THEN
          BEGIN
               {$IFDEF DOS}
               BytesNeeded:=FileSize (IOFile);
               KBNeeded:=BytesNeeded DIV 1024;
               IF ((BytesNeeded MOD 1024) > 0) THEN
                  Inc (KBNeeded);

               XmbHandle:=0;

               IF (NOT AllocateXmb (KBNeeded,XmbHandle)) THEN
                  Exit;  { error }

               TdbCacheMem:=TdbCacheMem+KBNeeded*1024;

               { inlees geheugen aanvragen }
               IF (MaxAvail > 16384) THEN BufferSize:=16384
                                     ELSE BufferSize:=MaxAvail;
               IF ((BufferSize AND 1) > 0) THEN
                  Dec (BufferSize);

               GetMem (BufferPtr,BufferSize);

               StorePos:=0;

               { lees de file in }
               Seek (IOFile,TdbHeaderLen+1); { header niet cachen }
               REPEAT
                     BlockRead (IOFile,BufferPtr^,BufferSize,BytesRead);

                     IF (BytesRead > 0) THEN
                     BEGIN
                          MoveCount:=BytesRead;

                          IF ((MoveCount AND 1) > 0) THEN
                             Inc (MoveCount); { altijd een even getal }

                          CopyToXmb (MoveCount,BufferPtr,XmbHandle,StorePos);

                          StorePos:=StorePos+BytesRead;
                     END;

               UNTIL (BytesRead = 0);

               FreeMem (BufferPtr,BufferSize);

               { copy cache geheugen aanvragen (na vrijgeven inlees buffer) }
               IF (XmsIOSize > CacheBufjeSize) THEN
               BEGIN
                    IF (CacheBufjeSize > 0) THEN
                       FreeMem (CacheBufje,CacheBufjeSize);
                    CacheBufjeSize:=XmsIOSize;
                    GetMem (CacheBufje,CacheBufjeSize);
               END;

               {$ELSE (not DOS, thus DPMI or OS2)}

               IF (MemAvail < FileSize (IOFile)+250000) THEN
                  Exit; { need some memory for message processing... }

               CachedRecNr:=0;
               CBufCount:=0;

               Seek (IOFile,TdbHeaderLen+1); { header niet cachen }
               REPEAT
                     FileLeft:=FileSize (IOFile)-FilePos (IOFile);

                     IF (FileLeft > 0) THEN
                     BEGIN
                          Inc (CBufCount);

                          IF (FileLeft > 65528) THEN
                             { take a multiple of IOBufSize }
                             CBufSize[CBufCount]:=(65528 DIV IOBufSize)*IOBufSize
                          ELSE
                              CBufSize[CBufCount]:=FileLeft;

                          GetMem (CBufPtr[CBufCount],CBufSize[CBufCount]);
                          TdbCacheMem:=TdbCacheMem+CBufSize[CBufCount];

                          BlockRead (IOFile,CBufPtr[CBufCount]^,CBufSize[CBufCount]);
                     END;

               UNTIL (FileLeft <= 0);  { OS2 can have FilePos > FileSize }
               {$ENDIF}

               { Alle records worden ingelezen, dus de cache }
               { bevat hetzelfde aantal records als op DIT   }
               { moment de database                          }
               CachedRecNr:=TdbRecCount (TdbNr);

               CurrPos:=-1;
               Cached:=TRUE;

          END; { nog niet gecached }

          IF Cached THEN
             TdbCache:=FALSE; { success }

     END; { with }
END;
{$ELSE} {!Caching}
BEGIN
     TdbCache:=FALSE; { success }
END;
{$ENDIF}


{-------------------------------------------------------------------------}
{ TdbCloseAndErase                                                        }
{                                                                         }
{ Deze routine sluit de gegeven database, om hem vervolgens te            }
{ verwijderen.                                                            }
{                                                                         }
FUNCTION TdbCloseAndErase (TdbNr : TdbNrType) : BOOLEAN;
BEGIN
     TdbClose (TdbNr);
     {$I-} Erase (TdbInfoPtr^[TdbNr].IOFile); {$I+} TdbLastIOResult:=IOResult;
     TdbCloseAndErase:=(TdbLastIOResult = 0);
END;


{-------------------------------------------------------------------------}
{ TdbCloseAndRename                                                       }
{                                                                         }
{ Deze routine sluit de gegeven database, om hem vervolgens te renamen.   }
{                                                                         }
FUNCTION TdbCloseAndRename (TdbNr : TdbNrType; FileName : STRING) : BOOLEAN;
BEGIN
     TdbClose (TdbNr);
     {$I-} Rename (TdbInfoPtr^[TdbNr].IOFile,FileName); {$I+} TdbLastIOResult:=IOResult;
     TdbCloseAndRename:=(TdbLastIOResult = 0);
END;


{---------------------------------------------------------------------------}
{ TdbLockFile                                                               }
{                                                                           }
{ Deze routine probeert een database te locken. Als dat niet lukt, dan      }
{ wordt FALSE terug gegeven, anders TRUE.                                   }
{                                                                           }
FUNCTION TdbLockFile (TdbNr : TdbNrType) : BOOLEAN;
BEGIN
     TdbLockFile:=LockFile (TdbInfoPtr^[TdbNr].IOFile);
END;


{---------------------------------------------------------------------------}
{ TdbUnLockFile                                                             }
{                                                                           }
{ Deze routine unlockt een file die daarvoor met Lock geblokeerd is.        }
{                                                                           }
PROCEDURE TdbUnLockFile (TdbNr : TdbNrType);
BEGIN
     UnLockFile (TdbInfoPtr^[TdbNr].IOFile);
END;


PROCEDURE TdbDone;
BEGIN
     FreeMem (TdbInfoPtr,SizeOf (TdbInfoArray));
END;


{--------------------------------------------------------------------------}
{ Unit Initialisation                                                      }
{                                                                          }
{ Zet de status van alle Tdb records op Closed.                            }
{                                                                          }

VAR Lp : BYTE;

BEGIN
     GetMem (TdbInfoPtr,SizeOf (TdbInfoArray));

     FOR Lp:=1 TO MaxTdbs DO
     BEGIN
          TdbInfoPtr^[Lp].Status:=Closed;
          {$IFDEF Caching}
          TdbInfoPtr^[Lp].Cached:=FALSE;
          {$ENDIF}
     END;

     {$IFDEF DOS}
     CacheBufjeSize:=0;
     CacheBufje:=NIL;
     {$ENDIF}

     TdbCacheMem:=0;
END.
