home *** CD-ROM | disk | FTP | other *** search
Text File | 1994-07-13 | 30.1 KB | 1,510 lines |
- ;
- ; PROGRAM: MENU
- ; AUTHOR: RICHARD CONN
- ; VERSION: 3.2
- ; DATE: 10 June 84
- ; PREVIOUS VERSIONS: 3.1 (28 Mar 84), 3.0 (18 Mar 84)
- ; DERIVATION. MENU 1.4 for ZCPR2
- ;
- VERS EQU 32
-
- ;
- ; MENU is the ZCPR3 Menu Processor. It loads, looks for the MENU.MNU
- ; file, and then displays it to the user (optionally) and prompts him for
- ; a single-character command. The ZCPR3 Multiple Command Line Buffer must
- ; be installed for MENU to work, and MENU uses this buffer to chain to the
- ; programs selected by the user and return to itself at the proper place.
- ;
- ; MENU supports multiple menus within one MENU.MNU file. When a command
- ; is invoked, MENU returns to the menu the command came from.
- ;
- ; MENU will ONLY RUN on ZCPR3 systems with the Multiple Command Line
- ; Buffer Option enabled.
- ;
-
- ;
- ; Menu Constants
- ;
- sysmenu equ 0 ;System Menu Enabled? 0=no, 1=yes
-
- ; 1 Special Menu Command Chars
- RNM EQU '>' ;NEXT MENU
- RNMP EQU '.' ;NEXT MENU PRIME (ALTERNATE)
- RLM EQU '<' ;LAST MENU
- RLMP EQU ',' ;LAST MENU PRIME (ALTERNATE)
- RFM EQU '*' ;FIRST MENU
- ;
- if sysmenu
- RSM EQU '$' ;SYSTEM MENU (PASSWORD REQUIRED)
- ; THIS IS SAME AS CONTROL CHAR
- endif ;sysmenu
-
- ; 2 Internal Menu Control Chars
- MCMD EQU ':' ;COMMAND TO JUMP TO ANOTHER MENU
- PCHAR EQU '"' ;INDICATES AUTO PROMPT FOR SPECIFIC CMD
- MINDIC EQU '#' ;MENU SECTION INDICATOR
- MFIRST EQU '%' ;FIRST MENU INDICATOR
- GOPTION EQU '-' ;GLOBAL OPTION INDICATOR
- WOPTION EQU '!' ;ACTIVATES WAIT UPON RETURN
-
- ; 3 Menu Option Chars
- COPTION EQU 'C' ;DISPLAY COMMAND LINE TO USER
- DOPTION EQU 'D' ;DISPLAY MENU TO USER
- POPTION EQU 'P' ;PAGE OUT MENU DISPLAY TO USER
- XOPTION EQU 'X' ;DISABLE ZCPR3 RETURN
-
- ; 4 Miscellaneous
- IBUFSZ EQU 254 ;SIZE OF INPUT LINE BUFFER
- VARFLAG EQU '$' ;VARIABLE FLAG
- ;(FOLLOWED BY D,U,Fn,Nn,Tn)
- CMDSEP EQU ';' ;ZCPR3 COMMAND SEPARATOR
-
- ;
- ; Enter/Exit Standout Mode (Recommended that these values not be changed)
- ;
- DIM EQU 'A'-'@' ; ^A TO ENTER STANDOUT
- NOTDIM EQU 'B'-'@' ; ^B TO EXIT STANDOUT
-
- ;
- ; MACRO Library of Definitions
- ;
- MACLIB Z3BASE.LIB
-
- ;
- ; ZCPR3 CONSTANTS
- ;
- wboot equ 0
- bentry equ 5
- fcb equ 5ch
- tbuff equ 80h
- BEL equ 7
- CR equ 0dh
- LF equ 0ah
- CTRLC equ 'C'-'@'
- TAB equ 'I'-'@'
- CTRLZ equ 'Z'-'@'
-
- ;
- ; MACROS TO PROVIDE Z80 EXTENSIONS
- ; MACROS INCLUDE:
- ;
- ; BR - JUMP RELATIVE
- ; BRC - JUMP RELATIVE IF CARRY
- ; BRNC - JUMP RELATIVE IF NO CARRY
- ; BRZ - JUMP RELATIVE IF ZERO
- ; BRNZ - JUMP RELATIVE IF NO ZERO
- ; BJNZ - DECREMENT B AND JUMP RELATIVE IF NO ZERO
- ; PUTRG - SAVE REGISTERS
- ; GETRG - RESTORE REGISTERS
- ;
-
- ;
- ;
- ; Z80 MACRO EXTENSIONS
- ;
- BR MACRO ?N ;;JUMP RELATIVE
- IF I8080 ;;8080/8085
- JMP ?N
- ELSE ;;Z80
- .Z80
- JR ?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- BRC MACRO ?N ;;JUMP RELATIVE ON CARRY
- IF I8080 ;;8080/8085
- JC ?N
- ELSE ;;Z80
- .Z80
- JR C,?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- BRNC MACRO ?N ;;JUMP RELATIVE ON NO CARRY
- IF I8080 ;;8080/8085
- JNC ?N
- ELSE ;;Z80
- .Z80
- JR NC,?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- BRZ MACRO ?N ;;JUMP RELATIVE ON ZERO
- IF I8080 ;;8080/8085
- JZ ?N
- ELSE ;;Z80
- .Z80
- JR Z,?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- BRNZ MACRO ?N ;;JUMP RELATIVE ON NO ZERO
- IF I8080 ;;8080/8085
- JNZ ?N
- ELSE ;;Z80
- .Z80
- JR NZ,?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- BJNZ MACRO ?N ;;DECREMENT B AND JUMP RELATIVE ON NO ZERO
- IF I8080 ;;8080/8085
- DCR B
- JNZ ?N
- ELSE ;;Z80
- .Z80
- DJNZ ?N
- .8080
- ENDIF ;;I8080
- ENDM
- ;
- PUTRG MACRO
- PUSH H ;;SAVE REGISTERS IN ORDER
- PUSH D
- PUSH B
- ENDM
- ;
- GETRG MACRO
- POP B ;;RESTORE REGISTERS IN ORDER
- POP D
- POP H
- ENDM
- ;
- ; END OF Z80 MACRO EXTENSIONS
- ;
-
- ;
- ; Externals from SYSLIB
- ;
- ext z3vinit,cls,stndout,stndend
- ext getcl1,putcl,getsh2,qshell,retud,getefcb,shpush,shpop
- ext getshm,putshm,moveb,getfn2,pfn1,getcrt,getzrun,putzex,putcst
- ext eprint,cin,cout,caps,crlf,pafdc,madc,bline,initfcb,sksp
- ext f$open,f$close,f$read,codend,hmovb
-
- ;
- ; Environment Definition
- ;
- if z3env ne 0
- ;
- ; External ZCPR3 Environment Descriptor
- ;
- jmp start
- db 'Z3ENV' ;This is a ZCPR3 Utility
- db 1 ;External Environment Descriptor
- z3eadr:
- dw z3env
- start:
- lhld z3eadr ;pt to ZCPR3 environment
- ;
- else
- ;
- ; Internal ZCPR3 Environment Descriptor
- ;
- MACLIB SYSENV.LIB
- z3eadr:
- jmp start
- SYSENV
- start:
- lxi h,z3eadr ;pt to ZCPR3 environment
- endif
-
- ;
- ; Start of Program -- Initialize ZCPR3 Environment
- ;
- call z3vinit ;initialize the ZCPR3 Env and the VLIB Env
- jmp strt
- ;
- ; This is the FCB which defines the default name of the MENU.MNU file
- ;
- if sysmenu
- ppass:
- db 'SYSTEM ',0 ;system password
- endif ;sysmenu
- ;
- menufcb:
- db 0 ;FCB for MENU.MNU
- db 'MENU '
- db 'MNU'
- ds 4
- scratch: ;this doubles as a scratch area
- ds 16 ;buffer definition is at end of program
- ds 4 ;36 bytes total
-
- ;
- ; Start of Program
- ;
- strt:
- ;
- ; Check for Shell Stack
- ;
- call getsh2 ;get shell status
- brnz strt0 ;skip over shell init
- call eprint
- db ' No Shell Stack',0
- ret
- ;
- ; See if Command Line Available
- ;
- strt0:
- call getcl1 ;get line
- brnz strt01
- call eprint
- db ' No Command Line',0
- ret
- ;
- ; See if this program was invoked as a shell
- ;
- strt01:
- call qshell ;find out from ZCPR3 environment
- push psw ;save status
- xra a ;A=0
- call putcst ;put command status (normal = 0)
- pop psw ;restore status
- jz menu ;do not push onto stack if invoked as a shell
- ;
- ; Set Name of Shell from External FCB if Possible or From Default if Not
- ;
- setshn:
- call retud ;get run address
- lxi h,shdisk ;pt to shell disk
- mov a,b ;get disk
- adi 'A' ;convert to letter
- mov m,a ;set disk letter
- inx h ;pt to user 10's
- mov a,c ;get user number
- mvi b,10 ;subtract 10's
- mvi d,'0' ;set char
- setshn1:
- sub b ;subtract
- brc setshn2
- inr d ;increment digit
- br setshn1
- setshn2:
- add b ;get 1's
- mov m,d ;set 10's digit for user
- inx h ;pt to 1's digit
- adi '0' ;compute 1's digit
- mov m,a ;set 1's digit
- call getefcb ;get ptr to external fcb
- brz strt02 ;no external FCB, so use default name
- inx h ;pt to program name
- lxi d,shname ;pt to string
- mvi b,8 ;8 chars
- call moveb ;copy into buffer
- ;
- ; Check for File Name and Set It If Given
- ;
- strt02:
- lxi h,fcb+1 ;pt to file name
- lxi d,menufcb+1
- mvi b,11 ;11 chars
- mov a,m ;get first char
- cpi ' '
- cnz moveb ;copy if one present
- ;
- ; Set File Name in MENUFCB into Line
- ;
- lxi h,menufcb+1 ;set shell file name
- lxi d,shfile ;pt to shell file
- mvi b,8 ;8 chars
- strt03:
- mov a,m ;get next char
- cpi ' ' ;done?
- brz strt04
- stax d ;put char
- inx d ;pt to next
- strt04:
- inx h ;pt to next
- bjnz strt03
- mvi a,'.' ;put dot
- stax d
- inx d ;pt to next
- mvi b,3 ;file type
- strt05:
- mov a,m ;copy
- stax d
- inx h ;pt to next
- inx d
- bjnz strt05
- xra a ;store zero
- stax d
-
- ;
- ; Set Menu Number
- ;
- mvi b,1 ;shell message 1
- xra a ;menu 0
- call putshm ;set message
-
- ;
- ; Push Name of Shell onto Stack
- ;
- lxi h,shdisk ;pt to name of shell
- call shpush ;push shell onto stack
- brnz strt2
- ;
- ; Shell Successfully Installed
- ;
- call eprint
- db ' Shell Installed',0
- ret
- ;
- ; Shell Stack Push Error
- ;
- strt2:
- cpi 2 ;shell stack full?
- brnz strt3
- ;
- ; Shell Stack is Full
- ;
- call eprint
- db ' Shell Stack Full',0
- ret
- ;
- ; Shell Stack Entry Size is too small for command line
- ;
- strt3:
- call eprint
- db ' Shell Stack Entry Size',0
- ret
- ;
- ; Check for ZEX Execution and Pass ZEX if So
- ;
- menu:
- call getzrun ;is ZEX running?
- brz runmenu ;process menu if not
- br menuz1 ;skip new line
- menuzex:
- call crlf ;new line
- menuz1:
- call eprint
- db 'Menu> ',0
- mvi a,1 ;tell ZEX that it is prompted
- call putzex
- call codend ;set up buffer
- mvi m,ibufsz ;set size
- mvi a,0FFH ;capitalize
- call bline ;get line from ZEX
- xra a ;A=0
- call putzex ;resume ZEX normally
- call sksp ;skip over leading spaces
- mov a,m ;check for comment
- cpi ';'
- brz menuzex
- xchg ;DE pts to command line
- xra a ;don't display command
- sta cpflag
- jmp runcmnd ;run command pted to by DE
- ;
- ; Begin Menu Processing
- ;
- runmenu:
- call eprint
- db 'MENU Version '
- db (vers/10)+'0','.',(vers mod 10)+'0',0
- ;
- ; Check for Wait Flag and Wait if So
- ;
- mvi b,0 ;get shell message 0
- call getshm
- ani 80h ;check for wait flag
- cnz sak ;Strike Any Key
- ;
- ; Open Menu File
- ;
- lxi h,fcb ;copy FCB into MENU FCB
- lxi d,menufcb
- mvi b,36 ;36 bytes
- push d ;save ptr
- call moveb
- pop d ;pt to MENU.MNU FCB
- call initfcb ;init fcb
- call f$open ;open file
- brz menu1 ;abort if no menu
- call eprint
- db CR,LF,' File ',0
- lxi d,menufcb+1
- call pfn1
- call eprint
- db ' Not Found',0
- jmp shpop
- ;
- ; Load MENU.MNU from disk
- ;
- menu1:
- call codend ;get address of buffer for menu load
- mload:
- lxi d,menufcb ;pt to FCB
- call f$read ;read in next block
- ora a ;error?
- brnz mloaddn ;load done if error
- lxi d,tbuff ;copy from TBUFF into memory pted to by HL
- xchg ;HL is source, DE is dest
- mvi b,128 ;128 bytes
- call hmovb
- lhld bentry+1 ;get address of top of TPA
- mov a,h ;set to bottom of ZCPR3
- sui 10
- cmp d ;about to overflow ZCPR3?
- brnc mload1 ;continue if not
- call eprint
- db CR,LF,' TPA Full',0
- ret
- mload1:
- xchg ;HL pts to next byte to load to
- br mload ;continue load
-
-
- ;
- ; Init Flags and Clear MSB of all bytes in Menu File
- ;
- mloaddn:
- call f$close ;close input file
- mvi m,CTRLZ ;ensure EOF mark
- lxi d,80H ;pt to next block
- dad d
- shld ibuff ;set ptr to input line buffer
- mvi m,ibufsz ;set size
- dad d ;allow 256 bytes
- dad d
- shld expline ;set ptr to expand line
- xra a ;A=0
- sta cflag ;turn off command display
- sta dflag ;turn off menu display
- sta pflag ;disallow paging
- sta cpmok ;turn off ZCPR3 return flag
- call codend ;pt to beginning of file
- push h ;save ptr
- menul1:
- mov a,m ;get byte
- ani 7FH ;mask out MSB
- mov m,a ;put byte
- inx h ;pt to next
- cpi CTRLZ ;EOF?
- brnz menul1 ;continue if not
- ;
- ; Mark all Menu Sections
- ;
- pop h ;HL pts to first byte of menu
- mvi b,0FFH ;set menu counter
- ;
- ; Skip to Next Menu
- ;
- menul2:
- mov a,m ;get byte
- cpi CTRLZ ;error?
- jz mstrerr ;structure error if so
- cpi MINDIC ;menu indicator (start of menu?)
- brnz menul4
- ori 80H ;beginning of menu found -- set MSB
- mov m,a ;put byte
- inr b ;increment menu count
- inx h ;pt to next
- mov a,m ;get byte
- cpi MINDIC ;menu indicator (end of menu?)
- brz menul5 ;done if so
- cpi CTRLZ ;error?
- jz mstrerr
- ;
- if sysmenu
- cpi RSM ;system menu indicator?
- brnz menul3
- mov a,b ;set system menu number
- sta smeno
- mvi a,0FFH ;set flag
- sta smenfl ;system menu present
- dcx h ;back up to beginning of menu
- shld smenadr ;start address
- inx h ;pt to RSM
- endif ;sysmenu
- ;
- ; Skip out Menu Display
- ;
- menul3:
- call lskipt ;skip to beginning of next line
- brz menul4 ;found menu indicator
- cpi CTRLZ ;error?
- jz mstrerr
- br menul3 ;continue if not
- ;
- ; Skip to Next Menu
- ;
- menul4:
- call lskip ;skip to beginning of next menu
- br menul2
- ;
- ; Check Menu Options
- ;
- menul5:
- call codend ;pt to beginning of file
- mov a,m ;check for option
- cpi GOPTION ;global option char?
- jnz mfile ;if no global option, scan for menu files
- inx h ;pt to option char
- option:
- mov a,m ;get option char
- call caps ;capitalize
- inx h ;pt to next
- cpi CR ;done?
- brz optdn
- cpi COPTION ;display command?
- brz optc
- cpi DOPTION ;display menu?
- brz optd
- cpi POPTION ;paging?
- brz optp
- cpi XOPTION ;exit OK?
- jnz mstrerr ;option error if not
- ;
- ; Disable Exit to ZCPR3
- ;
- mvi a,0FFH ;turn flag off
- sta cpmok
- br option
- ;
- ; Process Paging Option
- ;
- optp:
- mvi a,0FFH ;set flag
- sta pflag
- br option
- ;
- ; Process Display Menu Option
- ;
- optd:
- mvi a,0FFH ;set flag
- sta dflag
- br option
- ;
- ; Process Display Command Option
- ;
- optc:
- mvi a,0FFH ;set flag
- sta cflag
- br option
-
- ;
- ; Option Processing Done
- ;
- optdn:
- inx h ;skip LF
-
- ;
- ; Check for Menu Display
- ;
- mfile:
- mov a,m ;get first byte
- ani 7FH ;mask
- cpi MINDIC ;start of menu?
- jnz mstrerr
-
- ;
- ; Check and Set First Menu
- ;
- shld mstart ;save start address of first menu item
- mvi m,MFIRST+80H ;set first char of first menu
-
- ;
- ; Entry Point for Menu Display
- ; On entry, HL pts to first byte of current menu
- ;
- dmenu:
- mvi b,1 ;shell message 1 contains menu number
- call getshm ;get menu number flag
- cnz mchc0 ;skip to proper menu
- shld cstart ;save start address of current menu
- lda cflag ;copy display command flag for temp use
- sta cpflag
- lda dflag ;copy display menu flag for temp use
- sta dpflag
- lda pflag ;copy paging flag for temp use
- sta ppflag
- inx h ;pt to first char after menu indicator char
- dispm1:
- mov a,m ;get char
- call caps ;capitalize
- inx h ;pt to next
- cpi CR ;end of options?
- brz dispm2
- ;
- if sysmenu
- cpi RSM ;system menu?
- brz dispm1 ;ok if so
- endif ;sysmenu
- ;
- cpi COPTION ;command display?
- brz dispmc
- cpi DOPTION ;display?
- brz dispmd
- cpi POPTION ;paging?
- brz dispmp
- cpi XOPTION ;ZCPR3 return?
- jnz mstrerr ;error if not
- ;
- ; Toggle ZCPR3 Return Option
- ;
- lda cpmok ;get flag
- cma ;toggle
- sta cpmok
- br dispm1
- ;
- ; Toggle Paging Option
- ;
- dispmp:
- lda ppflag ;get flag
- cma ;toggle
- sta ppflag
- br dispm1
- ;
- ; Toggle Display Menu Option
- ;
- dispmd:
- lda dpflag ;get flag
- cma ;toggle
- sta dpflag
- br dispm1
- ;
- ; Toggle Display Command Option
- ;
- dispmc:
- lda cpflag ;get flag
- cma ;toggle
- sta cpflag
- br dispm1
- ;
- ; Done with Menu-Specific Option Processing
- ;
- dispm2:
- call lskip ;skip to LF
- lda dpflag ;display menu?
- ora a ;0=no
- brz dispm8 ;skip over menu if not
- call getnlines ;get line count in A
- sta pagcnt ;set count
- lda ppflag ;paging?
- ora a ;0=no
- push psw ;save flag
- cnz cls ;clear screen if so
- pop psw ;get flag
- cz crlf ;else new line
- ;
- ; Print Next Line of Menu if not Starting with ESCAPE Char (MINDIC)
- ;
- dispm3:
- mov a,m ;get first char of line
- ani 7FH ;mask
- cpi MINDIC ;done?
- brz dispm4
- call expand ;expand line pted to by HL
- push h ;save ptr to next line
- xchg ;HL pts to expanded line
- call lprintx ;print line pted to by HL ending in <CR>
- pop h ;pt to next line
- br dispm3
- ;
- ; Done with Menu Display -- Page it out
- ;
- dispm4:
- call lskip ;skip to first char of next line (option char)
- shld optstrt ;set start address of options
- lda pagcnt ;number of remaining lines
- mov b,a ;count in B
- ora a ;ok?
- brz dispm6 ;don't do anything if already there
- lda ppflag ;page?
- ora a ;0=No
- brz dispm6
- ;
- ; Page Loop for Menu Display
- ;
- dispm5:
- call crlf ;new line
- bjnz dispm5
- ;
- ; Determine if Another Menu Follows
- ;
- dispm6:
- xra a ;A=0
- sta nmenfl ;set for no next menu
- mov a,m ;ok?
- ani 7FH ;mask
- cpi CTRLZ ;error if EOF
- jz mstrerr
- cpi MINDIC ;next menu?
- brnz dispm7
- inx h ;double indicator if end
- mov a,m
- cpi MINDIC ;end?
- brz dispm9
- ;
- if sysmenu
- cpi RSM ;system menu = no next menu
- brz dispm9
- endif ;sysmenu
- ;
- mvi a,0FFH ;set next menu
- sta nmenfl
- br dispm9
- dispm7:
- call lskip ;skip to next line
- br dispm6
-
- ;
- ; Skip over current menu so it is not displayed
- ;
- dispm8:
- call lskipt ;skip to beginning of command
- brnz dispm8
- call lskip ;skip over end of display indicator
- shld optstrt ;set pointer to options
- br dispm6 ;determine if next menu available
- dispm9:
-
- ;
- ; Ready for Option Input
- ; The following Flags/Values are now set:
- ; CPFLAG -- Display Command Flag (0=No, 0FFH=Yes)
- ; DPFLAG -- Display Menu Flag (0=No, 0FFH=Yes)
- ; OPTSTRT -- Address of First Menu Option
- ; NMENFL -- 0 if no next menu, 0FFH if next menu
- ; MSTART -- Start Address of MINDIC Before Menu Display
- ; (MSTART)=MFIRST with MSB Set
- prompt:
- call stndout ;begin standout
- mvi a,0ffh
- sta pagcnt ;turn off paging
- sta dpflag ;turn on future menu displays
- call retud ;get DU
- mov a,b ;print D
- adi 'A'
- call cout
- mov a,c ;print U
- call pafdc
- call eprint
- db '> Command (CR=Menu',0
- lda cpmok ;OK to return to ZCPR3?
- ora a ;0=No
- cnz prmptc
- lhld cstart ;pt to first char
- mov a,m ;get it
- ani 7FH ;mask
- cpi MFIRST
- cnz prmptf ;print previous menu prompt if not first menu
- lda nmenfl ;next menu available?
- ora a ;0=No
- cnz prmptn ;print next menu prompt
- call eprint
- db ') - ',0
- call stndend ;end standout
- prompt1:
- call cin ;get response
- call caps ;capitalize
- mov b,a ;result in B
-
- ;
- ; Check for CR
- ;
- cpi CR ;<CR>?
- jz dispm2 ;reprint menu if so
-
- ;
- ; Check for Reboot
- ;
- lda cpmok ;ok to abort?
- ora a ;0=No
- brz prmpt0
- mov a,b ;get command
- cpi CTRLC ;reboot?
- jz shpop ;pop shell stack and return to OS if so
-
- ;
- ; Check for Command to Return to First Menu
- ;
- prmpt0:
- mov a,m ;get it
- ani 7FH ;mask
- cpi MFIRST
- brz prmpt1
- mov a,b ;get command
- cpi RFM ;return to first menu?
- brnz prmpt1
- lhld mstart ;pt to first menu
- mvi b,1 ;shell message 1 is menu number
- xra a ;A=0=menu 0
- jmp putshm ;reenter shell at first menu
-
- ;
- ; Check for Command to go to Next Menu
- ;
- prmpt1:
- lda nmenfl ;next menu available?
- ora a ;0=No
- brz prmpt2
- mov a,b ;get command
- cpi RNMP ;goto next menu?
- brz rnmx
- cpi RNM ;goto next menu?
- brnz prmpt2
- rnmx:
- mvi b,1 ;shell message 1 is menu number
- call getshm ;increment menu number
- inr a
- jmp putshm ;reenter menu system at new menu
-
- ;
- ; Check for Command to go to Last Menu
- ;
- prmpt2:
- mov a,m ;get menu char
- ani 7FH ;at first menu?
- cpi MFIRST
- brz prmpt3 ;skip if at first menu
- mov a,b ;get command
- cpi RLMP ;goto last menu?
- brz lstmnu
- cpi RLM ;goto last menu?
- brnz prmpt3
- lstmnu:
- mvi b,1 ;shell message 1 is menu number
- call getshm ;decrement menu number
- dcr a
- jmp putshm ;reenter shell at last menu
-
- ;
- ; Check for Command to goto System Menu
- ;
- prmpt3:
- if sysmenu
- ;
- lda smenfl ;system menu available?
- ora a ;0=No
- brz prmpt4
- mov a,b ;get command
- cpi RSM ;system menu?
- brnz prmpt4
- call password ;prompt for and get password
- jnz prompt ;reprompt if error
- lhld smenadr ;get address of system menu
- lda smeno ;set system menu number
- mvi b,1 ;shell message 1 is menu number
- jmp putshm ;reenter shell at system menu
- ;
- endif ;sysmenu
- ;
- ; This is where additional functions may be added
- ;
- prmpt4:
-
- ;
- ; Check for Option Letter
- ;
- lhld optstrt ;pt to first option char
- prmptx:
- mov a,m ;get it
- call caps ;capitalize
- cpi MINDIC ;at next menu?
- brz prmpter
- cmp b ;match user selection?
- brz prmptd
- call lskip ;skip to next line
- br prmptx
-
- ;
- ; Invalid Option
- ;
- prmpter:
- call eprint
- db BEL,0
- jmp prompt1
-
- ;
- ; Process Option
- ;
- prmptd:
- mov a,b ;output user selection
- call cout
- mvi b,0 ;shell message 0, bit 7 = wait flag
- call getshm
- ani 7FH ;set no wait
- call putshm
- inx h ;pt to first letter of command
- mov a,m ;get it
- cpi MCMD ;invoke other menu?
- jz mchcmd ;menu change command
- cpi WOPTION ;turn on wait?
- brnz prmptg
- mvi b,0 ;shell message 0, bit 7 = wait flag
- call getshm
- ori 80h ;set wait flag
- call putshm ;set shell message
- inx h ;skip option char
- prmptg:
- call expand ;expand line, DE pts to result
- ;
- ; Run Command Pted to by DE
- ;
- runcmnd:
- call getcl1 ;get address of command buffer
- mov b,h ;... in BC also
- mov c,l
- mvi a,4 ;HL=HL+4 for address of first char
- add l
- mov l,a
- mov a,h
- aci 0
- mov h,a
- mov a,l ;store address
- stax b
- inx b
- mov a,h
- stax b
- ;
- ; Copy Command Line in DE into Buffer in HL
- ;
- cmdcpy:
- ldax d ;get command letter
- call caps ;capitalize it
- ora a ;done?
- brz ccpyd
- cpi CR ;done?
- brz ccpyd
- cpi PCHAR ;prompt?
- brz ccpyp
- mov m,a ;store it
- inx h ;pt to next
- inx d
- br cmdcpy
- ccpyd:
- mvi m,0 ;store ending 0
- jmp cmddisp ;optionally display command
- ;
- ; Prompt User for Input and Accept It
- ;
- ccpyp:
- inx d ;pt to first char of prompt
- call crlf ;new line
- ccpyp1:
- ldax d ;get char
- cpi PCHAR ;end of prompt?
- brz ccpyp2
- cpi CR ;new line?
- brz ccpyp3
- call cout ;echo char
- inx d ;pt to next char
- br ccpyp1 ;continue looping
- ccpyp2:
- inx d ;pt to char after closing PCHAR
- ccpyp3:
- push d ;save ptr to next char
- xchg ;DE pts to buffer
- mvi a,0FFH ;capitalize input from user
- lhld ibuff ;input line buffer
- call bline ;get input from user
- xchg ;HL pts to buffer, DE pts to user input
- cmdlp:
- ldax d ;get char from user
- ora a ;end of input?
- brz cmdlp1 ;store rest of line
- mov m,a ;store char
- inx h ;pt to next
- inx d
- br cmdlp
- cmdlp1:
- pop d ;DE pts to next char, HL pts to buffer
- br cmdcpy ;resume copying
- ;
- ; Check for Display of Loaded Command and Do So if Set
- ;
- cmddisp:
- lda cpflag ;display command?
- ora a ;0=No
- rz ;return to OS if so to run command
- call crlf ;new line
- call getcl1 ;pt to first char
- mov e,m ;get low-order address
- inx h
- mov d,m ;get high-order address
- xchg ;HL pts to first char
- cmdd1:
- mov a,m ;get char
- cpi CMDSEP ;done if command separator
- rz
- inx h ;pt to next
- call cout ;print char
- br cmdd1
-
- ;
- ; Menu Change Command -- Jump to Specified Menu
- ;
- mchcmd:
- inx h ;pt to menu number
- call eval ;convert to decimal number in A
- sta menuno ;save menu number
- call mchc0 ;skip to desired menu to check for it
- lda menuno ;get menu number
- mvi b,1 ;menu number is shell message 1
- jmp putshm ;set message and reenter shell
-
- ;
- ; Entry Point if MENU is Reinvoked
- ;
- mchc0:
- mov b,a ;menu number in B
- inr b ;add 1 for initial offset
- lhld mstart ;pt to first menu
- mchc1:
- dcr b ;count down
- rz ;done if found
- mchc2:
- call lskipt ;skip to next line
- brnz mchc2 ;continue if not end of menu display
- mchc3:
- call lskipt ;skip to next line
- brnz mchc3 ;continue if not at end of menu commands
- inx h ;end of MENU.MNU?
- mov a,m ;yes if double MINDIC
- ani 7FH ;mask
- cpi MINDIC
- brz mchcerr ;error if so
- dcx h ;pt to first char
- br mchc1 ;continue
- ;
- ; Premature End of Menu File
- ;
- mchcerr:
- pop psw ;clear stack
- jmp mstrerr ;menu structure error
-
- ;
- ; Print Line pted to by HL Ending in <CR>
- ; Decrement PAGCNT
- ;
- lprintx:
- call lprint ;print without <CR>
- jmp crlf ;do <CR> <LF>
- ;
- ; Print Line Pted to by HL; Decrement PAGCNT
- ;
- lprint:
- mvi b,0 ;set tab counter
- lprnt0:
- mov a,m ;get char
- inx h ;pt to next
- ani 7FH ;mask MSB
- cpi DIM ;goto standout mode?
- brz lprnt3
- cpi NOTDIM ;end standout mode?
- brz lprnt4
- cpi TAB ;tabulate?
- brz lprnt2
- cpi CR ;done?
- brz lprnt1
- call cout ;print
- inr b ;incr tab counter
- br lprnt0
- lprnt1:
- inx h ;pt to first char of next line
- lda pagcnt ;count down pages
- dcr a
- sta pagcnt
- rnz
- call getnlines ;get line count in A
- sta pagcnt
- call eprint
- db CR,LF,'Pause -',0
- br sak1
- lprnt2:
- mvi a,' ' ;print <SP>
- call cout
- inr b ;incr tab counter
- mov a,b ;done?
- ani 7 ;every 8
- brnz lprnt2
- br lprnt0
- lprnt3:
- call stndout ;enter standout mode
- br lprnt0
- lprnt4:
- call stndend ;end standout mode
- br lprnt0
- ;
- ; Strike Any Key Message
- ;
- sak:
- mvi b,0 ;clear any pending wait
- call getshm
- ani 7FH ;mask MSB
- call putshm
- sak1:
- call stndout ;goto standout
- call eprint
- db ' Strike Any Key - ',0
- call stndend ;exit standout
- call cin ;get response
- call crlf ;new line
- ret
-
- ;
- ; Prompt for, input, and check password (only one chance)
- ; If accepted, return with Zero Flag Set; if not, return with NZ
- ;
- if sysmenu
- password:
- call eprint
- db CR,LF,'Pass? ',0
- lhld ibuff ;pt to input line buffer
- xra a ;don't capitalize user input
- call bline ;get line from user
- lxi d,ppass ;pt to system password
- pass1:
- ldax d ;get sys pass char
- cmp m ;ok?
- brnz passerr ;error if no match
- inx h ;pt to next
- inx d
- ora a ;end of strings?
- brnz pass1
- ret ;return with zero set to show match
- passerr:
- call eprint
- db CR,LF,' Password Error',0
- call sak1 ;strike any key
- call crlf
- mvi a,0FFH ;set no zero
- ora a
- ret
- endif ;sysmenu
- ;
- ; Skip to Beginning of Next Line and Test First Char for Menu Indicator
- ;
- lskipt:
- call lskip ;skip
- mov a,m ;get char
- ani 7FH ;mask
- cpi MINDIC ;test
- ret
-
- ;
- ; Skip to Beginning of Next Line
- ;
- lskip:
- mov a,m ;get char
- ani 7FH ;mask out MSB
- inx h ;pt to next
- cpi LF
- brnz lskip
- ret
-
- ;
- ; Print ZCPR3 Return Prompt
- ;
- prmptc:
- call eprint
- db ', ^C=Z3',0
- ret
- ;
- ; Print First/Last Menu Chars
- ;
- prmptf:
- call eprint
- db ', ',RFM,'=1st Menu, ',RLM,'=Prev Menu',0
- ret
- ;
- ; Print next menu message
- ;
- prmptn:
- call eprint
- db ', ',RNM,'=Next Menu',0
- ret
-
- ;
- ; Menu Structure Error -- FATAL
- ; This message is printed to indicate an error in the structure of
- ; the MENU.MNU file.
- ;
- mstrerr:
- call eprint
- db CR,LF,' Structure Error',0
- jmp shpop
-
- ;
- ; Expand Line Pted to by HL into Scratch Area
- ; Return with HL pting to next line, DE pting to current line
- ;
- expand:
- xchg
- lhld expline ;pt to buffer
- xchg
- exp1:
- mov a,m ;get next char
- ani 7fh ;mask MSB
- stax d ;store char
- cpi CR ;end of line?
- jz expx
- inx h ;pt to next
- inx d
- cpi VARFLAG ;variable follows?
- brnz exp1
- ;
- ; Variable Identified - Process it
- ;
- mov a,m ;get next char
- inx h ;pt to next
- cpi VARFLAG ;one variable char?
- brz exp1 ;resume if double VARFLAG
- dcx d ;pt to variable position
- call caps ;capitalize variable
- cpi 'D' ;current disk?
- brz expdisk
- cpi 'U' ;current user?
- brz expuser
- cpi 'F' ;filename.typ?
- brz expfile
- cpi 'N' ;filename?
- brz expname
- cpi 'T' ;filetype?
- brz exptype
- br exp1 ;resume expansion
- ;
- ; Expand Exit
- ;
- expx:
- inx h ;pt to line feed
- mov a,m ;get it
- cpi LF ;line feed?
- brnz expx1
- inx h ;pt to char after line feed
- expx1:
- xchg ;DE pts to next line
- lhld expline ;pt to expanded line
- xchg ;HL pts to next line, DE pts to expanded line
- ret
-
- ;
- ; Expand Disk
- ;
- expdisk:
- call retud ;get disk in B
- mov a,b ;get disk number (A=0)
- adi 'A' ;convert to ASCII
- stax d ;store letter
- inx d ;pt to next
- br exp1 ;resume expansion
- ;
- ; Expand User
- ;
- expuser:
- call retud ;get user in C
- mov a,c ;get user number
- mvi b,10 ;subtract 10's
- mvi c,'0' ;set char
- expu1:
- sub b ;-10
- brc expu2
- inr c ;increment digit
- br expu1
- expu2:
- add b ;+10
- adi '0' ;convert 1's to ASCII
- mov b,a ;B=1's
- mov a,c ;get 10's
- stax d ;store 10's
- inx d
- mov a,b ;get 1's
- stax d ;store 1's
- inx d ;pt to next
- br exp1 ;resume
- ;
- ; Expand File
- ;
- expfile:
- call getfnum ;get file number
- jz exp1 ;resume if error
- push h ;save ptr to next char
- call ptfn ;set ptr to file name
- call putn ;put file name
- mvi a,'.'
- stax d ;store dot
- inx d ;pt to next
- call putt ;put file type
- pop h ;restore ptr
- jmp exp1 ;resume
- ;
- ; Expand Name
- ;
- expname:
- call getfnum ;get file number
- jz exp1 ;resume if error
- push h ;save ptr to next char
- call ptfn ;set ptr to file name
- call putn ;put file name
- pop h ;restore ptr
- jmp exp1 ;resume
- ;
- ; Expand Type
- ;
- exptype:
- call getfnum ;get file number
- jz exp1 ;resume if error
- push h ;save ptr to next char
- call ptfn ;set ptr to file name
- mvi a,8 ;add 8
- add l
- mov l,a
- mov a,h
- aci 0
- mov h,a
- call putt ;put file type
- pop h
- jmp exp1 ;resume
- ;
- ; Pt to File Name whose Number (1-4) is in A
- ;
- ptfn:
- mov b,a ;get number in B
- call getfn2 ;pt to file name 2
- push d ;save DE
- mov a,b ;file 0?
- ora a
- brz ptfnx
- lxi d,11 ;size of file name and type
- ptfn1:
- dad d ;pt to next
- bjnz ptfn1
- ptfnx:
- pop d ;restore DE
- ret
- ;
- ; Put File Name pted to by HL
- ;
- putn:
- mvi b,8 ;8 chars
- br putc
- ;
- ; Put File Type pted to by HL
- ;
- putt:
- mvi b,3 ;3 chars
- ;
- ; Copy Chars from HL to DE for up to B bytes -- flush if space
- ;
- putc:
- mov a,m ;get next char
- cpi ' ' ;skip spaces
- brz putc1
- stax d ;put next char
- inx d ;pt to next
- putc1:
- inx h ;pt to next
- bjnz putc
- ret
-
- ;
- ; Get File Number (1 to 4)
- ; If valid number, return with value in A and HL pting to next char
- ; If not valid, return with Z and HL pting to last char (F, N, T)
- ;
- getfnum:
- mov a,m ;get char
- sui '1' ;convert
- brc getfne ;error
- cpi 4 ;range?
- brnc getfne
- inx h ;pt to next char
- ret ;NZ from CPI 4
- getfne:
- dcx h ;error return
- xra a
- ret
-
- ;
- ; Return Number of Lines on CRT in A
- ;
- getnlines:
- push h ;save HL
- call getcrt ;get CRT info
- inx h ;pt to number of lines
- mov a,m ;get count
- pop h ;restore HL
- dcr a ;subtract 1 for footer
- ret
-
- ;
- ; Convert char string pted to by HL into decimal number in A
- ; On Entry, HL pts to first digit char
- ; On Exit, HL pts to after last digit char and A=number
- ;
- eval:
- push b ;save BC
- mvi b,0 ;set value
- eval1:
- mov a,m ;get digit
- sui '0' ;convert to binary
- brc eval2
- cpi 10 ;range?
- brnc eval2
- inx h ;pt to next digit
- mov c,a ;new digit in C
- mov a,b ;multiply B by 10
- add a ;*2
- add a ;*4
- add b ;*5
- add a ;*10
- add c ;add in new digit
- mov b,a ;result in B
- br eval1
- eval2:
- mov a,b ;result in A
- pop b ;restore ptr
- ret
-
- ;
- ; These buffers overlay the scratch area to save space
- ;
- optstrt equ scratch ;Address of First Option in Current Menu
- mstart equ optstrt+2 ;Address of First Menu
- cstart equ mstart+2 ;Address of Current Menu
- smenfl equ cstart+2 ;System Menu Available Flag (0=No)
- smeno equ smenfl+1 ;System Menu Number
- smenadr equ smeno+1 ;Address of First Byte of System Menu
- nmenfl equ smenadr+2 ;Next Menu Available Flag (0=No)
- menuno equ nmenfl+1 ;Number of Menu
- pagcnt equ menuno+1 ;Paging Counter
- cflag equ pagcnt+1 ;Display Command Line Flag
- dflag equ cflag+1 ;Display Menu Flag
- pflag equ dflag+1 ;Paging Flag
-
- ;
- ; Buffers
- ;
- ibuff:
- ds 2 ;input line buffer
- expline:
- ds 2 ;scratch area to expand lines in
- cpflag:
- ds 1 ;Temp Display Command Line Flag
- dpflag:
- ds 1 ;Temp Display Menu Flag
- ppflag:
- ds 1 ;Temp Paging Flag
- cpmok:
- ds 1 ;OK to Return to ZCPR3 (0=No)
- tnum:
- ds 41 ;space for chars and ending 0
- shdisk:
- db 'A' ;disk to return to
- db '00' ;user to return to
- db ':;' ;log in and next command
- shname:
- db 'MENU ' ;program name (filled in at installation)
- shfile:
- ds 13 ;file name (12) and ending 0
-
- end