📄 code.s
字号:
# This program will Demonstrate the use of the Mico8
# In a ECP6 device. It will use EBR ram to
# store the instruction set.
#
#
# The demo will show the following functionality:
# UART TX
# PWM
# LEDs
# 4x20 character LCD display
# SEROUT
#
# Interrupt handler
# RC5 RX
# DIP8 DIPSwitch inputs
# RX UART
#
#
#Mico8 address bus:
#------------------
#
#UART settings:
#This UART runs at a default 9600baud,8 data bits,1 stop bit no parity
#
# Address map:
# 0-0x00 00000000: NU
# 1-0x01 00000001: NU
# 2-0x02 00000010: NU
# 3-0x03 00000011: W 7 Segments display
# 4-0x04 00000100: W LCD Data register
# 5-0x05 00000101: W LCD control register
# 6-0x06 00000110: W TX Uart data register
# 7-0x07 00000111: W LED peripheral register
# 8-0x08 00001000: W PWM duty cycle register
# 9-0x09 00001001: W SEROUT peripheral register
#...
#16-0x10 00010000: R Interrupt Source Register
#17-0x11 00010001: R Interrupt data register peripheral1 = RC5 RX
#18-0x12 00010010: R Interrupt data register peripheral2 = DIP8
#19-0x13 00010011: R Interrupt data register peripheral3 = RX UART
#20-0x14 00010100: R Interrupt data register peripheral4
#
#
# The interrupt handler generates an interrupt when one of its peripherals
# has new data available.
# Mico8 can then read the 'Interrupt Source Register' to check what peripheral
# caused the interrupt.
# Then Mico8 can read the corresponding 'Interrupt Data Register', this automaticaly
# clears the bit in the 'Interrupt Source Register'.
# When Mico8 exits its interrupt service routine, the Mico8_Intack goes low.
# At that point the Interrupt handler will check if there are still pending
# data available but in case there are it will wait for a certain amount of time
# before regenerating a new Mico8_INT.
#
#
# Register Usage
#
# r1(0) right/left control (1=right)
# r2 rotate reg
# r3 countdown timer1
# r4 countdown timer2
# r5 countdown timer3
# r6 Wait loop speed setting variable
# r7 INT register
# r8 INT register
# r9 INT register
# r10 LCD interface variable
# r11 lcd data text register
b int_handler
start:
movi r1, 0x01 # use r1 bit0 as rotate direction. 1=rt 0=dn
movi r2, 0xFE # initialize reg2 + indicate the system is active
movi r6, 0x01 # init speed variable to fast, (medium=0x3F, slow=0xFF)
seti # set the program to be able to receive interrupt
call lcd_init
call lcd_init
call lcd_init
call lcd_reset
call lcd_line1
call lcd_text1
# call line2
# call text2
# call line3
##################################################################
rotate_right:
ror r2, r2 # rotate contents of reg2 right speedcontrol
export r2,0x07 # export value in reg2 to io port 7
export r2,0x09 # export value in reg2 to io port 9
call wait # control increment so led activity is visible
cmpi r2,0xFE # check if we are at the end
bz rotate_left # turn around
b rotate_right # next count
rotate_left:
rol r2, r2 # rotate contents of reg2 left speedcontrol
export r2,0x07 # export value in reg2 to io port 7
export r2,0x09 # export value in reg2 to io port 9
call wait # control decrement so led activity is visible
cmpi r2,0x7F # check if we are at the end
bz rotate_right # turn around
b rotate_left # next rotate
##################################################################
lcd_init:
movi r10,0x30
export r10,0x04 # LCD_Data PORT initialized to 0x30
call lcd_renable
movi r6,0x3F
call wait
ret
lcd_reset:
movi r10,0x38
export r10,0x04 # 8bit interface, 2lines, standard font
call lcd_renable
movi r6,0x3F
call wait
movi r10,0x08
export r10,0x04 # turn off display, cursor off, blink off
call lcd_renable
movi r6,0x3F
call wait
movi r10,0x01
export r10,0x04 # clear display
call lcd_renable
movi r6,0x3F
call wait
movi r10,0x06
export r10,0x04 # increment cursor, no scroll
call lcd_renable
movi r6,0x3F
call wait
movi r10,0x0C
export r10,0x04 # display on, cursor off, no blinking
call lcd_renable
movi r6,0x3F
call wait
ret
lcd_line1:
movi r10,0x80
export r10,0x04 # cursor at begin 1st line
call lcd_renable
movi r6,0x3F
call wait
lcd_line2:
movi r10,0xC0
export r10,0x04 # cursor at begin 2nd line
call lcd_renable
movi r6,0x3F
call wait
lcd_line3:
movi r10,0xA0
export r10,0x04 # cursor at begin 3rd line
call lcd_renable
movi r6,0x3F
call wait
lcd_line4:
movi r10,0xE0
export r10,0x04 # cursor at begin 4th line
call lcd_renable
movi r6,0x3F
call wait
lcd_text1:
movi r11,'H'
call lcd_data
movi r11,'E'
call lcd_data
movi r11,'L'
call lcd_data
movi r11,'L'
call lcd_data
movi r11,'O'
call lcd_data
movi r11,' '
call lcd_data
movi r11,'I'
call lcd_data
movi r11,' '
call lcd_data
movi r11,'A'
call lcd_data
movi r11,'M'
call lcd_data
movi r11,' '
call lcd_data
movi r11,'M'
call lcd_data
movi r11,'I'
call lcd_data
movi r11,'C'
call lcd_data
movi r11,'O'
call lcd_data
movi r11,'8'
call lcd_data
ret
lcd_data:
mov r10,r11
export r10,0x04 # LCD_Data PORT
call lcd_denable # send DATA
movi r6,0x3F
call wait
ret
lcd_renable:
movi r6,0x01 # register write action
movi r10,0x00
export r10,0x05 # LCD control PORT write, enable=0
call wait
movi r10,0x02
export r10,0x05 # LCD control PORT write, enable=1
call wait
nop
nop
nop
nop
movi r10,0x00
export r10,0x05 # LCD control PORT write, enable=0
ret
lcd_denable:
movi r6,0x01 # data write action
movi r10,0x01
export r10,0x05 # LCD control PORT write, enable=0
call wait
movi r10,0x03
export r10,0x05 # LCD control PORT write, enable=1
call wait
nop
nop
nop
nop
movi r10,0x01
export r10,0x05 # LCD control PORT write, enable=0
ret
##################################################################
wait:
movi r5, 0x18 #load reg3&4&5 with wait values
init_reg4:
mov r4,r6
init_reg3:
movi r3, 0xff
dec_reg3:
subi r3, 0x01 #decrement reg3
bz dec_reg4
b dec_reg3
dec_reg4:
subi r4, 0x01 #decrement reg4
bz dec_reg5
b init_reg3
dec_reg5:
subi r5, 0x01 #decrement reg4
bz timeout
b init_reg4
timeout:
ret # go back for next rotate
nop
##################################################################
int_handler:
# clri
#we received an interrupt so we start the handler:
import r7,0x10 # interrupt source register
mov r8,r7 # copy r7 to r8
andi r8,0x01 # check if it is the first peripheral?
bz peri2 # not peri1, check peri2
import r8,0x11 # read/clear interrupt data register 1 (RC5 RX)
export r8,0x03 # write value to 7segments display
peri2:
mov r8,r7
andi r8,0x02 # check if it is the second peripheral?
bz peri3 # not peri2, check peri3
import r8,0x12 # read/clear interrupt data register 2 (DIP8)
export r8,0x08 # send DIPSwitch data to PWM
peri3:
mov r8,r7
andi r8,0x04 # check if it is the third peripheral?
bz peri4 # not peri3, check peri4
import r8,0x13 # read/clear interrupt data register 3 (RX UART)
export r8,0x06 # send the RX data to the TX Uart
peri4:
mov r8,r7
andi r8,0x08 # check if it is the fourt peripheral?
bz exisr # not peri4, exit ISR
import r8,0x14 # read/clear interrupt data register 4
nop # do nothing
exisr:
# seti
iret
nop
##################################################################
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -