home *** CD-ROM | disk | FTP | other *** search
- (*----------------------------------------------------------------------*)
- (* Display_Lbr_Contents --- Display contents of library (.LBR) file *)
- (*----------------------------------------------------------------------*)
-
- PROCEDURE Display_Lbr_Contents( LbrFileName : AnyStr );
-
- (*----------------------------------------------------------------------*)
- (* *)
- (* Procedure: Display_Lbr_Contents *)
- (* *)
- (* Purpose: Displays contents of a library file (.LBR file) *)
- (* *)
- (* Calling sequence: *)
- (* *)
- (* Display_Lbr_Contents( LbrFileName : AnyStr ); *)
- (* *)
- (* LbrFileName --- name of library file whose contents *)
- (* are to be listed. *)
- (* *)
- (* Calls: *)
- (* *)
- (* Aside from internal subroutines, these routines are required: *)
- (* *)
- (* Dir_Convert_Date --- convert DOS packed date to string *)
- (* Dir_Convert_Time --- convert DOS packed time to string *)
- (* Display_File_Info --- display information about a file *)
- (* Open_File --- open a file *)
- (* Close_File --- close a file *)
- (* *)
- (*----------------------------------------------------------------------*)
-
- (*----------------------------------------------------------------------*)
- (* Map of Library file (.LBR) entry header *)
- (*----------------------------------------------------------------------*)
-
- TYPE
- Lbr_Entry_Type = RECORD
- Flag : BYTE (* LBR - Entry flag *);
- Name : ARRAY[1 .. 8] OF CHAR (* File name *);
- Ext : ARRAY[1 .. 3] OF CHAR (* Extension *);
- Offset: WORD (* Offset within Library *);
- N_Sec : WORD (* Number of 128-byte sectors *);
- CRC : WORD (* CRC (optional) *);
- Date : WORD (* # days since 1/1/1978 *);
- UDate : WORD (* Date of last update *);
- Time : WORD (* Packed time *);
- UTime : WORD (* Time of last update *);
- Pads : ARRAY[1 .. 6] OF CHAR (* Currently unused *);
- END;
-
- CONST
- Lbr_Header_Length = 32 (* Length of library file header entry *);
-
- VAR
- LbrFile : FILE (* Library file *);
- Lbr_Entry : Lbr_Entry_Type (* Header describing one file in library *);
- Lbr_Pos : LONGINT (* Current byte position in library *);
- Lbr_Dir_Size : INTEGER (* # of entries in library directory *);
- Bytes_Read : INTEGER (* # bytes read at current file position *);
- Ierr : INTEGER (* Error flag *);
- Do_Blank_Line : BOOLEAN (* TRUE to print blank line before entry *);
-
- (*----------------------------------------------------------------------*)
- (* Get_Next_Lbr_Entry --- Get next header entry in library *)
- (*----------------------------------------------------------------------*)
-
- FUNCTION Get_Next_Lbr_Entry( VAR LbrEntry : Lbr_Entry_Type;
- VAR Error : INTEGER ) : BOOLEAN;
-
- VAR
- Month : INTEGER;
- Year : INTEGER;
- Done : BOOLEAN;
- T : INTEGER;
- (* # of days in each month *)
- (* STRUCTURED *) CONST
- NDays : ARRAY[1..12] OF INTEGER = ( 31, 28, 31, 30, 31, 30,
- 31, 31, 30, 31, 30, 31 );
-
- BEGIN (* Get_Next_Lbr_Entry *)
- (* Assume no error *)
- Error := 0;
- (* Loop over directory entries *)
- REPEAT
- (* Decrement directory entry count. *)
- (* If = 0, reached end of directory *)
- (* entries. *)
-
- Lbr_Dir_Size := PRED( Lbr_Dir_Size );
- IF ( Lbr_Dir_Size < 0 ) THEN
- Error := End_Of_File;
- (* If not end of entries ... *)
- IF ( Error = 0 ) THEN
- BEGIN
- (* If not first time, move to next *)
- (* directory entry position in file. *)
-
- IF ( Lbr_Pos <> 0 ) THEN
- Seek( LbrFile, Lbr_Pos );
-
- (* Read directory entry *)
-
- BlockRead( LbrFile, Lbr_Entry, SizeOf( Lbr_Entry ), Bytes_Read );
- Error := 0;
- (* If wrong length, .LBR format must *)
- (* be incorrect. *)
-
- IF ( Bytes_Read < Lbr_Header_Length ) THEN
- Error := Format_Error
- ELSE
- (* If length OK, assume entry OK. *)
- WITH Lbr_Entry DO
- BEGIN
- (* Point to next .LBR entry in file *)
-
- Lbr_Pos := Lbr_Pos + Lbr_Header_Length;
-
- (* Pick up time/date of creation this *)
- (* entry if specified. If the update *)
- (* time/date is different, then we *)
- (* will report that instead. *)
-
- IF ( Time = 0 ) THEN
- BEGIN
- Time := UTime;
- Date := UDate;
- END
- ELSE
- IF ( ( Time <> UTime ) OR ( Date <> UDate ) ) THEN
- BEGIN
- Time := UTime;
- Date := UDate;
- END;
- (* Convert date from library format of *)
- (* # days since 1/1/1978 to DOS format *)
- Month := 1;
- Year := 78;
- (* This is done using brute force. *)
- REPEAT
- (* Account for leap years *)
-
- T := 365 + ORD( Year MOD 4 = 0 );
-
- (* See if we have less than 1 year left *)
-
- Done := ( Date < T );
-
- IF ( NOT Done ) THEN
- BEGIN
- Year := SUCC( Year );
- Date := Date - T;
- END;
-
- UNTIL Done;
- (* Now get months and days within year *)
- REPEAT
-
- T := Ndays[Month] +
- ORD( ( Month = 2 ) AND ( Year MOD 4 = 0 ) );
-
- Done := ( Date < T );
-
- IF ( NOT Done ) THEN
- BEGIN
- Month := SUCC( Month );
- Date := Date - T;
- END;
-
- UNTIL Done;
- (* If > 1980, convert to DOS date *)
- (* else leave unconverted. *)
-
- IF ( Year >= 80 ) THEN
- Date := ( Year - 80 ) SHL 9 + Month SHL 5 + Date
- ELSE
- Date := 0;
-
- END (* With *);
-
- END (* Error = 0 *);
-
- UNTIL ( ( Error <> 0 ) OR ( Lbr_Entry.Flag = 0 ) );
-
- (* Report success/failure to caller *)
-
- Get_Next_Lbr_Entry := ( Error = 0 );
-
- END (* Get_Next_Lbr_Entry *);
-
- (*----------------------------------------------------------------------*)
- (* Display_Lbr_Entry --- Display library header entry *)
- (*----------------------------------------------------------------------*)
-
- PROCEDURE Display_Lbr_Entry( Lbr_Entry : Lbr_Entry_Type );
-
- VAR
- SDate : STRING[10];
- STime : STRING[12];
- I : INTEGER;
- FName : AnyStr;
- RLength : LONGINT;
- RSize : LONGINT;
- DateTime : LONGINT;
- DTWord : ARRAY[1..2] OF WORD ABSOLUTE DateTime;
-
- BEGIN (* Display_Lbr_Entry *)
-
- WITH Lbr_Entry DO
- BEGIN
- (* Pick up file name *)
-
- FName := TRIM( Name );
-
- IF ( Ext <> ' ' ) THEN
- FName := FName + '.' + Ext;
-
- (* See if this file matches the *)
- (* entry spec wildcard. Exit if *)
- (* not. *)
-
- IF Use_Entry_Spec THEN
- IF ( NOT Entry_Matches( Fname ) ) THEN
- EXIT;
-
- (* Make sure room on current page *)
- (* for this entry name. *)
- (* If enough room, print blank *)
- (* line if requested. This will *)
- (* only happen for first file. *)
- IF Do_Blank_Line THEN
- BEGIN
- IF ( Lines_Left < 2 ) THEN
- Display_Page_Titles
- ELSE
- BEGIN
- WRITELN( Output_File );
- Lines_left := Lines_Left - 1;
- END;
- Do_Blank_Line := FALSE;
- END
- ELSE
- IF ( Lines_Left < 1 ) THEN
- Display_Page_Titles;
-
- (* Add '. ' to front if we're *)
- (* expanding LBRs in main listing *)
- IF Expand_Arcs_In THEN
- Fname := '. ' + Fname;
-
- (* Write out file name *)
-
- WRITE( Output_File , Left_Margin_String , ' ' , FName );
-
- FOR I := LENGTH( FName ) TO 14 DO
- WRITE( Output_File , ' ' );
-
- (* Convert length in sectors to *)
- (* length in bytes. *)
-
- RLength := N_Sec * 128;
- WRITE( Output_File , RLength:8, ' ' );
-
- (* If time/date specified, output *)
- (* them. *)
- IF ( Date > 0 ) THEN
- BEGIN
- DTWord[1] := Time;
- DTWord[2] := Date;
- Dir_Convert_Date_And_Time( DateTime , SDate , STime );
- END
- ELSE
- BEGIN
- SDate := ' ';
- STime := ' ';
- END;
-
- WRITE( Output_File , SDate, ' ' );
- WRITE( Output_File , STime );
- WRITELN( Output_File );
-
- (* Count lines left on page *)
- IF Do_Printer_Format THEN
- Lines_Left := Lines_Left - 1;
-
- (* Increment total entry count *)
-
- Total_Entries := Total_Entries + 1;
-
- (* Increment total space used *)
-
- Total_ESpace := Total_ESpace + RLength;
-
- END;
-
- END (* Display_Lbr_Entry *);
-
- (*----------------------------------------------------------------------*)
-
- BEGIN (* Display_Lbr_Contents *)
-
- (* Set library left margin spacing *)
-
- Left_Margin_String := Left_Margin_String + DUPL( ' ' , ArcLbr_Indent );
-
- (* Set file title *)
-
- File_Title := Left_Margin_String + ' Library file: ' + LbrFileName;
-
- (* Display library file's name *)
- IF Do_Printer_Format THEN
- IF Lines_Left < 3 THEN
- Display_Page_Titles;
- (* If we're listing contents at end *)
- (* of directory, print library name. *)
- (* Do_Blank_Line flags whether we *)
- (* need to print blank line in entry *)
- (* lister subroutine. If listing *)
- (* inline, then it's true for the *)
- (* first file; otherwise it's false. *)
- (* This is to prevent unnecessary *)
- (* blank lines in output listing *)
- (* when no files are selected from *)
- (* a given library. *)
- IF ( NOT Expand_Arcs_In ) THEN
- BEGIN
- WRITELN( Output_File ) ;
- WRITE ( Output_File , File_Title );
- Lines_Left := Lines_Left - 2;
- Do_Blank_Line := FALSE;
- END
- ELSE
- Do_Blank_Line := TRUE;
- (* Open library file *)
-
- Open_File( LbrFileName , LbrFile, Lbr_Pos, Ierr );
-
- (* Set # directory entries = 1 so *)
- (* we can process actual directory. *)
- Lbr_Dir_Size := 1;
- (* Issue error message if library file *)
- (* can't be opened. *)
- IF ( Ierr <> 0 ) THEN
- BEGIN
- WRITELN( Output_File ,
- DUPL( ' ' , MAX( 0 , MIN( 12 , 13 - LENGTH( LbrFileName ) ) ) ),
- ' Can''t open library file ',LbrFileName );
- IF Do_Printer_Format THEN
- BEGIN
- Lines_Left := Lines_Left - 1;
- IF ( Lines_Left < 1 ) THEN
- Display_Page_Titles;
- END;
- EXIT;
- END
- ELSE IF ( NOT Expand_Arcs_In ) THEN
- BEGIN
-
- WRITELN( Output_File );
- WRITELN( Output_File );
- (* Count lines left on page *)
- IF Do_Printer_Format THEN
- Lines_Left := Lines_Left - 1;
-
- END;
- (* Pick up actual number of entries *)
- (* in library. *)
-
- IF ( Get_Next_Lbr_Entry( Lbr_Entry , Ierr ) ) THEN
- WITH Lbr_Entry DO
- IF ( ( ( Flag OR Offset ) = 0 ) AND ( N_Sec <> 0 ) ) THEN
- Lbr_Dir_Size := N_Sec * 4 - 1
- ELSE
- Ierr := Format_Error;
-
- (* Loop over library entries and print *)
- (* information about each entry. *)
- IF( Ierr = 0 ) THEN
- WHILE( Get_Next_Lbr_Entry( Lbr_Entry , Ierr ) ) DO
- Display_Lbr_Entry( Lbr_Entry );
-
- (* Print blank line after last entry *)
- (* in library, if we're expanding *)
- (* libraries right after listing them, *)
- (* but only if library had any entries *)
- (* listed. *)
-
- IF ( Expand_Arcs_In AND ( NOT Do_Blank_Line ) ) THEN
- BEGIN
- WRITELN( Output_File );
- IF Do_Printer_Format THEN
- Lines_Left := Lines_Left - 1;
- END;
-
- (* Close library file *)
- Close_File( LbrFile );
- (* Restore previous left margin spacing *)
-
- Left_Margin_String := DUPL( ' ' , Left_Margin );
-
- (* No file title *)
- File_Title := '';
-
- END (* Display_Lbr_Contents *);