$ROM(LARGE) $DEBUG NOSYMBOLS NOPAGING /*THIS PLM/51 PROGRAM CONTROLS THE DIGITAL VOICE PROGRAMMER. IT IS TARGETED FOR AN 8751 RUNNING AT 10.00 MHZ. VERSION 1.1 23 OCT 1986 BY BILL HEIDEMAN THESE ARE THE COMMANDS FOR THE CRT DISPLAY; DISPLAY ------- DB DBXXYYYY BEGINNING DE DEXXYYYY END DR DR RECORD NEXT DP DP PRESENT PLAY DC DC CONTINUE PLAY DT DT TRIM VALUE DS DS VOICE SPEED DA DA ALL BOUNDARIES DZB DZB PROG BEGIN ADDR DZE DZE PROG END ADDR DZO DZO PROM OFFSET SET --- SB SBXXYYYY BEGINING SE SEXXYYYY END SR SRXX RECORD NEXT SP SPXX PRESENT PLAY SC SCXX CONTINUE PLAY ST STXX TRIM VALUE SS SSXX SPEED VALUE SZB SZBYYYY PROG BEGIN ADDR SZE SZEYYYY PROG END ADDR SZO SZOYYYY PROM OFFSET */ VOICE_REC: DO; $NOLIST $INCLUDE(REG51.DCL) $LIST DECLARE LIT LITERALLY 'LITERALLY'; DECLARE DCL LIT 'DECLARE'; DCL FOREVER LIT 'WHILE 1'; DCL AUX LIT 'AUXILIARY'; DCL MEM_PTR WORD MAIN; DCL MEMDATA BASED MEM_PTR BYTE AUX; DCL (VOCH,VOCM,VOCL,STATUS) BYTE MAIN; DCL (SWT_RD,SWT_VAL,SWT_LST) BYTE MAIN; DCL (ENTRY,J,DPL_SAVE,DPH_SAVE) BYTE MAIN; DCL (LOW_ADDR,MID_ADDR,HIGH_ADDR) BYTE; DCL (READ_PNTR,WRITE_PNTR) WORD; DCL (SWT_EDGE,LOOP,PLAY_INC,NO_CR) BIT; DCL MESS_START (50) WORD AT (0E000H) AUX; DCL MESS_STOP (50) WORD AT (0E200H) AUX; DCL ERR_ADDR WORD AT (0E1D8H) AUX; DCL ERR_DATM BYTE AT (0E1DAH) AUX; DCL ERR_DATD BYTE AT (0E1DBH) AUX; DCL PRG_BGN WORD AT (0E1DCH) AUX; DCL PRG_END WORD AT (0E1DEH) AUX; DCL PRG_OFF WORD AT (0E1E0H) AUX; DCL PLAY_CNT BYTE AT (0E3D8H) AUX; DCL REC_CNT BYTE AT (0E3D9H) AUX; DCL TRIM_CNT BYTE AT (0E3DAH) AUX; DCL SPEED BYTE AT (0E3DBH) AUX; DCL INT BYTE AT (0E3DCH) AUX; DCL DATABUS BYTE AT (8000H) AUX; DCL ADDRL BYTE AT (0A000H) AUX; DCL ADDRH BYTE AT (0C000H) AUX; DCL SWT_PORT BYTE AT (0A000H) AUX; DCL VOCCE LIT '0BCH'; DCL VOCWR LIT '0B4H'; DCL VOCRD LIT '0F8H'; DCL VOCDIS LIT '0FEH'; DCL BUSY LIT '80H'; DCL EOS LIT '40H'; DCL ERR LIT '20H'; DCL OVR LIT '10H'; DCL VOICE LIT '1'; DCL PLAY LIT '2'; DCL PROGM LIT '2'; DCL REDUCE LIT '4'; DCL VOC_SPD LIT '60H'; DCL FIX_UP LIT '2'; DCL CR LIT '0DH',LF LIT '0AH',EOF LIT '00H'; DCL ESC LIT '1BH'; DCL CAN_PNTR WORD; DCL CAN_OUT BASED CAN_PNTR BYTE CONSTANT; DCL OUT_BASE BYTE AT (0E1E0H) AUX; DCL OUT_PNTR WORD; DCL MES_OUT BASED OUT_PNTR BYTE AUX; DCL IN_BASE BYTE AT (0E3E0H) AUX; DCL IN_PNTR WORD; DCL MES_IN BASED IN_PNTR BYTE AUX; DCL SIGN_ON (*) BYTE CONSTANT (ESC,'G','VOICE', ' RECORDING DEVELOPMENT SYSTEM',CR,LF,LF, 'COPYRIGHT 1986 MICRO-NETICS',CR,LF,LF,LF,LF,EOF); DCL DONE_MSG (*) BYTE CONSTANT (' DONE.',CR,LF,EOF); DCL ENTRY_ERROR (*) BYTE CONSTANT ('ENTRY ERROR', CR,LF,EOF); DCL PROMPT (*) BYTE CONSTANT (CR,LF,'*',EOF); DCL LINE_FEED (*) BYTE CONSTANT (LF,EOF); DCL DELETE_C (*) BYTE CONSTANT (8,' ',8,EOF); DCL TAB (*) BYTE CONSTANT (' ',EOF); DCL ERR_AT (*) BYTE CONSTANT ('ERROR ADDRESS',EOF); DCL ERR_DAT (*) BYTE CONSTANT ('DEVICE DATA',EOF); DCL ERR_WAS (*) BYTE CONSTANT ('SHOULD BE',CR,LF,EOF); /**************************************** * * * THESE ARE THE EXTERNAL PROCEDURES. * * * ****************************************/ CAS: PROCEDURE EXTERNAL; END CAS; SET_UP: PROCEDURE EXTERNAL; END SET_UP; /**************************************** * * * THIS IS THE REAL TIME CLOCK. * * * ****************************************/ TIMER_ZERO: PROCEDURE INTERRUPT 1 USING 1; TH0=0BEH; /* SET TO 20 MSEC */ TL0=0E6H; SWT_RD=SWT_PORT; IF SWT_RD=SWT_LST THEN DO; IF ((SWT_LST XOR SWT_VAL) AND (NOT(SWT_LST)) AND 18H) <>0 THEN SWT_EDGE=1; SWT_VAL=SWT_LST; END; ELSE SWT_LST=SWT_RD; END TIMER_ZERO; /**************************************** * * * THIS IS THE ROUTINE FOR INTR 1. * * RECORDING STOP. * * * ****************************************/ REC_STOP: PROCEDURE INTERRUPT 2 USING 2; EX1=0; /* DISABLE FURTHER INTS */ DPL_SAVE=DPL; DPH_SAVE=DPH; MESS_STOP(REC_CNT)=DPH_SAVE; MESS_STOP(REC_CNT)=(256 * MESS_STOP(REC_CNT)) + DPL_SAVE; LOOP=0; /* CLEAR LOAD WAIT */ EX0=0; /* STOP CAS PULSES */ SWT_VAL=SWT_VAL OR 8; /* SET STOP */ SWT_EDGE=1; END REC_STOP; /************************************ * * * THESE ROUTINES ARE FOR VOICE * * BOARD COMMUNICATIONS. * * * ************************************/ BSY_CK: PROCEDURE; P1=VOCRD; P1=VOCRD; P1=VOCRD; DO WHILE (DATABUS AND BUSY)<>0; P1=0FCH; CALL TIME(1); P1=VOCRD; P1=VOCRD; P1=VOCRD; END; P1=0FCH; CALL TIME(1); END BSY_CK; WR_PULSE: PROCEDURE; P1=VOCCE; P1=VOCWR; P1=VOCWR; P1=VOCWR; P1=VOCCE; CALL TIME(1); CALL BSY_CK; END WR_PULSE; COM_SND: PROCEDURE(SELECT); DCL SELECT BYTE; DCL VALUES (4) BYTE CONSTANT(0,10H,20H,80H); DATABUS=VALUES(SELECT); CALL WR_PULSE; END COM_SND; ADDR_SND: PROCEDURE(SELECT,ADH,ADM,ADL); DCL (SELECT,ADH,ADM,ADL) BYTE; IF SELECT=4 THEN DATABUS=(ADH OR 30H); ELSE DATABUS=(ADH OR 40H); CALL WR_PULSE; DATABUS=ADM; CALL WR_PULSE; DATABUS=ADL; CALL WR_PULSE; END ADDR_SND; CNTRL_SND: PROCEDURE(RATE); DCL RATE BYTE; DATABUS=(RATE OR 50H); CALL WR_PULSE; END CNTRL_SND; LABL_SND: PROCEDURE; END LABL_SND; ADDR_RD: PROCEDURE; CALL BSY_CK; DATABUS=70H; /* SET UP ADD READ */ P1=VOCCE; P1=VOCWR; P1=VOCWR; P1=VOCWR; P1=VOCCE; CALL TIME(1); P1=VOCRD; P1=VOCRD; P1=VOCRD; VOCH=DATABUS; P1=0FCH; CALL TIME(1); P1=VOCRD; P1=VOCRD; P1=VOCRD; VOCM=DATABUS; P1=0FCH; CALL TIME(1); P1=VOCRD; P1=VOCRD; P1=VOCRD; VOCL=DATABUS; CALL TIME(1); CALL BSY_CK; CALL TIME(1); END ADDR_RD; STAT_RD: PROCEDURE; P1=VOCRD; P1=VOCRD; P1=VOCRD; STATUS=DATABUS; P1=0FCH; CALL TIME(1); END STAT_RD; COMMAND: PROCEDURE(COM_NUM,AH,AM,AL,SPD); DCL (COM_NUM,AH,AM,AL,SPD) BYTE; IF COM_NUM<10 THEN DO CASE COM_NUM; CALL COM_SND(0); /* NOP */ CALL COM_SND(1); /* START */ CALL COM_SND(2); /* STOP */ CALL COM_SND(3); /* REC */ CALL ADDR_SND(4,AH,AM,AL); /* START ADDR */ CALL ADDR_SND(5,AH,AM,AL); /* STOP ADDR */ CALL CNTRL_SND(SPD); /* CNTROL */ CALL LABL_SND; /* LABEL */ CALL ADDR_RD; /* ADDR REQ */ CALL STAT_RD; /* STATUS REQ */ END; END COMMAND; /******************************** * * * THESE ROUTINES ARE FOR * * DATA CAPTURE. * * * ********************************/ EXP_ADDR: PROCEDURE(PNTR); DCL PNTR WORD; LOW_ADDR=LOW(SHL(PNTR,3)); MID_ADDR=HIGH(SHL(PNTR,3)); HIGH_ADDR=HIGH(SHR(PNTR,5)); END EXP_ADDR; LOAD_WAIT: PROCEDURE(STRT); DCL STRT WORD; EA=0; LOOP=1; EX0=1; EX1=1; ET0=0; DPL=LOW(STRT); DPH=HIGH(STRT); CALL SET_UP; EA=1; DO WHILE LOOP<>0; /* WAIT FOR INTR */ END; ET0=1; END LOAD_WAIT; MEM_SHIFT: PROCEDURE(MESSG,CNT); DCL CNT WORD; DCL (I,MESSG) BYTE; DO I=MESSG TO REC_CNT; MESS_START(I)=MESS_START(I)-CNT; MESS_STOP(I)=MESS_STOP(I)-CNT; END; WRITE_PNTR=MESS_START(MESSG); READ_PNTR=MESS_START(MESSG)+CNT; DO WHILE READ_PNTREOF; TI=0; N=CAN_OUT; IF N<>EOF THEN DO; SBUF=N; DO WHILE TI=0; END; CAN_PNTR=CAN_PNTR+1; END; END; END SND_CAN; SND_MSG: PROCEDURE; DCL N BYTE; OUT_PNTR=.OUT_BASE; N=0FFH; DO WHILE N<>EOF; TI=0; N=MES_OUT; IF N<>EOF THEN DO; SBUF=N; DO WHILE TI=0; END; OUT_PNTR=OUT_PNTR+1; END; END; IF NO_CR=0 THEN DO; TI=0; SBUF=CR; DO WHILE TI=0; END; TI=0; SBUF=LF; DO WHILE T1=0; END; END; END SND_MSG; IN_MSG: PROCEDURE; DCL N BYTE; N=0; IN_PNTR=.IN_BASE; DO WHILE N<>CR; DO WHILE RI=0; END; RI=0; N=SBUF AND 7FH; IF N=7FH THEN DO; IN_PNTR=IN_PNTR-1; CALL SND_CAN(.DELETE_C); END; ELSE DO; MES_IN=N; IN_PNTR=IN_PNTR+1; TI=0; SBUF=N; DO WHILE TI=0; END; END; END; END IN_MSG; BIN_CONV: PROCEDURE(STRT,LEN) WORD; DCL (STRT,LEN,I,VAL) BYTE; DCL BIN_RET WORD; IN_PNTR=((.IN_BASE)+(STRT+LEN-1)); BIN_RET=0; VAL=0; DO I=0 TO LEN; IF MES_IN>40H THEN BIN_RET=BIN_RET OR SHL(( DOUBLE(MES_IN-37H)),VAL); ELSE BIN_RET=BIN_RET OR SHL(( DOUBLE(MES_IN-30H)),VAL); VAL=VAL+4; IN_PNTR=IN_PNTR-1; END; RETURN BIN_RET; END BIN_CONV; DIS_ASCII: PROCEDURE(AD_PNTR,LEN); DCL (LEN,I) BYTE; DCL AD_PNTR WORD; DCL VAL BASED AD_PNTR BYTE AUX; OUT_PNTR=.OUT_BASE; DO I=0 TO LEN-1; IF (VAL AND 0F0H)<0A0H THEN MES_OUT=SHR((VAL AND 0F0H),4) + 30H; ELSE MES_OUT=SHR((VAL AND 0F0H),4) + 37H; OUT_PNTR=OUT_PNTR+1; IF (VAL AND 0FH)<10 THEN MES_OUT=(VAL AND 0FH) + 30H; ELSE MES_OUT=(VAL AND 0FH) + 37H; OUT_PNTR=OUT_PNTR+1; AD_PNTR=AD_PNTR+1; END; MES_OUT=EOF; END DIS_ASCII; COM_SET: PROCEDURE; IN_PNTR=.IN_BASE+1; IF MES_IN='B' THEN MESS_START(LOW(BIN_CONV( 2,2)))=(BIN_CONV(4,4)); ELSE IF MES_IN='E' THEN MESS_STOP(LOW(BIN_CONV( 2,2)))=(BIN_CONV(4,4)); ELSE IF MES_IN='R' THEN REC_CNT=LOW(BIN_CONV(2,2)); ELSE IF MES_IN='P' THEN PLAY_CNT=LOW(BIN_CONV(2,2)); ELSE IF MES_IN='T' THEN TRIM_CNT=LOW(BIN_CONV(2,2)); ELSE IF MES_IN='S' THEN DO; SPEED=LOW(BIN_CONV(2,2)); CALL COMMAND(6,0,0,0,SPEED); END; ELSE IF MES_IN='C' THEN DO; IF LOW(BIN_CONV(2,2))<>0 THEN PLAY_INC=1; ELSE PLAY_INC=0; END; ELSE IF MES_IN='Z' THEN DO; IN_PNTR=.IN_BASE+2; IF MES_IN='B' THEN PRG_BGN=BIN_CONV(3,4); ELSE IF MES_IN='E' THEN PRG_END=BIN_CONV(3,4); ELSE IF MES_IN='O' THEN PRG_OFF=BIN_CONV(3,4); ELSE DO; CALL SND_CAN(.ENTRY_ERROR); END; ELSE CALL SND_CAN(.ENTRY_ERROR); END COM_SET; COM_DISP: PROCEDURE; IN_PNTR=.IN_BASE+1; IF MES_IN='B' THEN DO; CALL DIS_ASCII(.MESS_START (LOW(BIN_CONV(2,2))),2); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='E' THEN DO; CALL DIS_ASCII(.MESS_STOP (LOW(BIN_CONV(2,2))),2); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='R' THEN DO; CALL DIS_ASCII(.REC_CNT,1); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='P' THEN DO; CALL DIS_ASCII(.PLAY_CNT,1); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='T' THEN DO; CALL DIS_ASCII(.TRIM_CNT,1); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='S' THEN DO; CALL DIS_ASCII(.SPEED,1); OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='C' THEN DO; OUT_PNTR=.OUT_BASE; IF PLAY_INC<>0 THEN MES_OUT=31H; ELSE MES_OUT=30H; OUT_PNTR=OUT_PNTR+1; MES_OUT=EOF; OUT_PNTR=.OUT_BASE; CALL SND_MSG; END; ELSE IF MES_IN='A' THEN DO; DO INT=0 TO REC_CNT; CALL DIS_ASCII(.INT,1); NO_CR=1; CALL SND_MSG; CALL SND_CAN(.TAB); CALL DIS_ASCII(.MESS_START (INT),2); CALL SND_MSG; CALL SND_CAN(.TAB); CALL EXP_ADDR(MESS_START(INT)); CALL DIS_ASCII(.HIGH_ADDR,1); CALL DIS_ASCII(.MID_ADDR,1); CALL DIS_ASCII(.LOW_ADDR,1); CALL SND_MSG; CALL SND_CAN(.TAB); CALL DIS_ASCII(.MESS_STOP (INT),2); CALL SND_MSG; CALL SND_CAN(.TAB); NO_CR=0; CALL EXP_ADDR(MESS_STOP(INT)); CALL DIS_ASCII(.HIGH_ADDR,1); CALL DIS_ASCII(.MID_ADDR,1); CALL DIS_ASCII(.LOW_ADDR,1); CALL SND_MSG; TI=0; SBUF=LF; DO WHILE TI=0; END; END; END; ELSE IF MES_IN='Z' THEN DO; IN_PNTR=.IN_BASE+2; IF MES_IN='B' THEN DO; CALL DIS_ASCII(.PRG_BGN,2); CALL SND_MSG; END; ELSE IF MES_IN='E' THEN DO; CALL DIS_ASCII(.PRG_END,2); CALL SND_MSG; END; ELSE IF MES_IN='O' THEN DO; CALL DIS_ASCII(.PRG_OFF,2); CALL SND_MSG; END; ELSE CALL SND_CAN(.ENTRY_ERROR); END; ELSE CALL SND_CAN(.ENTRY_ERROR); END COM_DISP; /**************************************** * * * THESES ROUTINES ARE FOR PROM * * PROGRAMMING. * * * ****************************************/ DIS_ERROR: PROCEDURE; CALL SND_CAN(.TAB); CALL SND_CAN(.ERR_AT); CALL SND_CAN(.TAB); CALL SND_CAN(.ERR_DAT); CALL SND_CAN(.TAB); CALL SND_CAN(.ERR_WAS); NO_CR=1; CALL SND_CAN(.TAB); CALL SND_CAN(.TAB); CALL DIS_ASCII(.ERR_ADDR,2); CALL SND_CAN(.TAB); CALL SND_CAN(.TAB); CALL DIS_ASCII(.ERR_DATM,1); NO_CR=0; CALL SND_CAN(.TAB); CALL SND_CAN(.TAB); CALL DIS_ASCII(.ERR_DATD,1); CALL SND_MSG; END DIS_ERROR; TRANS: PROCEDURE; DCL CNTR WORD; P1=7EH; CALL TIME(100); DO CNTR=0 TO (PRG_END-PRG_BGN); MEM_PTR=(PRG_BGN+CNTR); ADDRL=LOW(PRG_OFF+CNTR); ADDRH=HIGH(PRG_OFF+CNTR); MEMDATA=DATABUS; END; CALL SND_CAN(.DONE_MSG); END TRANS; PROG: PROCEDURE; DCL CNTR WORD; DCL (X,COMP,REP) BYTE; EA=0; /* DISABLE ALL INTRS */ P1=0CEH; /* TURN ON HV */ CALL TIME(100); DO CNTR=0 TO (PRG_END-PRG_BGN); X=0; /* SET UP ADDR/DATA */ MEM_PTR=(PRG_BGN+CNTR); ADDRL=LOW(PRG_OFF+CNTR); ADDRH=(HIGH(PRG_OFF+CNTR) OR 80H); DATABUS=MEMDATA; P1=8EH; COMP=0FFH; DO WHILE (X<>25) AND (COMP<>0); P1=0EH; CALL TIME(9); /* PULSE CE */ P1=8EH; X=X+1; P1=0CEH; /* DO COMPARE */ ADDRH=HIGH(PRG_OFF+CNTR); IF DATABUS=MEMDATA THEN COMP=0; END; IF COMP=0 THEN DO REP=0 TO (3*X); P1=0EH; CALL TIME(9); END; ELSE DO; ERR_ADDR=(PRG_BGN+CNTR); ERR_DATM=MEMDATA; ERR_DATD=DATABUS; CALL DIS_ERROR; CNTR=(PRG_END-PRG_BGN); END; P1=0CEH; END; P1=0FEH; ADDRH=80H; EA=1; /* ENABLE INTRS */ CALL SND_CAN(.DONE_MSG); END PROG; VERIF: PROCEDURE; DCL CNTR WORD; P1=7EH; CALL TIME(100); DO CNTR=0 TO (PRG_END-PRG_BGN); MEM_PTR=(PRG_BGN+CNTR); ADDRL=LOW(PRG_OFF+CNTR); ADDRH=HIGH(PRG_OFF+CNTR); IF MEMDATA<>DATABUS THEN DO; ERR_ADDR=(PRG_BGN+CNTR); ERR_DATM=MEMDATA; ERR_DATD=DATABUS; CALL DIS_ERROR; CNTR=(PRG_END-PRG_BGN); END; END; CALL SND_CAN(.DONE_MSG); END VERIF; /******************************** * * * THESE ROTUINES ARE HIGH * * LEVEL COMMANDS TO THE * * VOICE BOARD. * * * ********************************/ PLAY_MSG: PROCEDURE; CALL COMMAND(0,0,0,0,0); /* SET PLAY */ CALL EXP_ADDR(MESS_START(PLAY_CNT)); CALL COMMAND(4,HIGH_ADDR,MID_ADDR, LOW_ADDR,0); CALL EXP_ADDR(MESS_STOP(PLAY_CNT)); CALL COMMAND(5,HIGH_ADDR,MID_ADDR, LOW_ADDR,0); CALL COMMAND(1,0,0,0,0); /* SET START */ END PLAY_MSG; /******************************** * * * THIS IS THE MAIN LOOP * * * ********************************/ INIT: DO; P1=0FFH; ADDRL=00; ADDRH=80H; DATABUS=00; SWT_EDGE=0; PX0=1; /* EXTERN INTR */ IT0=1; PX1=1; SCON=50H; /* USART */ TH1=0F5H; /* TIMER */ TL1=0F5H; /* 2400 B */ TMOD=21H; EA=1; TR0=1; TR1=1; ET0=1; CALL COMMAND(0,0,0,0,0); /* RESET ERR */ SPEED=(SHR(SWT_VAL,5) AND 3); CALL COMMAND(6,0,0,0,SPEED); /* SEND SPEED */ CALL COMMAND(4,0,0,0,0); /* SEND START ADDR */ MESS_START(0)=0; PLAY_CNT=0; REC_CNT=0; TRIM_CNT=20H; NO_CR=0; PLAY_INC=0; PRG_BGN=0; PRG_END=7FFFH; PRG_OFF=0; CALL SND_CAN(.SIGN_ON); /* SEND SIGN ON */ CALL SND_CAN(.PROMPT); END INIT; MAIN_LOOP: DO FOREVER; IF RI<>0 THEN DO; CALL IN_MSG; CALL SND_CAN(.LINE_FEED); IN_PNTR=.IN_BASE; IF MES_IN='S' THEN CALL COM_SET; ELSE IF MES_IN='D' THEN CALL COM_DISP; CALL SND_CAN(.PROMPT); END; IF SWT_EDGE<>0 THEN DO; SWT_EDGE=0; IF (SWT_VAL AND VOICE)<>0 THEN DO; IF (SWT_VAL AND REDUCE)<>0 THEN DO; IF (SWT_VAL AND FIX_UP)<>0 THEN DO; CALL MEM_SHIFT(0,MESS_START(0)); DO J=1 TO (REC_CNT-1); CALL MEM_SHIFT(J,(MESS_START(J)- MESS_STOP(J-1))); END; CALL PLAY_MSG; END; ELSE IF (SWT_VAL AND 8)<>0 THEN DO; MESS_STOP(PLAY_CNT)= MESS_STOP(PLAY_CNT)-TRIM_CNT; CALL PLAY_MSG; END; ELSE DO; MESS_START(PLAY_CNT)= MESS_START(PLAY_CNT)+TRIM_CNT; CALL PLAY_MSG; END; END; ELSE IF (SWT_VAL AND 8)<>0 THEN DO; CALL COMMAND(2,0,0,0,0); /* SET STOP */ END; ELSE DO; IF (SWT_VAL AND PLAY)<>0 THEN DO; IF REC_CNT<>0 THEN DO; CALL PLAY_MSG; IF PLAY_INC<>0 THEN DO; IF PLAY_CNT=REC_CNT-1 THEN PLAY_CNT=0; ELSE PLAY_CNT=PLAY_CNT+1; END; END; END; ELSE DO; CALL COMMAND(3,0,0,0,0); /* SET RECORD */ CALL EXP_ADDR(MESS_START(REC_CNT)); CALL COMMAND(4,HIGH_ADDR,MID_ADDR, LOW_ADDR,0); CALL COMMAND(1,0,0,0,0); /* SET START */ CALL LOAD_WAIT(MESS_START(REC_CNT)); REC_CNT=REC_CNT+1; MESS_START(REC_CNT)=MESS_STOP(REC_CNT-1); END; END; END; ELSE DO; /* PROGRAM MODE */ IF (SWT_VAL AND 8)<>0 THEN DO; CALL VERIF; /* DO VERIFY */ END; ELSE DO; IF (SWT_VAL AND PROGM)<>0 THEN DO; CALL PROG; /* DO PROGRAM */ CALL VERIF; /* DO VERIFY */ END; ELSE DO; CALL TRANS; /* DO TRANSFER */ END; END; END; END; END MAIN_LOOP; END VOICE_REC;