-- lsd.mesa    May 27, 1982 2:33 pm 
-- Interface to the Local System Directory component of the
--  Interim Cedar File System.
-- what a trip... d. gifford


DIRECTORY
  File: TYPE USING [Capability],
  Rope: TYPE USING [ROPE];

LSD: DEFINITIONS = {

--  The LSD consists of a set of entries that are indexed in three ways:
--  (1) There is name to entry map implemented by hashing
--  (2) Entries can be enumerated in LRU
--  (3) Dirty Entries can be enumerated 


    
  -- Procedures
  
  Entry: TYPE = LONG POINTER TO EntryObject;
  
  ClearDirty: PROC[entry: Entry];
       -- Marks an entry as clean.
       -- If the entry was not dirty ClearDirty is a nop.
     
  Create: PROC[name: Rope.ROPE, fc: File.Capability, create: LONG CARDINAL]
    RETURNS [entry: Entry];
       -- Creates an entry in the LSD, links it into the hash chain,
       -- and makes it MRU. The new entry is locked in exclusive mode.
       -- If an entry already existed under name, it will be updated
       -- with the new information 
    
  Delete: PROC[entry: Entry];
       -- Deletes an entry in the LSD.  Any locks are released.

  EProc: TYPE = PROCEDURE [entry: Entry]
    RETURNS [stop: BOOLEAN];
       -- Type of procedure called when the LSD is enumerated.
       
  Enumerate: PROC[p: EProc];
       -- Enumerates the LSD, MRU to LRU
       
  EnumerateLocked: PROC[p: EProc];
       -- Enumerates the LSD entries that are locked
   
  GetDirty: PROC
    RETURNS [dirty: Entry];
        -- Returns a dirty entry.
	-- The returned entry is locked in exclusive mode.
	-- If no dirty entry is found, NIL is returned.
  
  GetVictim: PROC
    RETURNS[victim: Entry];
       -- Returns the LRU entry that is eligible for replacement.
       -- The returned entry is locked in exclusive mode.
       -- If no victim is found, NIL is returned.

  Lock: PROC[entry: Entry, exclusive: BOOLEAN]
    RETURNS [success: BOOLEAN];
       -- Locks an LSD entry in share or exclusive mode.
       -- Returns T if it was able to set the requested lock. 

  Lookup: PROC[name: Rope.ROPE]
    RETURNS [entry: Entry];
       -- Looks up an entry in the LSD by name.  No lock is set.
       -- Returns NIL if there is no entry with the specified name. 
       -- If entry is found, it is made MRU

  SetDirty: PROC[entry: Entry];
       -- Marks an entry dirty.
       
  Unlock: PROC[entry: Entry];
       -- Clears the lock set on an entry.
       -- If entry is not locked, Unlock is a nop.
       
  UnlockAll: PROC[];
       -- Sledge hammer to unlock everything

  
  -- Internal Structure of the LSD
  
  -- max size in pages
    maxSize: CARDINAL = 200;
    
  -- number of hash buckets
  -- don't make this so big that LSDHeader is > 4K words or the compiler croaks
    buckets: CARDINAL = 997;
    
  -- LSD base
    Base: TYPE = LONG BASE POINTER TO LSDHeader;
    
  -- LSD internal links  
    LPtr: TYPE = Base RELATIVE LONG POINTER TO Link;
    Link: TYPE = RECORD [
      next, last: LPtr
      ];
      
  -- LSD header
    mruHeadOffset: LPtr = LOOPHOLE[LONG[2], LPtr];
    freeHeadOffset: LPtr = LOOPHOLE[LONG[6], LPtr];
    dirtyHeadOffset: LPtr = LOOPHOLE[LONG[10], LPtr];
        
    LSDHeader: TYPE = MACHINE DEPENDENT RECORD [
      version (0): LONG CARDINAL,
      mruChain (2): Link,
      freeChain (6): Link,
      dirtyChain (10): Link,
      freePointer (14): LONG CARDINAL,
      hash (16): ARRAY [0..buckets) OF Link
      ];
      
    headerVersion: LONG CARDINAL = 23264373274B;
    
  -- LSD Entry   
    mruOffset: LONG CARDINAL = 0;
    hashOffset: LONG CARDINAL = 4;
    dirtyOffset: LONG CARDINAL = 8;
    
    EntryObject: TYPE = MACHINE DEPENDENT RECORD [
      -- mru chain
      mru (0): Link,
      -- hash links entries together in the same hash class
      hash (4): Link,
      -- dirty links together entries that are dirty
      dirty (8): Link,
      -- size of entry object in words
      size (12): CARDINAL,
      -- local name of the file
      fc (13): File.Capability,
      -- time when the file was checked at the remote server
      checked (19): LONG CARDINAL,
      -- time file last modified
      create (21): LONG CARDINAL,
      -- dirty is T if the file must be written back to the server
      -- free is T if this is a free entry
      dirtyF (23:0..0): BOOLEAN,
      free (23:1..15): BOOLEAN,
      -- remote name of the file
      name (24): StringBody
      ];

}..