; ************************** AMUS Program Label ******************************
; Filename: D.M68                                           Date: 02/06/90
; Category: UTIL         Hash Code: 315-624-543-525      Version: 2.0(107)
; Initials: ULTR/AM      Name: DAVID PALLMANN
; Company: ULTRASOFT CORPORATION                   Telephone #: 5163484848
; Related Files: WLDSCN.LIB (wildcard scanner, hash 275-510-373-412)
; Min. Op. Sys.: AMOSL 1.3B                    Expertise Level: BEG
; Special: Requires 2.0 assembler
; Description: Directory program.  Defaults to wide directory.
; Type /H for a list of options.  Has some unique, useful switches such as
; /MIN:n and /MAX:n to see only files of a certain size.
; ****************************************************************************

;****************************************************************************
;*                                                                          *
;*                                    D                                     *
;*                            Directory Command                             *
;*                                                                          *
;****************************************************************************
;Copyright (C) 1986, 1989 UltraSoft Corporation.  All Rights Reserved.
;
;Related Files: WLDSCN.LIB - wildcard scanner
;
;Assembly Instructions:
;
;       1. You need the 2.0 assembler.  You can't assemble D otherwise.
;       2. .M68 D
;       3. .LNKLIT D,WLDSCN.LIB/L
;
;To make FIND.LIT (defaults to ALL:[]), specify .M68 D/V:1
;
;Written by: David Pallmann
;
;1.0(100)  12-Sep-86  created. /DFP
;
;2.0(101)  30-Dec-88  link with updated wildcard scanner for AMOS 2.0 and
;                     extended file structure support. /DFP
;2.0(102)  06-Jan-89  use new per-user SSD protection scheme. /DFP
;2.0(103)  28-Nov-89  SSD protection removed, donated to AMUS. /DFP
;2.0(104)  22-Jan-90  correct bug with /N - showed wrong # of blocks. /DFP
;2.0(105)  23-Jan-90  add /V:1 assembly option to make FIND.LIT. /DFP
;2.0(106)  06-Feb-90  correct help descriptions of /MIN and /MAX switches. /DFP
;2.0(107)  06-Feb-90  relinked with 1.9 version of WLDSCN. /DFP

       VMAJOR  =2
       VMINOR  =0
       VSUB    =0
       VEDIT   =107.
       VWHO    =0

       NVALU   FIND

       IF      EQ,FIND,ASMMSG "Creating D.LIT"
       IF      EQ,FIND,OBJNAM D.LIT

       IF      NE,FIND,ASMMSG "Creating FIND.LIT"
       IF      NE,FIND,OBJNAM FIND.LIT

       AUTOEXTERN

       SEARCH  SYS
       SEARCH  SYSSYM
       SEARCH  TRM

;-----------------------------------
;don't let the 1.X assembler through
;-----------------------------------
       SYMBOL1 =1
       SYMBOL2 =2
       IF      EQ,SYMBOL1-SYMBOL2,ASMERP "?The 2.0 assembler is required"

;----------------
;ASCII characters
;----------------

       LF      =12                     ; line feed
       CR      =15                     ; carriage return
       ESC     =33                     ; escape

;--------------
;registers used
;--------------

       MEM     =A5                     ; points to work memory
       INDEX   =A4                     ; points to current file DDB
       TRM     =A3
       SIZE    =D3
       COL     =D5                     ; contains column count
       COUNT   =D4                     ; contains file number

;-----------
;work memory
;-----------

       .OFINI
       .OFDEF  OLD.DEV,2               ; old device
       .OFDEF  OLD.DRV,2               ; old drive
       .OFDEF  OLD.PPN,2               ; old PPN
       .OFDEF  TOTAL.FILES,4           ; total files
       .OFDEF  TOTAL.BLOCKS,4          ; total blocks
       .OFDEF  GRAND.FILES,4           ; grand total - files
       .OFDEF  GRAND.BLOCKS,4          ; grand total - blocks
       .OFDEF  MIN.SIZE,4              ; min block size
       .OFDEF  MAX.SIZE,4              ; max block size
       .OFDEF  WIDTH,4                 ; width
       .OFDEF  FLAGS,4                 ; flags:
               F$WIDTH=1               ;  width was specified
               F$SIZ=2                 ;  show file sizes
               F$VER=4                 ;  show file version numbers
               F$TOTAL=10              ;  show totals
               F$NO=20                 ;  no file information 'cept totals
               F$PAGE=40               ;  page handling
               F$CONTIG=100            ;  show contiguous files in low intensity
               F$LOW=1000000           ;  low intensity
               F$NEGATE=2000000        ;  switch negate flag
       .OFDEF  FILE,D.DDB              ; work DDB
       .OFDEF  DELAY,2                 ; output speed (1/10 seconds to wait)
       .OFDEF  BUFFER,80.              ; conversion buffer             [105]
       .OFSIZ  MEMSIZ

;------
;macros
;------

DEFINE  BIT     SRC,DST
       MOV     DST,D7
       AND     SRC,D7
       ENDM

DEFINE  RNE
       BEQ     1$$
       RTN
1$$:
       ENDM

DEFINE  REQ
       BNE     1$$
       RTN
1$$:
       ENDM

DEFINE  RLE
       BGT     1$$
       RTN
1$$:
       ENDM

DEFINE  RGE
       BLT     1$$
       RTN
1$$:
       ENDM

DEFINE  RLO
       BHIS    1$$
       RTN
1$$:
       ENDM

DEFINE  RHI
       BLOS    1$$
       RTN
1$$:
       ENDM

DEFINE  TFUNC   CODE
       PUSH    D1
       MOVW    #-1_8.+^D<CODE>,D1
       TCRT
       POP     D1
       ENDM

DEFINE LOW=TFUNC 11
DEFINE HIGH=TFUNC 12
DEFINE JUMP=TFUNC 95
DEFINE SMOOTH=TFUNC 98

DEFINE  MOVWL   SRC,DST
       CLR     D7
       MOVW    SRC,D7
       MOV     D7,DST
       ENDM

DEFINE  DEPACK  ADDR
       PUSH    A1
       IF NB,ADDR,LEA A1,ADDR
       CALL    DEPACK
       POP     A1
       ENDM

;-----------------------
;wildcard scanner macros
;-----------------------

DEFINE  WINIT
       IF      NDF,W.INIT,EXTERN W.INIT
       CALL    W.INIT
       ENDM

DEFINE  WSPEC   EXT
       IF      NDF,W.SPEC,EXTERN W.SPEC
       CALL    W.SPEC
       IF      B,EXT,ASCII /???/
       IF      NB,EXT,ASCII /'EXT/
       BYTE    0
       ENDM

DEFINE  WSCAN
       IF      NDF,W.SCAN,EXTERN W.SCAN
       CALL    W.SCAN
       ENDM

DEFINE  WFULL
       IF      NDF,W.FULL,EXTERN W.FULL
       CALL    W.FULL
       ENDM

DEFINE  WLIST   ADDR
       IF      NDF,W.LIST,EXTERN W.LIST
               IF      NB,ADDR
               PUSH    A0
               LEA     A0,ADDR
               ENDC
       CALL    W.LIST
               IF      NB,ADDR
               POP     A0
               ENDC
       ENDM

;---------------------------------------
;start of code - standard initialization
;---------------------------------------

START:  PHDR    -1,,PH$REE!PH$REU       ; program header - reentrant, reusable
       GETIMP  MEMSIZ,MEM              ; allocate local memory - index w/MEM
       INIT    FILE(MEM)
       WINIT                           ; initialize wildcard scanner - sets A4
       MOV     #4,WIDTH(MEM)           ; default display width to siz
       CLR     COUNT                   ; clear file count
       MOV     #F$SIZ!F$TOTAL,FLAGS(MEM)
       JOBIDX                          ;
       MOV     JOBTRM(A6),TRM          ;
       ORW     #T$IMI!T$ECS,T.STS(TRM) ;
       SET     MAX.SIZE(MEM)           ;
       JMP     COMMAND.LINE            ;

;-----------------------------------------------------------------------
;command line processing - check for /W:n switch before, after file spec
;-----------------------------------------------------------------------

COMMAND.LINE:
       IF      NE,FIND
       LEA     A0,BUFFER(MEM)          ; [105]...
       MOVB    #'A,(A0)+               ;
       MOVB    #'L,(A0)+               ;
       MOVB    #'L,(A0)+               ;
       MOVB    #':,(A0)+               ;
       MOVB    #'[,(A0)+               ;
       MOVB    #'],(A0)+               ;
10$:    LIN                             ;
       BEQ     20$                     ;
       MOVB    (A2)+,(A0)+             ;
       BR      10$                     ;
20$:    MOVB    #CR,(A0)+               ;
       MOVB    #LF,(A0)+               ;
       CLRB    @A0                     ;
       LEA     A2,BUFFER(MEM)          ; ...[105]
       ENDC

       BYP                             ; bypass white spac
       CALL    SWITCH                  ; check for switches
       WSPEC                           ; process wildcard filespec
       JNE     EXIT                    ;  error
       CALL    SWITCH                  ; check for switches again
       CALL    FIND.FILE
       BEQ     DISPLAY.DIRECTORY       ; got one - start display
       TYPECR  %No such files          ; no files - break the news
       CRLF                            ; next line
       JMP     CHECK.FOR.COMMA         ; get next spec

;----------------------------------------------------------------
;display account number and ersatz name if first time in this PPN
;----------------------------------------------------------------

DISPLAY.DIRECTORY:
       WFULL                           ; convert DDB @INDEX to FULL spec
       CMMW    D.DEV(INDEX),OLD.DEV(MEM) ; has device changed?
       BNE     DISPLAY.ACCOUNT         ;    yes - display new account
       CMMW    D.DRV(INDEX),OLD.DRV(MEM) ; has drive number changed?
       BNE     DISPLAY.ACCOUNT         ;    yes - display new account
       CMMW    D.PPN(INDEX),OLD.PPN(MEM) ; has PPN changed?
       JEQ     DISPLAY.FILE            ;    no - bypass account display

DISPLAY.ACCOUNT:
       TST     COUNT                   ; is this the first file displayed?
       BEQ     20$                     ;  yes - skip first crlf
       CMM     COL,WIDTH(MEM)          ; are we in mid-line?
       BEQ     10$                     ;  no
       CALL    NEW.LINE
10$:    BIT     #F$TOTAL,FLAGS(MEM)
       BEQ     14$
       CALL    SHOW.TOTAL
       CLR     TOTAL.BLOCKS(MEM)
       CLR     TOTAL.FILES(MEM)
14$:    CALL    NEW.LINE
20$:    INC     COUNT
       DEPACK  D.DEV(INDEX)            ; output the device code
       CLR     D1                      ; ...
       MOVW    D.DRV(INDEX),D1         ; get the drive number
       DCVT    0,OT$TRM                ; print it
       TYPE    :[                      ; ...
       PRPPN   D.PPN(INDEX)            ; print the PPN
       TYPE    ]                       ; ...
       MOVW    D.DEV(INDEX),OLD.DEV(MEM) ; store
       MOVW    D.DRV(INDEX),OLD.DRV(MEM) ;  new device, drive,
       MOVW    D.PPN(INDEX),OLD.PPN(MEM) ;   and PPN

DISPLAY.ERSATZ:
       MOV     ERSATZ,D7               ; get ersatz table address
       JEQ     DISPLAY.FILE            ;  isn't any
       MOV     D7,A0                   ; put in A0
10$:    CTRLC   EXIT                    ; ^C check
       CMMW    EZ.DEV(A0),D.DEV(INDEX) ; device code match?
       BNE     20$                     ;  no
       CMMW    EZ.UNT(A0),D.DRV(INDEX) ; drive number match?
       BNE     20$                     ;  no
       CMMW    EZ.PPN(A0),D.PPN(INDEX) ; PPN match?
       BNE     20$                     ;  no
       TYPE    < - >                   ; figured out the ersatz name,
       SAVE    A1,A2
       LEA     A2,BUFFER(MEM)
       LEA     A1,EZ.NAM(A0)
       UNPACK
       UNPACK
12$:    CMMB    -(A2),#40
       BEQ     12$
       CLRB    1(A2)
       TTYL    BUFFER(MEM)
       TYPE    :
       REST    A1,A2
       BR      30$                     ; ...
20$:    ADD     #EZ.SIZ,A0              ; on to next ersatz entry
       TSTW    @A0                     ; at end of table?
       BNE     10$                     ;  no - check next entry
30$:    CALL    NEW.LINE                        ; print newline

;-------------------------------
;display file name and extension
;-------------------------------
DISPLAY.FILE:
       BIT     #F$NO,FLAGS(MEM)
       JNE     UPDATE.TOTALS
       CMM     D.LSZ(INDEX),#512.
       BLOS    10$
       CALL    LOW.INTENSITY
       BR      20$
10$:    CALL    HIGH.INTENSITY
20$:    DEPACK  D.FIL(INDEX)            ; print file
       DEPACK  D.FIL+2(INDEX)          ;  name
       TYPE    .                       ; print dot
       DEPACK  D.EXT(INDEX)            ; print extension
       MOVW    D.DEV(INDEX),FILE+D.DEV(MEM)
       MOVW    D.DRV(INDEX),FILE+D.DRV(MEM)
       MOV     D.FIL(INDEX),FILE+D.FIL(MEM)
       MOVW    D.EXT(INDEX),FILE+D.EXT(MEM)
       MOVW    D.PPN(INDEX),FILE+D.PPN(MEM)
;[104]  MOV     D.FSZ(INDEX),SIZE

UPDATE.TOTALS:
       MOV     D.FSZ(INDEX),SIZE               ; [104]
       BIT     #F$TOTAL,FLAGS(MEM)
       BEQ     DISPLAY.SIZE
       ADD     SIZE,TOTAL.BLOCKS(MEM)
       INC     TOTAL.FILES(MEM)

DISPLAY.SIZE:
       BIT     #F$SIZ,FLAGS(MEM)       ; /S specified?
       BEQ     DISPLAY.VERSION         ;  no
       TYPESP
       MOV     SIZE,D1
       PUSH    A2
       LEA     A2,BUFFER(MEM)
       DCVT    0,OT$MEM!OT$ZER
       MOV     #5,D0
10$:    MOVB    #40,(A2)+
       SOB     D0,10$
       CLRB    BUFFER+5(MEM)
       TTYL    BUFFER(MEM)
       POP     A2

DISPLAY.VERSION:
       BIT     #F$VER,FLAGS(MEM)       ; /V specified?
       JEQ     ADVANCE                 ;  no
       LOOKUP  FILE(MEM)
       MOV     FILE+D.BAS(MEM),FILE+D.REC(MEM)
       READ    FILE(MEM)
       MOV     FILE+D.BUF(MEM),A0
       CMMB    2(A0),#-1
       BEQ     10$
       CMMB    2(A0),#-2
       BNE     ADVANCE
10$:    ADD     #4,A0
       VCVT    @A0,OT$TRM!OT$LSP

ADVANCE:
       BIT     #F$NO,FLAGS(MEM)
       BNE     DISPLAY.NEXT
       DEC     COL                     ; dec column
       BEQ     10$                     ;  end of line
       TYPE    < >                     ; ...
       BIT     #F$SIZ,FLAGS(MEM)
       BNE     DISPLAY.NEXT
       TYPE    < >
       BR      DISPLAY.NEXT            ; on to next file
10$:    CALL    NEW.LINE                        ; print newline

DISPLAY.NEXT:
       CTRLC   EXIT                    ; ^C check
       CALL    FIND.FILE
       JEQ     DISPLAY.DIRECTORY       ; got one - go display it
10$:    TST     TOTAL.FILES(MEM)
       BEQ     20$
       CALL    SHOW.TOTAL
       CALL    NEW.LINE
       BR      CHECK.FOR.COMMA
20$:    CMM     COL,WIDTH(MEM)          ; are we in mid-line?
       BEQ     CHECK.FOR.COMMA         ;  no
       CALL    NEW.LINE                ; yeah - go to next line

;-------------------------------------------------------------
;check for comma (indicates another file spec on command line)
;-------------------------------------------------------------
CHECK.FOR.COMMA:
       CMMB    (A2)+,#<',>             ; another spec present?
       BNE     SHOW.GRAND.TOTAL
       TST     COUNT
       BEQ     10$
       CALL    NEW.LINE
10$:    CLR     COUNT                   ; clear count in case we're not done
       CLRW    OLD.PPN(MEM)
       CLR     TOTAL.FILES(MEM)
       CLR     TOTAL.BLOCKS(MEM)
       JMP     COMMAND.LINE

SHOW.GRAND.TOTAL:
       TST     GRAND.FILES(MEM)
       JEQ     EXIT
       CMM     GRAND.FILES(MEM),TOTAL.FILES(MEM)
       JEQ     EXIT
       TYPESP  Grand total of
       MOV     GRAND.BLOCKS(MEM),D1
       DCVT    0,OT$TRM!OT$TSP
       TYPE    block
       CMP     D1,#1
       BEQ     20$
       TYPE    s
20$:    TYPE    < in >
       MOV     GRAND.FILES(MEM),D1
       DCVT    0,OT$TRM
       TYPE    < file>
       CMP     D1,#1
       BEQ     30$
       TYPE    s
30$:    CALL    NEW.LINE

EXIT:   BIT     #F$PAGE,FLAGS(MEM)
       BEQ     10$
       JUMP
10$:    EXIT                            ; exit to AMOS

;---------------------------------------------------------------
;switch processing - only switch currently supported is /W:width
;---------------------------------------------------------------

SWITCH: AND     #^C<F$NEGATE>,FLAGS(MEM)
       BYP
       CMMB    @A2,#'/                 ; slash present?
       RNE                             ;  no - return
       BCALL   SWITCH2
       BR      SWITCH

SWITCH2:
       INC     A2
       MOVB    (A2)+,D1
       UCS
       CMPB    D1,#'C
       JEQ     SWITCH.C
       CMPB    D1,#'F
       JEQ     SWITCH.F
       CMPB    D1,#'M
       JEQ     SWITCH.M
       CMPB    D1,#'N
       JEQ     SWITCH.N
       CMPB    D1,#'S
       JEQ     SWITCH.S
       CMPB    D1,#'P
       JEQ     SWITCH.P
       CMPB    D1,#'T
       JEQ     SWITCH.T
       CMPB    D1,#'V
       JEQ     SWITCH.V
       CMPB    D1,#'W
       JEQ     SWITCH.W
       CMPB    D1,#'H
       JEQ     SWITCH.H
       CMPB    D1,#'?
       JEQ     SWITCH.H
       JMP     SWITCH.ERROR

;-------------------------------------------
;/C - show contiguous files in low intensity
;-------------------------------------------

SWITCH.C:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$CONTIG,FLAGS(MEM)
       HIGH
       RTN
10$:    AND     #^C<F$CONTIG>,FLAGS(MEM)
       RTN

;------------------------------------------------------
;/F - show full file information - equivalent to /S/V/T
;------------------------------------------------------

SWITCH.F:
       CALL    SWITCH.C                ; /C
       CALL    SWITCH.S                ; /S
       CALL    SWITCH.V                ; /V
       CALL    SWITCH.T                ; /T
       RTN

;------------------
;/H, /? - show help
;------------------

SWITCH.H:
DEFINE  LINE    TEXT
       ASCII   #TEXT#
       BYTE    CR
       ENDM

       TTYI
       LINE    <File Directory Utility>
       LINE    <Copyright (C) 1986, 1989 UltraSoft Corporation.  All Rights Reserved.>
       LINE
       IF EQ,FIND,LINE <Command format:                .D spec {, spec, ...spec}>
       IF NE,FIND,LINE <Command format:                .FIND spec {, spec, ...spec}>
       LINE    <Command switches:      /C - show contiguous files in low intensity>
       LINE    <                       /F - "full" - same as /C/S/V/T>
       LINE    <                       /N - no filenames, just totals>
       LINE    <                       /NOx - negates action of "/x">
       LINE    <                       /MIN:n - show files n blocks or larger in size>
       LINE    <                       /MAX:n - show files n blocks or smaller in size>
       LINE    <                       /P - "page" - use smooth scroll>
       LINE    <                       /S - show file sizes (default)>
       LINE    <                       /T - show file totals (default)>
       LINE    <                       /V - show version numbers>
       LINE    <                       /W:n - show n files per line (default: 4)>
       LINE    <Keystrokes:            0 .. 9 - change display speed>
       LINE    <                       SPACE  - suspend/resume output>
       LINE
       BYTE    0
       EVEN
       EXIT

;----------------------------------------------------------
;/N - display no filenames, only account numbers and totals
;----------------------------------------------------------
SWITCH.N:
       CMMB    @A2,#'O
       BEQ     SWITCH.NO
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$NO,FLAGS(MEM)
       AND     #^C<F$SIZ!F$VER!F$CONTIG>,FLAGS(MEM)
       RTN
10$:    AND     #^C<F$NO>,FLAGS(MEM)
       RTN

SWITCH.NO:
       XOR     #F$NEGATE,FLAGS(MEM)
       JMP     SWITCH2

;----------------------------------
;/M - beginning of /MAX:n or /MIN:n
;----------------------------------
SWITCH.M:
       MOVB    (A2)+,D1
       UCS
       CMPB    D1,#'I
       JEQ     SWITCH.MIN
       CMPB    D1,#'A
       JNE     SWITCH.ERROR

;---------------------------------------
;/MAX:n - set maximum block size to show
;---------------------------------------
SWITCH.MAX:
       MOVB    (A2)+,D1
       UCS
       CMPB    D1,#'X
       JNE     SWITCH.ERROR
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       CMMB    (A2)+,#':
       JNE     SWITCH.ERROR
       GTDEC
       MOV     D1,MAX.SIZE(MEM)
       RTN
10$:    SET     MAX.SIZE(MEM)
       RTN

;---------------------------------------
;/MIN:n - set minimum block size to show
;---------------------------------------
SWITCH.MIN:
       MOVB    (A2)+,D1
       UCS
       CMPB    D1,#'N
       JNE     SWITCH.ERROR
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       CMMB    (A2)+,#':
       JNE     SWITCH.ERROR
       GTDEC
       MOV     D1,MIN.SIZE(MEM)
       RTN
10$:    CLR     MIN.SIZE(MEM)
       RTN

;-------------------------------
;/P - "page" - set smooth scroll
;-------------------------------
SWITCH.P:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$PAGE,FLAGS(MEM)
       SMOOTH
       RTN
10$:    AND     #^C<F$PAGE>,FLAGS(MEM)
       JUMP
       RTN

;---------------------------------------
;/S - show file sizes, set width to four
;---------------------------------------
SWITCH.S:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$SIZ,FLAGS(MEM)
       BIT     #F$WIDTH,FLAGS(MEM)
       RNE
       CMM     WIDTH(MEM),#4
       RLE
       MOV     #4,WIDTH(MEM)
       RTN
10$:    AND     #^C<F$SIZ>,FLAGS(MEM)
       BIT     #F$WIDTH,FLAGS(MEM)
       RNE
       CMM     WIDTH(MEM),#4
       RNE
       MOV     #6,WIDTH(MEM)
       RTN

;-------------------------------------------------
;/V - display file version numbers, set width to 1
;-------------------------------------------------
SWITCH.V:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$VER,FLAGS(MEM)
       BIT     #F$WIDTH,FLAGS(MEM)
       RNE
       MOV     #1,WIDTH(MEM)
       RTN
10$:    AND     #^C<F$VER>,FLAGS(MEM)
       BIT     #F$WIDTH,FLAGS(MEM)
       RNE
       CMM     WIDTH(MEM),#1
       RNE
       MOV     #6,WIDTH(MEM)
       RTN

;---------------------------
;/T - show block/file totals
;---------------------------
SWITCH.T:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     10$
       OR      #F$TOTAL,FLAGS(MEM)
       RTN
10$:    AND     #^C<F$TOTAL>,FLAGS(MEM)
       RTN

;-------------------------------------------
;/W:n - set width (number of files per line)
;-------------------------------------------
SWITCH.W:
       BIT     #F$NEGATE,FLAGS(MEM)
       BNE     20$
       MOV     #4,D1
       C
MMB     @A2,#':
       BNE     10$
       INC     A2
       GTDEC
10$:    CMP     D1,#1
       BLO     FORMAT.ERROR
       MOV     D1,WIDTH(MEM)
       OR      #F$WIDTH,FLAGS(MEM)
       JMP     SWITCH
20$:    AND     #^C<F$WIDTH>,FLAGS(MEM)
       MOV     #4,WIDTH(MEM)
       RTN

SWITCH.ERROR:
       LEA     A1,UNKNOWN.SWITCH
       CALL    $CMDER
       EXIT

FORMAT.ERROR:
       LEA     A1,COMMAND.FORMAT.ERROR
       CALL    $CMDER
       EXIT

;------------------------
;Show total blocks, files
;------------------------
SHOW.TOTAL:
       MOV     TOTAL.BLOCKS(MEM),D1
       REQ
       CMM     COL,WIDTH(MEM)          ; are we in mid-line?
       BEQ     10$                     ;  no
       CALL    NEW.LINE                        ; yeah - go to next line
10$:    TYPESP  Total of
       DCVT    0,OT$TRM!OT$TSP
       TYPE    block
       CMP     D1,#1
       BEQ     20$
       TYPE    s
20$:    TYPE    < in >
       MOV     TOTAL.FILES(MEM),D1
       DCVT    0,OT$TRM
       TYPE    < file>
       CMP     D1,#1
       BEQ     30$
       TYPE    s
30$:    CALL    NEW.LINE
       MOV     TOTAL.BLOCKS(MEM),D7
       ADD     D7,GRAND.BLOCKS(MEM)
       MOV     TOTAL.FILES(MEM),D7
       ADD     D7,GRAND.FILES(MEM)
       RTN

;-------------------------------------------------------------
;subroutine - convert RAD50 triplet @A1 to ASCII and output it
;-------------------------------------------------------------
DEPACK: SAVE    A1,A2
       SUB     #4,SP
       MOV     SP,A2
       UNPACK
       CLRB    @A2
       TTYL    @SP
       ADD     #4,SP
       REST    A1,A2
       RTN

;----------------------------------
;subroutine - output CR/LF and wait
;----------------------------------
NEW.LINE:
       SAVE    D0
       CRLF
       MOV     WIDTH(MEM),COL
       CALL    HIGH.INTENSITY
       MOVWL   DELAY(MEM),D0
       BEQ     10$
       MUL     D0,#1000.
       SLEEP   D0
10$:    REST    D0

CHECK.CHAR:
       TST     T.ICC(TRM)
       REQ
       KBD     EXIT
       CMPB    D1,#ESC
       JEQ     EXIT
       CMPB    D1,#40
       JEQ     SUSPEND
       CMPB    D1,#'S-'@
       JEQ     SUSPEND
       CMPB    D1,#'0
       RLO
       CMPB    D1,#'9
       RHI
       AND     #177,D1
       SUBB    #'0,D1
       MOVW    D1,DELAY(MEM)
       BR      CHECK.CHAR

SUSPEND:
       KBD     EXIT
       CMPB    D1,#ESC
       JEQ     EXIT
       CMPB    D1,#'S-'@
       BEQ     SUSPEND
       RTN

;------------------------------------
;subroutine - find next matching file
;------------------------------------
FIND.FILE:
       CTRLC   10$
       WSCAN                           ; get first file - return @INDEX
       RNE
       CMM     D.FSZ(INDEX),MIN.SIZE(MEM)
       BLO     FIND.FILE
       CMM     D.FSZ(INDEX),MAX.SIZE(MEM)
       BHI     FIND.FILE
10$:    LCC     #PS.Z
       RTN

;------------------------------
;subroutine - set low intensity
;------------------------------
LOW.INTENSITY:
       BIT     #F$CONTIG,FLAGS(MEM)    ; do we care about intensity?
       REQ                             ;  no
       BIT     #F$LOW,FLAGS(MEM)       ; low intensity flag set?
       RNE                             ;  yes - do nothing
       LOW
       OR      #F$LOW,FLAGS(MEM)
       RTN

;-------------------------------
;subroutine - set high intensity
;-------------------------------
HIGH.INTENSITY:
       BIT     #F$CONTIG,FLAGS(MEM)    ; do we care about intensity?
       REQ                             ;  no
       BIT     #F$LOW,FLAGS(MEM)       ; low intensity flag set?
       REQ                             ;  no - do nothing
       HIGH
       AND     #^C<F$LOW>,FLAGS(MEM)
       RTN

;------------
;switch table
;------------
SWITCH.TABLE:
       BYTE    'S,F$SIZ                ; /S - show file sizes
       BYTE    'V,F$VER                ; /V - show file version numbers
       BYTE    0
       EVEN

;--------------
;text constants
;--------------
UNKNOWN.SWITCH:
       ASCIZ   /Unknown switch/

COMMAND.FORMAT.ERROR:
       ASCIZ   /Command format error/
       EVEN

       END