📄 keyboard.asm
字号:
;==========================================
;function: moniter ps2 bus,get command from ps2(keyboard to pc)
;so we can start a communication with pc
;no output clk, listen keyboard send start
;input: no
;output: no
rec_from_key:
ldi temp,key_board_err
mov cmd_register,temp
sbic ps2_dat_in_addr,ps2_dat ;dat =0 ,start,then low pulse of clk
rjmp pc_to_keyboard
rec_key_start:
ldi key_bit_count, 8
ldi parity, 0x00
rec_key_loop:
sbis ps2_clk_in_addr,ps2_clk ;clk -> high
rjmp $-2
sbic ps2_clk_in_addr,ps2_clk ;clk -> low
rjmp $-2
clc
sbic ps2_dat_in_addr,ps2_dat ;recieve a bit
sec
ror key_bit_buffer
sbrc key_bit_buffer, 7
inc parity
rec_key_loop1:
dec key_bit_count
brne rec_key_loop
sbis ps2_clk_in_addr,ps2_clk ;clk -> high
rjmp $-2
sbic ps2_clk_in_addr,ps2_clk ;clk -> low
rjmp $-2
sbic ps2_dat_in_addr,ps2_dat ;parity bit
inc parity ;xor rx8 ,here,result must be a 1
sbis ps2_clk_in_addr,ps2_clk ;clk -> high
rjmp $-2
sbic ps2_clk_in_addr,ps2_clk ;clk -> low
rjmp $-2
sbis ps2_dat_in_addr,ps2_dat ;stop
ret ;stop error,find new start bit again
sbrs parity, 0 ;partiy xor rx8 = 1,odd success
ret ;parity error,find a new start bit
; st y+, key_bit_buffer ;just for test key rec,for send to uart
sbis ps2_clk_in_addr,ps2_clk ;clk -> high
rjmp $-2
clr cmd_register
ret
pc_to_keyboard:
sbis ps2_clk_in_addr,ps2_clk
rjmp $-2 ;wait for clk high,show next clk can be detected
ldi temp,no_key_in
mov cmd_register,temp
ret
;=================================================
/************** with break ************************
listen_ps2:
sbic ps2_clk_in_addr,ps2_clk ;keyboard_clk -> low
ret
clr counter1 ;for make
clr counter2 ;for break
ldi ZH, key_buffer_high
ldi ZL, key_buffer_low
brie listen_ps2_loop
cli ;protect realtime signal
ori app_state,en_ie
listen_ps2_loop:
wdr
sbic ps2_clk_in_addr,ps2_clk ;keyboard_clk -> low
rjmp listen_ps2_loop
rcall rec_from_key ;get make
mov temp,cmd_register
cpi temp,no_key_in
breq listen_ps2_loop ;a mouse clk occure
cpi temp, cmd_ok
brne listen_ps2_error11 ;parity error or stop bit losed
;****** for repeat **************
cpi counter1,0 ;first key
breq save_new_key
mov temp, key_bit_buffer
cpi temp,0xe1 ;e1 no repeat,but lose other break
brne func_repeat_e0
ldi XH, key_buffer_high ;e1,return to counter = 0
ldi XL, key_buffer_low
ld temp, X
cpi temp,0xe1
breq save_new_key
ldi ZH, key_buffer_high ;first e1,return to counter = 0
ldi ZL, key_buffer_low
clr counter1
clr counter2
rjmp save_new_key
listen_ps2_error11:
rjmp listen_ps2_error
func_repeat_e0:
cpi temp, 0xe0
brne repeat_current
rjmp save_new_key
repeat_current:
ld temp, -Z ;current key
ld temp1,Z+
cp temp, key_bit_buffer
breq listen_ps2_loop ;normal repeat
cpi counter1, 0x02
brlo save_new_key
cpi temp, 0xe0 ;current key = e0,now we must find ahead
brne save_new_key
ld temp,-Z ;current
ld temp,-Z ;last,the next is e0
cp temp, key_bit_buffer
breq function_repeat ;repeat
ld temp, Z+ ;z->current
ld temp, Z+ ;z->new
rjmp save_new_key
function_repeat:
dec counter1
dec counter1
ld temp, Z+
rjmp listen_ps2_loop
save_new_key:
mov temp,key_bit_buffer
cpi temp, 0xf0
breq listen_ps2_break
st Z+, key_bit_buffer
inc counter1
;**********count for break ***************
mov temp, key_bit_buffer
cpi temp,0xe1
breq listen_ps2_loop
cpi temp,0xe0
breq listen_ps2_loop ;e0,function key,then get the real key value
inc counter2
rjmp listen_ps2_loop ;get next push down key
listen_ps2_break:
out UDR,counter2
sbis UCSRA,UDRE
rjmp $-2
listen_ps2_break01:
wdr
dec counter2 ;get a key pop up
breq listen_ps2_break03
listen_ps2_break02:
sbic ps2_clk_in_addr,ps2_clk ;keyboard_clk -> low
rjmp listen_ps2_break02
rcall rec_from_key ;get break
mov temp,cmd_register
cpi temp,no_key_in
breq listen_ps2_break02 ;a mouse clk occure
cpi temp, cmd_ok
brne listen_ps2_error ;parity error or stop bit losed
mov temp,key_bit_buffer
cpi temp,0xf0
brne listen_ps2_break02 ;not f0,just real key,half of break
rjmp listen_ps2_break01 ; dec counter2 ;get a break start
;brne listen_ps2_break01 ;get real key,and next f0
listen_ps2_break03:
wdr
sbic ps2_clk_in_addr,ps2_clk ;keyboard_clk -> low
rjmp listen_ps2_break03
rcall rec_from_key ;get last break
mov temp,cmd_register
cpi temp,no_key_in
breq listen_ps2_break03 ;a mouse clk occure
cpi temp, cmd_ok
brne listen_ps2_error ;parity error or stop bit losed
;----------------------------------------
;now get a sort of key value,we can compare with config item
/****************** without break ******************/
;=================================================
listen_ps2:
;cpi app_state, init_state
;breq test_key_data
;ret
;cpi app_state, card_upload_state
; breq test_key_data
;ret
test_key_data:
sbic ps2_dat_in_addr,ps2_dat ;keyboard_data -> low
ret
clr find_card_timer1
clr find_card_timer2
clr counter1 ;for make
ldi ZH, key_buffer_high
ldi ZL, key_buffer_low
cli
;protect realtime signal
listen_ps2_loop_data:
wdr
sbic ps2_clk_in_addr,ps2_clk ;keyboard_clk -> low
rjmp listen_ps2_loop_data
rcall rec_from_key ;get make
mov temp,cmd_register
cpi temp,no_key_in
breq listen_ps2_loop ;a mouse clk occure
cpi temp, cmd_ok
brne listen_ps2_error11 ;parity error or stop bit losed
/****** for repeat **************/
cpi counter1,0 ;first key
breq save_new_key
mov temp, key_bit_buffer
cpi temp,0xe1 ;e1 no repeat,but lose other break
brne func_repeat_e0
ldi XH, key_buffer_high ;e1,return to counter = 0
ldi XL, key_buffer_low
ld temp, X
cpi temp,0xe1
breq save_new_key
ldi ZH, key_buffer_high ;first e1,return to counter = 0
ldi ZL, key_buffer_low
clr counter1
rjmp save_new_key
listen_ps2_loop:
wdr
sbic ps2_dat_in_addr,ps2_dat ;keyboard_data -> low
rjmp listen_ps2_loop
rjmp listen_ps2_loop_data
listen_ps2_error11:
rjmp listen_ps2_error
func_repeat_e0:
cpi temp, 0xe0
brne repeat_current
rjmp save_new_key
repeat_current:
ld temp, -Z ;current key
ld temp1,Z+
cp temp, key_bit_buffer
breq listen_ps2_loop ;normal repeat
cpi counter1, 0x02
brlo save_new_key
cpi temp, 0xe0 ;current key = e0,now we must find ahead
brne save_new_key
ld temp,-Z ;current
ld temp,-Z ;last,the next is e0
cp temp, key_bit_buffer
breq function_repeat ;repeat
ld temp, Z+ ;z->current
ld temp, Z+ ;z->new
rjmp save_new_key
function_repeat:
dec counter1
dec counter1
ld temp, Z+
rjmp listen_ps2_loop
save_new_key:
mov temp,key_bit_buffer
cpi temp, 0xf0
breq listen_ps2_break
st Z+, key_bit_buffer
inc counter1
rjmp listen_ps2_loop ;get next push down key
;----------------------------------------
listen_ps2_break:
;here must delay any time or do something,because break code after f0 would be recongnized as a make code,
;and program will wait another f0 as break,so,betwin two key,nothing can do
cpi counter1,0
breq no_item_equ ;recieve no make,just break
;rjmp test_send_out_key
//test ctrl+d for download config table
/* ********** for release key ************* 2006 9 19 remove
ldi temp1,10
rcall delay_mS
wdr
ldi temp1,10
rcall delay_mS
wdr
ldi temp1,10
rcall delay_mS
*/
wdr
ldi ZH,key_buffer_high
ldi ZL,key_buffer_low
clc
add ZL,counter1
adc ZH,zero_register
ld temp,-Z
cpi temp,0x23
brne goto_lookfor_table
ld temp,-Z
cpi temp,0x14
brne goto_lookfor_table
rcall download_key_table ;download config table
rjmp exit_ps2_listen
goto_lookfor_table:
/* *********** looking for code *********** *
ldi YH, key_buffer_high
ldi YL, key_buffer_low
clc
add YL,counter1
adc YH,zero_register ;after last key in buffer
clr counter2
ldi ZH,high(key_table_func)
ldi ZL,low(key_table_func)
adiw ZL,2 ;last key in item1
lpm
ld temp,-Y ;last key in buffer
look_for_item:
cp temp,R0
breq find_equ_item
inc counter2 ;item_index
clc
ldi temp1,0x03
add ZL,temp1 ;next item
adc ZH,zero_register
lpm
cp R0, zero_register ;end of table
brne look_for_item
no_item_equ:
rjmp exit_ps2_listen
find_equ_item:
ld temp,-Z
lpm
cp R0,zero_register ;second in table
breq goto_send_command
dec counter1
breq no_item_equ
ld temp,-Y ;before the last key
cp temp,R0
brne no_item_equ
ld temp,-Z
lpm
cp R0,zero_register
breq goto_send_command
dec counter1
breq no_item_equ
ld temp,-Y
cp temp,R0
brne no_item_equ
/*********************************************************/
/* *************** looking for eeprom ****************** */
ldi YH, key_buffer_high
ldi YL, key_buffer_low
clc
add YL,counter1
adc YH,zero_register ;after last key in buffer
clr counter2
ldi eeprom_addrl,EEP_SEX ;item1.0
dec eeprom_addrl ;item0.2
clr eeprom_addrh
rcall read_eeprom
ld temp,-Y ;last key in buffer
look_for_item:
wdr
cp temp,eeprom_data
breq find_equ_item
look_for_like_item: ;add 2006 9 19 for same num item
inc counter2 ;item_index
clc
ldi temp1,0x03
add eeprom_addrl,temp1 ;next item
rcall read_eeprom
ldi temp1,0xff
cp eeprom_data, temp1 ;end of table
brne look_for_item
no_item_equ:
rcall delay_200ms
rcall delay_200ms
rcall delay_200ms
rjmp exit_ps2_listen
look_for_like_item04:
look_for_like_item03:
inc counter1 ;before last
look_for_like_item02:
look_for_like_item01:
inc counter1 ;last key in buffer
ldi temp,3
push r1
mul counter2,temp
ldi eeprom_addrl,EEP_SEX ;item1.0
dec eeprom_addrl
clr eeprom_addrh
add eeprom_addrl,r0 ;current item.2
pop r1
;rewind point to last key ,and get last key
ldi YH, key_buffer_high
ldi YL, key_buffer_low
clc
add YL,counter1
adc YH,zero_register ;after last key in buffer
ld temp,-Y ;last key in buffer
rjmp look_for_like_item ;next item same last key
find_equ_item:
dec eeprom_addrl
rcall read_eeprom
cp eeprom_data,zero_register ;second in table
breq goto_send_command ;0 means item compare completed,ok
dec counter1
; breq no_item_equ ;eeprom item have some keyvalue,but buffer recieved little than eeprom,so item not complete
breq look_for_like_item01 ;looking for some like item
ld temp,-Y ;before the last key
cp temp,eeprom_data
; brne no_item_equ
brne look_for_like_item02 ;looking for some like item
dec eeprom_addrl
rcall read_eeprom
cp eeprom_data,zero_register
breq goto_send_command02
dec counter1
; brne no_item_equ
brne look_for_like_item03 ;looking for some like item
ld temp,-Y
cp temp,eeprom_data
; brne no_item_equ
brne look_for_like_item04 ;looking for some like item
inc counter1 ;old counter1
goto_send_command02:
inc counter1 ;old counter1
/**********************************************/
goto_send_command:
; rcall delay_200ms ;for release key 2006 9 19 remove
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -