home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Oakland CPM Archive
/
oakcpm.iso
/
sigm
/
vol131
/
clock.src
< prev
next >
Wrap
Text File
|
1984-04-29
|
10KB
|
390 lines
NAME CLOCK
ENTRY CLOCK
CLKBAS EQU 50H = CLOCK PORT BASE ADDRESS
CLKCMD EQU CLKBAS+10 = " COMMAND PORT ADDRESS
CLKDTA EQU CLKBAS+11 = " DATA " "
BIOS EQU 5
TO_CPM EQU 0
NO_OP EQU 00H
RDFREE EQU 10H
WRFREE EQU 20H
HOLD EQU 40H
RDHELD EQU 50H
WRHELD EQU 60H
SECS01 EQU 00H
SECS10 EQU 01H
MINS01 EQU 02H
MINS10 EQU 03H
HRS01 EQU 04H
HRS10 EQU 05H
AM_PM EQU 05H
WKDAY EQU 06H
DAYS01 EQU 07H
DAYS10 EQU 08H
LEAPYR EQU 08H
MTHS01 EQU 09H
MTHS10 EQU 0AH
YRS01 EQU 0BH
YRS10 EQU 0CH
ROW EQU 01
COLM EQU 55
**********************
* *
* MACROS *
* *
**********************
TYPE: MACRO MSG
LXI D,MSG
CALL TYPIST
ENDMAC
PRNT1: MACRO
MOV A,M
CALL RDDGT
ADI 30H
CALL PRNTCHAR
ENDMAC
*****************************
* *
* MAIN LOOP *
* *
*****************************
CLOCK: LXI SP,STACK SETUP LOCAL STACK
CLKBGN: CALL CLRHOM
CALL BEEP
CLKRPT: TYPE SIGNON
CALL RESPONSE
CPI 'X'
JZ TO_CPM
CPI 'S'
JZ SETTIME
CPI 'P'
JZ PRNTTIME
CPI 'C'
JZ FOREVER
TYPE BOOBOO
JMP CLKBGN
******************************
* *
* SUBROUTINES *
* *
******************************
* CLEAR THE SCREEN AND HOME THE CURSOR :
clrhom: TYPE CLEAR
RET
clear: db 1Ah,1Eh,24h ;1A=ASCII for clear screen
;1E " " home cursor
;24 " " end/TEXT
*********************
* RING CURSOR BELL :
BEEP: TYPE DING
RET
ding: DB 07h,24h ;07=ASCII for bell,24=end/TEXT
*********************
* MASTER ROUTINE FOR GETTING TIME AND DATE INPUT FROM USER.
* POINTS HL AND DE TO BUFFER AND COMMAND TABLE RESPECTIVELY.
* BUFFER IS FILLED AND THEN DIGITS WRITTEN FROM BUFFER TO CLOCK.
SETTIME: CALL GETTIME FILL THE TIME/DATE DIGIT BUFFER
LXI H,DTABLE POINT HL TO BUFFER
LXI D,ATABLE POINT DE TO COMMAND TABLE
MVI B,14 SETUP B AS COUNTER
MVI A,HOLD STOP THE CLOCK
OUT CLKCMD
SET1: DCR B
JZ SET2 IF ALL DONE THEN ------.
MOV A,M ELSE:GET DIGIT > A |
MOV C,A & MOVE IT > C, |
LDAX D GET COMMAND > A & |
CALL WRTDGT WRITE DIGIT > CLOCK. |
INX H BUMP |
INX D POINTERS |
JMP SET1 & LOOP. |
SET2: MVI A,NO_OP CLEAR CMND PORT, <----'
OUT CLKCMD
CALL CLKPRNT
JMP CLKBGN & EXIT SUBROUTINE.
****************
* NEXT S/R GETS DIGITS FROM CONSOLE INTO THE
* BUFFER POINTED TO BY HL.
GETTIME: TYPE ASKTIME
LXI H,DTABLE
GET1: CALL GETNUMB
CPI 0DH
JZ GETDATE
ANI 0FH
MOV M,A
INX H
JMP GET1
GETDATE: TYPE ASKDATE
GET2: CALL GETNUMB
CPI 0DH
JZ GETDAY
ANI 0FH
MOV M,A
INX H
JMP GET2
GETDAY: TYPE ASKDAY
GET3: CALL GETNUMB
CPI 0DH
RZ
ANI 0FH
MOV M,A
INX H
JMP GET3
******************
* NEXT S/R GETS A CHARACTER FROM CONSOLE :
* :RETURNS ONLY 'LEGAL' CHARACTERS
* :(i.e. A C/R OR A NUMERAL)
GETNUMB: CALL RESPONSE
CPI 0DH
RZ
CPI '0'
JC GETNUMB
CPI '9'+1
JNC GETNUMB
RET
******************
* WRITE A DIGIT TO THE CLOCK :
* SET THE 24hr & LEAPYEAR BITS :
* ON CALL DIGIT COMMAND IS IN A :
* " " " IS IN C :
WRTDGT: PUSH PSW SAVE THE COMMAND
ADI HOLD ADD HOLD COMMAND
OUT CLKCMD INSTRUCT CLOCK
CPI AM_PM+HOLD 24 HR BYTE ?
JNZ WRT1
MOV A,C IF SO :
ADI 08H SET 24 HR BIT.
JMP WRT3
WRT1: CPI LEAPYR+HOLD LEAP YEAR BYTE ?
JNZ WRT2
MOV A,C IF SO :
ANI 03H SET LEAPYEAR BIT.
JMP WRT3
WRT2: MOV A,C DIGIT > A
WRT3: OUT CLKDTA DIGIT > CLOCK
POP PSW COMMAND > A
ADI WRHELD ADD WRITE & HOLD COMMANDS
OUT CLKCMD
SUI WRFREE REMOVE 'WRITE' FROM COMMAND
OUT CLKCMD SEND LAST COMMAND OF SEQUENCE
RET
*************************
* THE NEXT S/R READS A DIGIT FROM THE CLOCK :
* :THE LEAPYEAR AND 24hr MODE BITS ARE MASKED.
* :ON CALL THE DIGIT COMMAND MUST BE IN A.
* :ON RETURN THE DIGIT VALUE IS IN A.
RDDGT: ADI RDFREE ADD 'READ' TO COMMAND.
OUT CLKCMD
CPI RDFREE+AM_PM WILL IT CONTAIN 24hr BIT?
IN CLKDTA GET DIGIT
RNZ
SUI 8 KILL 24hr BIT
RET
***************************
* MOVE CURSOR TO PREDEFINED ROW/COLUMN LOCATION
CRSR: PUSH H ;
PUSH D
PUSH B
MVI E,1BH ;ESC
MVI C,2
CALL 5
MVI E,3DH ;=
MVI C,2
CALL 5
MVI E,ROW+31 ;ROW OUT
MVI C,2
CALL 5
MVI E,COLM+31;COLUMN OUT
MVI C,2
CALL 5
POP B
POP D
POP H
RET
*************************
* NEXT S/R PRINTS THE CURRENT TIME AND DATE ONCE,COMPLETE
* WITH COLONS AND SLASHES,THEN RETURNS.
CLKPRNT: CALL CRSR
LXI H,ATABLE POINT HL TO TABLE OF COMMANDS
CALL PRINT2 PRINT 1ST 2 DIGITS
MVI A,':'
CALL PRNTCHAR
CALL PRINT2 PRINT NEXT 2 DIGITS
MVI A,':'
CALL PRNTCHAR
CALL PRINT2 & NEXT 2
MVI A,' '
CALL PRNTCHAR
MVI A,' ' & 2 SPACES
CALL PRNTCHAR
CALL PRINT2 & 2 MORE DIGITS
MVI A,'/'
CALL PRNTCHAR
CALL PRINT2 & 2 MORE
MVI A,'/'
CALL PRNTCHAR
CALL PRINT2 & LAST 2
RET
**********************
PRINT2: PRNT1
INX H
PRNT1
INX H
RET
***********************
PRNTTIME: CALL CLRHOM
CALL CLKPRNT
JMP CLKRPT
************************
* NEXT S/R PRINTS THE TIME, UPDATES IT ONCE EVERY SECOND,
* AND CONTINUES DOING SO UNTIL A ^C IS TYPED.
FOREVER: CALL CLRHOM
MVI A,0AH
CALL PRNTCHAR
FOR1: MVI A,0DH
CALL PRNTCHAR
CALL CLKPRNT
MVI A,SECS01
CALL RDDGT
MOV B,A
FOR2: MVI A,SECS01
CALL RDDGT
CMP B
JZ FOR2
JMP FOR1
***********************
RESPONSE: PUSH H
MVI C,01 BIOS CHAR/IN
CALL BIOS
POP H
CPI 'a' RANGE CHECK UPPER CASE
JC SKIP
ANI 5FH CONVERT TO UPPER CASE
SKIP: ANI 7FH STRIP OFF PARITY
CPI 03H CHECK FOR ^C
JZ TO_CPM
RET
************************
* NEXT S/R PRINTS A CHARACTER ON THE SCREEN :
* (ALSO WATCHES FOR ^C INPUT FROM CONSOLE).
PRNTCHAR: PUSH D -.
MOV E,A |
MVI C,2 | = PRINT CHARACTER
PUSH H |
CALL BIOS _|
MVI C,0BH -.
* | = CHECK CONSOLE
CALL BIOS _|
POP H
POP D
ORA A -. IF A KEY WAS STRUCK
CNZ RESPONSE | THEN GET CHARACTER
* | & CHECK FOR ^C.
* _|
RET
**********************
TYPIST: PUSH H
MVI C,09H
CALL BIOS
POP H
RET
************************
* *
* MESSAGES,etc. *
* *
************************
SIGNON: DB 0DH,0AH,' CALENDER-CLOCK MASTER PROGRAM'
DB 0DH,0AH,0DH,0AH
DB 'TO SELECT A FUNCTION PLEASE HIT CORRESPONDING COMMAND KEY'
DB 0DH,0AH,0DH,0AH
DB ' FUNCTION COMMAND KEY',0DH,0AH
DB ' SET THE TIME , DATE & WEEKDAY = S',0DH,0AH
DB ' PRINT THE TIME & DATE (ONCE) = P',0DH,0AH
DB ' PRINT THE TIME & DATE CONTINUOUSLY = C',0DH,0AH
DB ' EXIT TO OPERATING SYSTEM = X',0DH,0AH
DB 0DH,0AH,'COMMAND = ?',08H,'$'
BOOBOO: DB 0DH,0AH,'SORRY,I DID NOT RECOGNIZE THAT COMMAND.'
DB 0DH,0AH,'PLEASE TRY AGAIN.$'
ASKTIME: DB 0DH,0AH,'WHAT IS THE TIME (24hr FORMAT - HH:MM:SS)?'
DB 0DH,0AH,'$'
ASKDATE: DB 0DH,0AH,'WHAT IS THE DATE (MM/DD/YY)?',0DH,0AH,'$'
ASKDAY: DB 0DH,0AH,'WHAT IS THE WEEKDAY (SUNDAY = 0) ?',0DH,0AH,'$'
* DIGIT ADDRESS TABLE :
ATABLE: DB HRS10,HRS01,MINS10,MINS01,SECS10,SECS01,MTHS10,MTHS01
DB DAYS10,DAYS01,YRS10,YRS01,WKDAY
* DIGIT INPUT BUFFER :
DTABLE: DS 13
* LOCAL STACK AREA :
DS 32 16 LEVEL STACK
STACK: * N.B.: STACKS GROW INTO LOW MEMORY!
*********************
END CLOCK