The eZ8 can have up to two UART's built in. It can be used to send midi notes to a keyboard or text to a terminal program running on your computer.
To set up serial you need to specify the baudrate and set the pinmodes for the serial pins.
Calculating the frequency for the baudrate generator.
;Change this to the crystal frequency you are using. SYSFREQ EQU 2000000 ; UART baudrate selection UART_BAUD EQU 115200 UART_BRG EQU ((SYSFREQ + (UART_BAUD * 8)) / (UART_BAUD * 16))
Macro to turn on uart interrupts
EI_U: MACRO orx IRQ0ENH, #%10 orx IRQ0ENL, #%10 ENDMAC
If you want to be able to receive data via serial as well add this line:
VECTOR UART0_RX = isr_uart_rx
...and next: set up the pinmodes and interrupts.
init_uart: ldx PAADDR,#DDR ;Set RX to input orx PACTL,#(16) andx PACTL,#~(32) ;Set TX to output ldx PAADDR,#AF orx PACTL,#((16)|(32)) ldx U_BRH, #HIGH(UART_BRG) ldx U_BRL, #LOW(UART_BRG) ldx U_CTL1, #%00 ; clear for normal non-Multiprocessor operation ldx U_CTL0, #%C0 ; Transmit enable, Receive Enable, No Parity, 1 Stop EI_U ret
To send a byte simply do this:
ldx U_D, #42 ; Write 42 to serial data register.
If you want to make sure it works every time make sure to wait for the uart to finish sending the last byte. You can do this by checking the uart status register. In a routine it looks like this:
putc: push R1 $$: ldx R1, U_STAT0 ;Loop until serial is ready. and R1, #%04 jr Z, $B ldx U_D, R0 ; Write R0 to serial data register. It gets sent automatically! pop R1 ret
Using interrupts for receiving bytes is really helpful. You don't have to worry about continuously polling for data. Just have an interrupt service routine for it. Make sure your interrupts are globally enabled using the EI instruction. Also make sure you set the isr vector. VECTOR UART0_RX = isr_uart_rx
isr_uart_rx: ldx R0,U0RXD ;Load data from uart rx data register in R0 ;put your code here iret
This is simpleserial.inc revision 1.
; simpleserial.inc ; by Koen van Vliet ; CC0 - Public Domain ; blog: ; http://8times8.host56.com ; programmers reference: ; http://ez8tut.sourceforge.com VECTOR UART0_RX = isr_uart_rx ;Change this to the crystal frequency you are using. SYSFREQ EQU 2000000 ;------------------------------------------------------------------------------ ; UART baudrate selection UART_BAUD EQU 115200 UART_BRG EQU ((SYSFREQ + (UART_BAUD * 8)) / (UART_BAUD * 16)) ; UART control, status and data register mnemonics U_BRH EQU U0BRH U_BRL EQU U0BRL U_CTL0 EQU U0CTL0 U_CTL1 EQU U0CTL1 U_STAT0 EQU U0STAT0 U_D EQU U0D EI_U: MACRO orx IRQ0ENH, #%10 orx IRQ0ENL, #%10 ENDMAC ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Output a character to UART ; R0: holds the character to send putc: push R1 $$: ldx R1, U_STAT0 and R1, #%04 jr Z, $B ldx U_D, R0 pop R1 ret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Output a string to UART ; RR0: holds the address of the string puts: push R2 push R3 ld R2, R0 ld R3, R1 $$: ldc R0, @RR2 cp R0, #0 jr Z, $F call putc incw RR2 jr $B $$: pop R3 pop R2 ret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Output a string to UART from register file instead of flash ; RR0: holds the address of the string puts_r: push R2 push R3 ld R2, R0 ld R3, R1 $$: ldx R0, @RR2 cp R0, #0 jr Z, $F call putc incw RR2 jr $B $$: pop R3 pop R2 ret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Output data from Flash of SIZE bytes long ; RR0: holds the address of the data ; R4: The size putFd: push R2 push R3 ld R2,R0 ld R3,R1 $$: ldc R0, @RR2 call putc incw RR2 djnz R4,$B pop R3 pop R2 ret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Intialize UART init_uart: ldx U_BRH, #HIGH(UART_BRG) ldx U_BRL, #LOW(UART_BRG) ldx U_CTL1, #%00 ; clear for normal non-Multiprocessor operation ldx U_CTL0, #%C0 ; Transmit enable, Receive Enable, No Parity, 1 Stop EI_U ret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Output an integer to UART formatted as a string ; RR0: holds the integer puti: cp R1,#0 cpc R0,#0 jr nz,$F ld R0,#30h call putc ret $$: ld R5,#00h ld R2,#high(-10000) ld R3, #low(-10000) call Num1 ld R2,#high(-1000) ld R3, #low(-1000) call Num1 ld R2,#high(-100) ld R3, #low(-100) call Num1 ld R2,#high(-10) ld R3, #low(-10) call Num1 ld R3,R2 Num1: ld R4,#('0'-1) Num2: inc R4 add R1,R3 adc R0,R2 jr c,Num2 sub R1,R3 sbc R0,R2 cp R5,1 jr z,Num3 cp R4,#('0') jr z,Num4 Num3: ld R5,1 push R0 ld R0,R4 call putc pop R0 Num4: ret SCOPE ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ; Interrupt Service Routine for UART isr_uart_rx: ldx R0,U0RXD ;Load data from uart rx data register in R0 ;put your code here iret ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;;;; Routine: puth ;;;;; Print byte as hexadecimal ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; puth: push R0 ;Upper nibble srl R0 ;>>4 srl R0 srl R0 srl R0 add R0,#30h cp R0,#(30h + 9) ;0-9 jr ule,$F add R0,#(10h - 9);A-F $$: call putc pop R0 ;Lower nibble and R0,#0Fh add R0,#30h cp R0,#(30h + 9) ;0-9 jr ule,$F add R0,#(10h - 9);A-F $$: call putc ret
Please submit corrections, suggestions, and new documentation here: Submit a ticket
← Return to Reference Index
This is not an official Zilog website. Zilog nor 8times8 are liable for any damage done to equipment. Tutorial and reference copyright ©8times8 Creative Commons CC-0 License (public domain.) This reference uses content from Zilog's technical datasheets. Fair use only. Datasheets copyright © 2013 Zilog®, Inc. Z8, Z8 Encore!, Z8 Encore! XP and Z8 Encore! MC are trademarks or registered trademarks of Zilog, Inc. Read Zilog's terms at zilog.com
Website design by Koen van Vliet. Hosted by sourceforge.net