;MAIN.ASM ;MC68HC912B32 MAIN ROUTINE ;REGS.INC CONTAINS ALL REGISTERS ; ;REGS.INC and AUDIO.ASM ARE EXTERNAL FILES ; ******************************************************************************* *REVISION HISTORY: * *DATE REV. NO. DESCRIPTION * *January 26, 2000 1.00 Initial release * *Revised by Exequiel Rarama for the ADAPT 912 ******************************************************************************* ; ; --------------------------- ; Demo - Main Routine ; --------------------------- #include REGS912A.INC * Operational Parameters _100MS equ 25 _250MS equ 61 _500MS equ 125 _1SECOND equ 250 _2SECONDS equ 500 _3SECONDS equ 750 _5SECONDS equ 1250 _10SECONDS equ 2500 _25SECONDS equ 6250 _60SECONDS equ 15000 _2MIN equ 30000 ;Audio Variables are define in "AUDIO.ASM" file ;TONE_2K equ 500 ;frequencies in Hertz for tone generation ;TONE_1K equ 1000 ;TONE_440 equ 2272 ;TONE_220 equ 4545 ;TONE_180 equ 3000 ;TONE_110 equ 9090 ;TONE_60 equ 16666 RAM equ $0800 ;68HC912b32 internal RAM STACK equ $0bff ;Stack at top of internal ram rbase equ $0000 ;68HC912B32 register block EEPROM equ $0d00 ;68HC912B32 internal EEPROM CODE equ $8000 ;Start of Flash * Operational Constants TRUE equ $FF FALSE equ $00 CR equ $D LF equ $A SPACE equ $20 ********************************************************************** * PORT ASSIGNMENTS for this program ;PORTT is initialize in REGS.INC _PORTT equ PORTT ;input capture/output compare port of 68HC812A4 * PT0 spare ;I/O * PT1 spare ;I/O * PT2 spare ;I/O * PT3 spare ;I/O * PT4 spare ;I/O * PT5 spare ;I/O * PT6 SPEAKER ;I/O * PT7 spare ;I/O ********************************************************************** * Masks ;OC Variables are define in "AUDIO.ASM" file ;OC6mask1 equ %01000000 ;IOS6 = 1, Bit 6 as output compare ;OC6mask2 equ %01000000 ;C6I = 1, Enable Interrupt ;OC6mask3 equ %00010000 ;OM6 = 0, OL6 = 1, toggel OC output line ;OC6flag equ %01000000 ;C6F = 1 to clear Interrupt flag ;ATD Variables admask2 equ %11000000 ;AFFC,ADPU=1 - Enable Analog to Digital admask3 equ %00000000 ;FRZ1,FRZ0=0 admask4 equ %10000001 ;SMP1,SMP0 = 0; S10BM,PRS0=1 - Select Sample time adn Bit mode admask5 equ %01110000 ;S8CM = 1, SCAN = 1, MULT = 1 SCFflag equ %10000000 ;SCF - Sequence Complete flag ;RTI Variables clrmask equ %11000000 ;mask for clearing timer flags rtimask1 equ %10000001 ;M=8Mhz, 1.024 msec interrupt with 16 MHz xtal rtimask2 equ %10000010 ;M=8Mhz, 2.048 msec interrupt with 16 MHz xtal rtimask3 equ %10000011 ;M=8Mhz, 4.096 msec interrupt with 16 MHz xtal rtimask4 equ %10000100 ;M=8Mhz, 8.196 msec interrupt with 16 MHz xtal rtimask5 equ %10000101 ;M=8Mhz, 16.384 msec interrupt with 16 MHz xtal rtimask6 equ %10000110 ;M=8Mhz, 32.768 msec interrupt with 16 MHz xtal rtimask7 equ %10000111 ;M=8Mhz, 65.536 msec interrupt with 16 MHz xtal rtiflag equ %10000000 ;SCI Variables scimask equ %00101100 ;RIE - SCI Interrupt enable ;RE - Receiver Enable RDRFflag equ %00100000 ;RDRF - Receive Data Register Full flag TDREflag equ %10000000 ;TDRE - Transmit Data Register Empty flag ;Baud rate definitions ;MCLK=8Mzh BAUD110 equ 4545 ;(baud) 110 baud with 16 Mhz crystal BAUD300 equ 1667 ;(baud) 300 baud with 16 Mhz crystal BAUD600 equ 833 ;(baud) 600 baud with 16 Mhz crystal BAUD1200 equ 417 ;(baud) 1200 baud with 16 Mhz crystal BAUD2400 equ 208 ;(baud) 2400 baud with 16 Mhz crystal BAUD4800 equ 104 ;(baud) 4800 baud with 16 Mhz crystal BAUD9600 equ 52 ;(baud) 9600 baud with 16 Mhz crystal BAUD14400 equ 35 ;(baud) 14400 baud with 16 Mhz crystal BAUD19200 equ 26 ;(baud) 19200 baud with 16 Mhz crystal BAUD38400 equ 13 ;(baud) 19200 baud with 16 Mhz crystal org RAM * System Variables COMMAND rmb 1 ;used by ProcessCommand H rmb 1 ;used in binary to decimal conversion TO rmb 1 DURATION rmb 2 ;used for tone generation HALF_PERIOD rmb 2 TIMER rmb 2 ;software timers using RTI TIMER1 rmb 2 COUNTER rmb 1 dummy rmb 1 ;ATD ram variables atd_var ad0 rmb 2 ad1 rmb 2 ad2 rmb 2 ad3 rmb 2 ad4 rmb 2 ad5 rmb 2 ad6 rmb 2 ad7 rmb 2 * Boolean Variables COMMAND_PENDING rmb 1 ;used by ProcessCommand CONTINUOUS rmb 1 ;flag for real-time a/d screen update ad_flag rmb 1 ad_val rmb 2 DBUFR rmb 5 d_flag rmb 1 ***************************** Program ******************************* org CODE version db '1.00' ;version number RESET1 ;This is where the RESET vector points to sei ;Disable Any interrupts ;Initialize Stack lds #STACK ;initialize stack pointer ;Initialize Real Time Interrupt movb #rtimask1,RTICTL ;Enable RTI and initialize RTI rate movb #rtiflag,RTIFLG ;Initialize COP movb #%10000111,COPCTL ;COP is enabled and is armed to ; reset in 1 second. ;Initialize Analog To Digital movb #admask2,ATDCTL2 ;enable ATD movb #admask4,ATDCTL4 ;Select Sample rate movb #admask5,ATDCTL5 ;Select 8 channel mode, Continuous scan ;and Multichannel ;Initialize Serial Communication Interface movb #scimask,SC0CR2 ;enable SCI 0 rcvr. & xmtr. & rx int movb #0,SC0CR1 movw #BAUD9600,SC0BDH ;Set baud rate to 9600 ldaa SC0SR1 ;read register to clear flag RDRF ldaa SC0DRL ;dummy read to flush receive buffer ;Initialize PORTT movb #%11111111,DDRP ;Bit 6,5 of PORTT are Output clr PORTP jsr audio_init ;Initialize bit 6 of PORTT as OC for audio o/p clr COMMAND_PENDING clr CONTINUOUS clr d_flag cli ;unmask interrupts ;do 4 BEEPS ldx #TONE_440 ;generate two 100 millisecond beeps @ 440 Hz ldab #$4 ; (connect speaker to PA6) ldy #_100MS jsr PulseXToneB ;power tones main movb #$55,COPRST ; movb #$AA,COPRST jsr ProcessCommand ;this is the program loop ldaa CONTINUOUS beq NotCont jsr ShowAnalog NotCont bra main ;small delay delay LDY #0 dly dbne y,dly ;decrement y counter rts ;Interrupt test traps RESET sei movb #$55,COPRST movb #$AA,COPRST ;Bit 5 of PORTT is toggled jsr delay jsr delay bclr PORTT,%00100000 jsr delay jsr delay bset PORTT,%00100000 bra RESET *********************************************************************** *Procedure Definitions: *********************************************************************** WaitX stx TIMER1 ;delays a length of time defined by x W1 ldx TIMER1 ; (note that whenever TIMER1 is non-zero, bne W1 ; it is decremented in the RTI interrupt rts ; service routine) ;----------------------------- ;Choose which one to process ProcessCommand: ldaa COMMAND_PENDING ;commands received via SCI interrupt cmpa #TRUE beq Process jmp PCX Process clr COMMAND_PENDING clr CONTINUOUS jsr PutNewLine ldaa COMMAND cmpa #'A' beq PCA cmpa #'a' beq PCA cmpa #'B' beq PCB cmpa #'b' beq PCB cmpa #'E' beq PCE cmpa #'e' beq PCE cmpa #'P' beq PCP cmpa #'p' beq PCP cmpa #'S' beq PCS cmpa #'s' beq PCS cmpa #'T' beq PCT cmpa #'t' beq PCT cmpa #'D' beq PCD cmpa #'d' beq PCD cmpa #'C' beq PCC cmpa #'c' beq PCC cmpa #'R' beq PCR cmpa #'r' beq PCR cmpa #'L' beq PCL cmpa #'l' beq PCL cmpa #'0' blo PCM cmpa #'7' bhi PCM jsr TogglePLine bra PCXX ;---------------------------- ;X register points to routine ;---------------------------- PCA ldx #PPCA jsr 0,x ;go execute routine bra PCX PCB ldx #PPCB jsr 0,x ;go execute routine bra PCX PCE ldx #PPCE jsr 0,x ;go execute routine bra PCX PCP ldx #PPCP jsr 0,x ;go execute routine bra PCX PCS ldx #PPCS jsr 0,x ;go execute routine bra PCX PCT ldx #PPCT jsr 0,x ;go execute routine bra PCX PCD ldx #PPCD jsr 0,x ;go execute routine bra PCX PCC ldx #PPCC jsr 0,x ;go execute routine bra PCX PCR ldx #PPCR jsr 0,x ;go execute routine bra PCX PCL ldx #PPCL jsr 0,x ;go execute routine bra PCX PCM ldx #PPCM jsr 0,x ;go execute routine bra PCX PCX PCXX RTS ;---------------------------------------------- PPCA ldx #M_PORTA jsr SendString ldab PORTA clra jsr SendDecByte jsr PutNewLine bra PCXX PPCB ldx #M_PORTB jsr SendString ldab PORTB clra jsr SendDecByte jsr PutNewLine bra PCXX PPCE ldx #M_PORTE jsr SendString ldab PORTE clra jsr SendDecByte jsr PutNewLine bra PCXX PPCP ldx #M_PORTP jsr SendString ldab PORTP clra jsr SendDecByte jsr PutNewLine bra PCXX PPCS ldx #M_PORTS jsr SendString ldab PORTS clra jsr SendDecByte jsr PutNewLine bra PCXX PPCT ldx #M_PORTT jsr SendString ldab PORTT clra jsr SendDecByte jsr PutNewLine bra PCXX PPCD ldx #M_PORTDLC jsr SendString ldab PORTDLC clra jsr SendDecByte jsr PutNewLine bra PCXX PPCC clr PORTP ldx #M_POFF jsr SendString jsr PutNewLine bra PPCX PPCM jsr ShowMenu bra PPCX PPCR staa CONTINUOUS ;set continuous a/d display flag bra PPCX PPCX rts PPCL ldx #M_BEEP ;beep speaker (if connected to PT6) jsr SendString jsr PutNewLine ldx #TONE_440 ;generate two 100 millisecond beeps @ 440 Hz ldab #2 ldy #_100MS jsr PulseXToneB bra PPCX TogglePLine: ldab #1 ;number is between 0 and 7 suba #'0' ;convert ASCII digit to binary number beq TBL1 TBL0 aslb ;set the appropriate mask bit dbne a,TBL0 TBL1 bitb PORTP ;if designated port bit is 1 beq TBM1 ; then make it 0 comb bra TBM0 TBM1 orab PORTP stab PORTP rts TBM0 andb PORTP stab PORTP rts ;Reg y contain the port address to toggle ;Reg b contain the the toggle bit toggle_port movb #8,COUNTER ldab #%01 toggle stab 0,y stab 0,x movw #120,TIMER jsr wait lslb dec COUNTER bne toggle rts wait pshx pshy wt movb #$55,COPRST movb #$AA,COPRST ldx TIMER bne wt puly pulx rts ;----------------------------------------------------------------------------- ShowMenu jsr PutDblLine ldx #M_UNDLN jsr SendString jsr PutNewLine jsr PutNewLine ldx #M_HEADER1 jsr SendString jsr PutNewLine ldx #M_UNDLN jsr SendString jsr PutNewLine jsr PutNewLine ldx #M_LINE1 jsr SendString jsr PutNewLine ldx #M_LINE2 jsr SendString jsr PutNewLine ldx #M_LINE3 jsr SendString jsr PutNewLine ldx #M_LINE4 jsr SendString jsr PutNewLine ldx #M_LINE5 jsr SendString jsr PutNewLine ldx #M_LINE6 jsr SendString jsr PutNewLine ldx #M_LINE7 jsr SendString jsr PutNewLine ldx #M_LINE8 jsr SendString jsr PutNewLine ldx #M_LINE9 jsr SendString jsr PutNewLine ldx #M_LINE10 jsr SendString jsr PutNewLine ldx #M_LINE11 jsr SendString jsr PutNewLine ldx #M_PROMPT jsr SendString rts ShowAnalog inc d_flag ldx #M_AD0 jsr SendString ldx #ad0 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD1 jsr SendString ldx #ad1 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD2 jsr SendString ldx #ad2 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD3 jsr SendString ldx #ad3 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD4 jsr SendString ldx #ad4 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD5 jsr SendString ldx #ad5 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD6 jsr SendString ldx #ad6 jsr HTOD ldx #DBUFR+2 jsr P1K ldaa #SPACE jsr SendByte ldx #M_AD7 jsr SendString ldx #ad7 jsr HTOD ldx #DBUFR+2 jsr P1K clr d_flag ldaa #CR jsr SendByte rts HexByte2Dec * Supply hex value to be converted in B register clra ldx #100 ;numerator in D, denominator in X idiv * remainder in D, quotient in X * B is lo-order byte xgdx stab H ;8 bit quotient in B xgdx ldx #10 ;H=0X TO=packed BCD idiv stab TO xgdx aslb aslb aslb aslb orab TO stab TO rts SendDecByte * value is in B clra jsr HexByte2Dec ldaa H adda #'0' jsr SendByte ldaa TO jsr SendASCIIHex rts SendASCIIHex * value in A psha anda #$F0 lsra lsra lsra lsra cmpa #$A blt SAH1 suba #$A adda #'A' bra SAH2 SAH1 adda #'0' SAH2 jsr SendByte pula psha anda #$0F cmpa #$A blt SAH3 suba #$A adda #'A' bra SAH4 SAH3 adda #'0' SAH4 jsr SendByte pula rts SendByte: * Transmits a byte, contained in register A, to the serial device via the SCI. SB1 ldab SC0SR1 ;wait for transmit data register empty (TDRE) bpl SB1 staa SC0DRL ;send byte rts PutNewLine ldaa #CR jsr SendByte ldaa #LF jsr SendByte rts PutDblLine ldaa #CR jsr SendByte ldaa #LF jsr SendByte ldaa #LF jsr SendByte rts SendString * x contains starting address of string RV1 ldaa 0,X ;$FF denotes end of string cmpa #$FF beq RVX jsr SendByte inx bra RV1 RVX rts ******************************************************************************* * Interrupt Routines ******************************************************************************* * Real-time Interrupt Routine RealTimeInt movb #rtiflag,RTIFLG ;clear real-time interrupt flag ; so that other interrupts can be service cli RTI_1 ldx TIMER beq RTI_2 dex stx TIMER RTI_2 ldx TIMER1 beq RTI_3 dex stx TIMER1 RTI_3 ldaa d_flag bne RTI_4 brclr ATDSTAT,SCFflag,* ;Loop here until SCF of ATD is set ;save ATD ldd ADR0H anda #$3 std ad0 ldd ADR1H anda #$3 std ad1 ldd ADR2H anda #$3 std ad2 ldd ADR3H anda #$3 std ad3 ldd ADR4H anda #$3 std ad4 ldd ADR5H anda #$3 std ad5 ldd ADR6H anda #$3 std ad6 ldd ADR7H anda #$3 std ad7 ; movw ADR0H,ad0 ; movw ADR1H,ad1 ; movw ADR2H,ad2 ; movw ADR3H,ad3 ; movw ADR4H,ad4 ; movw ADR5H,ad5 ; movw ADR6H,ad6 ; movw ADR7H,ad7 RTI_4 rti * SCI Input Interrupt Handler * Gets bytes from SCI. Sets COMMAND_PENDING flag. SerInputInt ldaa SC0SR1 ;read register to clear flag RDRF movb SC0DRL,COMMAND ;read receive buffer movb #TRUE,COMMAND_PENDING SIIX rti ;This is needed to service SWI interrupt dummy_int movb #$55,COPRST movb #$AA,COPRST rti ;----------------------------------------------------------------------------- ;HTOD-SUBROUTINE TO CONVERT A 16-BIT HEX NUMBER TO A 5 DIGIT DECIMAL ;This routine is taken from the HC11 manual. ;D=HEX VALUE TO BE CONVERTED ;X=ADDRESS WHERE THE NUMBER IS STORED TO BE CONVERTED HTOD LDD 0,X ; LDX #10000 IDIV ; XGDX ADDB #$30 STAB DBUFR XGDX LDX #1000 IDIV XGDX ADDB #$30 STAB DBUFR+1 XGDX LDX #100 IDIV XGDX ADDB #$30 STAB DBUFR+2 XGDX LDX #10 IDIV ADDB #$30 STAB DBUFR+4 XGDX ADDB #$30 STAB DBUFR+3 RTS P5DEC LDX #DBUFR ;POINT AT DECIMAL LDAA #$30 ;CHECK FOR LEADING ZEROS CMPA 0,X ;CHECK FOR 10,000S DIGIT BNE P10K ;START AT 10K DIGIT BSR SKP1 ;INX AND PRINT A SPACE CMPA 0,X ;CHECK FOR 1,000S BNE P1K ;START AT 1K DIGIT BSR SKP1 BSR SKP1 DEX CMPA 0,X ;CHECK FOR 100S DIGIT BNE P100 ;START AT 100 DIGIT BSR SKP1 CMPA 0,X ;CHECK 10S DIGIT BNE P10 BSR SKP1 BRA P1 ;START AT 1S DIGIT P10K LDAA 0,X ;10,000 DIGIT PSHX jsr SB1 PULX INX P1K LDAA 0,X PSHX jsr SB1 PULX INX P100 LDAA 0,X PSHX jsr SB1 PULX INX P10 LDAA 0,X PSHX jsr SB1 PULX INX P1 LDAA 0,X jsr SB1 RTS SKP1 PSHA INX LDAA #$20 jsr SB1 PULA RTS ******************************************************************************* * Messages ******************************************************************************* * Messages M_LINE1 fcc 'A => SHOW PORT A STATUS (SINGLE CHIP ONLY)' fcb $ff M_LINE2 fcc 'B => SHOW PORT B STATUS (SINGLE CHIP ONLY)' fcb $ff M_LINE3 fcc 'C => CLEAR PORT P OUTPUTS' fcb $ff M_LINE4 fcc 'D => SHOW PORT DLC STATUS' fcb $ff M_LINE5 fcc 'E => SHOW PORT E STATUS' fcb $ff M_LINE6 fcc 'L => FLASH LED (CONNECT TO PP6)' fcb $ff M_LINE7 fcc 'P => SHOW PORT P STATUS' fcb $ff M_LINE8 fcc 'S => SHOW PORT S STATUS' fcb $ff M_LINE9 fcc 'T => SHOW PORT T STATUS' fcb $ff M_LINE10 fcc 'R => SHOW 10-bit REAL-TIME ANALOG VALUES' fcb $ff M_LINE11 fcc '0 TO 7 => TOGGLE THE SELECTED P PORT LINE' fcb $ff M_PROMPT fcc '?' fcb $ff M_HEADER1 fcc ' ADAPT912 DEMO PROGRAM COMMAND MENU V1.00' FCB $FF M_UNDLN fcc '_______________________________________________' FCB $FF M_AD0 fcc 'AD0=' fcb $ff M_AD1 fcc 'AD1=' fcb $ff M_AD2 fcc 'AD2=' fcb $ff M_AD3 fcc 'AD3=' fcb $ff M_AD4 fcc 'AD4=' fcb $ff M_AD5 fcc 'AD5=' fcb $ff M_AD6 fcc 'AD6=' fcb $ff M_AD7 fcc 'AD7=' fcb $ff M_PORTA fcc 'PORTA=' fcb $ff M_PORTB fcc 'PORTB=' fcb $ff M_PORTE fcc 'PORTE=' fcb $ff M_PORTP fcc 'PORTP=' fcb $ff M_PORTS fcc 'PORTS=' fcb $ff M_PORTT fcc 'PORTT=' fcb $ff M_PORTDLC fcc 'PORTDLC=' fcb $ff M_POFF fcc 'PORT P CLEARED' FCB $FF M_BEEP fcc '>>> BEEP! <<<' FCB $FF #include AUDIO.ASM PsuedoVECTOR EQU $F7CE FDB RESET ;reserved FDB RESET ;reserved FDB RESET ;ANALOG TO DIGITAL FDB RESET ;reserved FDB SerInputInt ;SERIAL COMMUNICATION 0 FDB RESET ;SPI SERIAL TRANSFER COMPLETE FDB RESET ;PULSE ACCUMULATOR INPUT EDGE FDB RESET ;PULSE ACCUMULATOR OVERFLOW FDB RESET ;TIMER OVERFLOW FDB RESET ;TIMER CHANNEL 7 FDB OC6Int ;TIMER CHANNEL 6 FDB RESET ;TIMER CHANNEL 5 FDB RESET ;TIMER CHANNEL 4 FDB RESET ;TIMER CHANNEL 3 FDB RESET ;TIMER CHANNEL 2 FDB RESET ;TIMER CHANNEL 1 FDB RESET ;TIMER CHANNEL 0 FDB RealTimeInt ;REAL TIME INTERRUPT FDB RESET ;IRQ OR KEY WAKE UP D FDB RESET ;XIRQ FDB dummy_int ;SWI FDB RESET ;RESERVED FDB RESET ;COP FAILURE RESET FDB RESET ;COP CLOCK MONITOR FAIL RESET FDB RESET1 ;RESET ;MC68HC912b32 VECTOR INTERRUPTS VECTOR EQU $FFCE ORG VECTOR FDB RESET ;reserved FDB RESET ;reserved FDB RESET ;ANALOG TO DIGITAL FDB RESET ;reserved FDB SerInputInt ;SERIAL COMMUNICATION 0 FDB RESET ;SPI SERIAL TRANSFER COMPLETE FDB RESET ;PULSE ACCUMULATOR INPUT EDGE FDB RESET ;PULSE ACCUMULATOR OVERFLOW FDB RESET ;TIMER OVERFLOW FDB RESET ;TIMER CHANNEL 7 FDB OC6Int ;TIMER CHANNEL 6 FDB RESET ;TIMER CHANNEL 5 FDB RESET ;TIMER CHANNEL 4 FDB RESET ;TIMER CHANNEL 3 FDB RESET ;TIMER CHANNEL 2 FDB RESET ;TIMER CHANNEL 1 FDB RESET ;TIMER CHANNEL 0 FDB RealTimeInt ;REAL TIME INTERRUPT FDB RESET ;IRQ OR KEY WAKE UP D FDB RESET ;XIRQ FDB dummy_int ;SWI FDB RESET ;RESERVED FDB RESET ;COP FAILURE RESET FDB RESET ;COP CLOCK MONITOR FAIL RESET FDB RESET1 ;RESET