From 59a06810cfad2183c1f457bc381b399ed4d6017e Mon Sep 17 00:00:00 2001 From: ian Date: Mon, 14 Nov 2005 00:12:37 +0000 Subject: [PATCH] before reorg for state-based --- detpic/i2clib.asm | 117 ++++++++++++++++++++++++++++------------------ 1 file changed, 72 insertions(+), 45 deletions(-) diff --git a/detpic/i2clib.asm b/detpic/i2clib.asm index dbdc00d..b3ff2d3 100644 --- a/detpic/i2clib.asm +++ b/detpic/i2clib.asm @@ -12,7 +12,7 @@ udata_acs -t res 1 +ssp res 1 st res 1 ; bitmask: st_writing equ 0 @@ -43,39 +43,30 @@ i2cs_init i2cs_interrupt bt_f_if0 PIR1, SSPIF return + ; We have an interrupt: -; We have an interrupt. Firstly, clear the interrupt flag -; so that if something else happens while we faff, the interrupt -; will be regenerated: +; Firstly, clear the interrupt flag so that if something else happens +; while we faff, the interrupt will be regenerated: bc_f PIR1, SSPIF -; Check that nothing is wrong: +; Check that nothing obvious is wrong: mov_fw SSPCON1 - mov_wf t + mov_wf ssp and_lw 0xc0 bra_nz i2cs_interrupt_wcolsspov_endif panic morse_SV i2cs_interrupt_wcolsspov_endif ; Find out what's just happened: - mov_ff SSPSTAT, t + mov_ff SSPSTAT, ssp ; bits we want to check ; 80 60 20 10 08 04 02 01 ; SMP CKE D_A P S R_W UA BF ; set clr data? stop start read? clr full? -chkvalm macro mask, value, label - mov_fw t - xor_lw value - bra_z label - endm - - chkvalm 0xdf, 0x90, s_case_something_stop - chkvalm 0xdb, 0x88, s_case_uninteresting_start - - mov_fw t - + mov_fw ssp chkval_lastvalue equ 0 + chkval macro value, label xor_lw value ^ chkval_lastvalue chkval_lastvalue equ value @@ -85,44 +76,59 @@ chkval macro value, label chkval 0x89, s_case_addr_recv_write chkval 0x8d, s_case_addr_recv_read chkval 0xa9, s_case_write_data_recv + + bt_f_if0 st, st_reading + bra s_ifnot_reading + + ; only check this if we're reading; otherwise + ; this will be handled by s_case_uninteresting_start chkval 0xac, s_case_read_data_sent chkval 0xa8, s_case_read_data_nack - mov_ff t, WREG2 ; fixme +s_ifnot_reading + +chkvalm macro mask, value, label + mov_fw ssp + xor_lw value + bra_z label + endm + + chkvalm 0xdf, 0x90, s_case_something_stop + chkvalm 0xdb, 0x88, s_case_uninteresting_start + + mov_ff ssp, WREG2 ; fixme panic morse_SS ;---------- s_case_something_stop - bc_f SSPCON1, 3 ; disable Start and Stop interrupts +s_case_something_start +s_ensure_idle + mov_fw st ; were we doing something ? + bt_f_if1 STATUS,Z + return + ; we were, it seems: - ; Were we receiving ? - bt_f_if0 st, st_writing - bra s_caseshare_something_uninteresting + bc_f SSPCON, 3 + clr_f st + ; now we're not (but W still has old st) - ; Yes, we were receiving: - clr_f st ; now we're idle + bt_f_if1 WREG, st_writing goto i2csu_write_done - ; tail call; we couldn't do anything after that - ; anyway since it might well reenter us. -;---------- -s_case_something_start - bc_f SSPCON, 3 ; disable Start and Stop interrupts -s_caseshare_something_uninteresting - tst_f_ifnz st ; were we doing something ? - bra s_panic_st_unexpected - return + bt_f_if1 WREG, st_reading + goto i2csu_read_done + + mov_wf st ; put it back and then ... s_panic_st_unexpected panic morse_ST ;---------- s_case_addr_recv_write + rcall s_ensure_idle bs_f SSPCON, 3; we'll need the Stop interrupt bs_f st, st_writing -s_case_addr_recv_read - ; well, this is all just fine so do carry on - rcall s_write_slurpbyte + ; well, now this is all fine so do carry on: s_write_slurpbyte ; W any byte from master @@ -136,40 +142,61 @@ s_case_write_data_recv bt_f_if0 st, st_writing bra s_panic_st_unexpected ; ok, we are writing: + rcall s_write_slurpbyte + bt_f_if1 st, st_subsequent goto i2csu_write_another - ; not subsequent: + ; not subsequent (yet): + bs_f st, st_subsequent goto i2csu_write_begin +;---------- +s_case_addr_recv_read + rcall s_ensure_idle + bs_f st, st_reading + call i2csu_read_begin + bra s_cases_read_data_send + ;---------- s_case_read_data_sent + call i2csu_read_another + +s_cases_read_data_send + mov_wf SSPBUF + bs_f SSPCON1, CKP + return + +;---------- +s_case_read_data_nack + rcall s_ensure_idle + goto i2csu_read_done -s_caseshare_write_alliswell +s_cases_write_alliswell - bt_f_if1 t, I2C_START + bt_f_if1 ssp, I2C_START bra si_if_start si_if_notstart ; So it should be stop - mov_fw t + mov_fw ssp and_lw 0xdf ; ?D_A xor_lw 0x90 ; SMP, !CKE, P; !S, !R_W, !UA, !BF bra_nz si_if_bad si_if_start - bt_f_if1 t, BF + bt_f_if1 ssp, BF bra si_if_bufferfull si_if_bufferempty - bt_f_if1 t, R_W ;read? + bt_f_if1 ssp, R_W ;read? bra si_if_bufferempty_reading si_if_bufferempty_notreading ; So we think this is just a START (which we want to ignore) - mov_fw t + mov_fw ssp and_lw 0xdf ; ?D_A xor_lw 0x88 ; SMP, !CKE, !P; S, !R_W, !UA, !BF bra_nz si_if_bad @@ -194,7 +221,7 @@ s_case_got_write_addr and_lw 0xfe bra_nz nonzero - mov_wf t + mov_wf ssp mov_fw SSPSTAT -- 2.30.2