; TMS is bit 1 #def tms_1 = b010; #def tms_0 = b101; ; TCK is bit 0 #def tck_1 = b001; #def tck_0 = b110; ; TDI is bit 2 #def tdi_1 = b100; #def tdi_0 = b011; ; TDO is bit 2 #def tdo_msk = b100; #def tdo_pos = -2; #def tdi_off = b011; #def j2c_timed = 10; ;#def MaxLoop = 0xFFF ;#def looptest = 1; #def oportd = r15; #def j2c_wrk = r0; #def return1 = r8; #def return2 = r7; #def return3 = r6; #def dat2send = r2; #def bit2send = r3; #def rec_data = r4; tst: #ifdef looptest mov MaxLoop, r12 shl 8, r12, r12 mov 0, r14 ; error counter j2c_loop: mov b1000, r11 mov 0xFF, r13 and r12, r13, r13 ; only to see the LEDs ; mov 0x80, j2c_wrk ; or j2c_wrk, r13, r13 shl 4, r13, r13 or r11, r13, r11 ; data to send sgio r11, 0x0C03 jmpr cc_busy, 0 ; start, write mvpcr +2, return1 jmp cc_uncond, j2c_cmd mov b0100, r11 sgio r11, 0x0C03 jmpr cc_busy, 0 ; start, read mvpcr +2, return1 jmp cc_uncond, j2c_cmd shl -4, r13, r13 cmp r13, rec_data jmpr cc_eq, +2 add r14, c1, r14 ; delay just to see the LEDs ; mov 0xFFF, j2c_wrk ; shl 4, j2c_wrk, j2c_wrk ; sub j2c_wrk, c1, j2c_wrk ; jmpr cc_nzero, -1 sub r12, c1, r12 jmp cc_nzero, j2c_loop ; sgio r14, 0x0C03 ; the address of c11 in GIO iext srv_outdata ; the address in GIO sgio r14, srv_outdata ; the address in GIO jmpr cc_busy, 0 #else mvpcr +2, return1 jmp cc_uncond, j2c_cmd #endif ; low power mov CMD_LP, j2c_wrk sgio j2c_wrk, SMCMD jmpr cc_uncond, 0 nop j2c_cmd: ; INIT mov tms_1, oportd iext SEBDOU sgio oportd, SEBDOU ; TCK=0, TMS=1, TDI=0 mov 7, j2c_wrk ; all enabled jmpr cc_busy, 0 iext SEBDEN sgio j2c_wrk, SEBDEN ; copy the command & data iext srv_command lgio 0, srv_command jmpr cc_busy, 0 lpio 0x300, dat2send ; send the command mov 4, bit2send ; 4 bits to send mvpcr +2, return2 ; return address jmp cc_uncond, j2c_sendd ; send 4 bits of dat2send ; set TDI high mvpcr +2, return3 jmp cc_uncond, j2c_set_tdi ; TDI=1 mvpcr +2, return2 ; return address jmp cc_uncond, j2c_tmsp ; tms pulse ; send/receive data mov 8, bit2send ; 8 bits to send mvpcr +2, return2 ; return address jmp cc_uncond, j2c_sendd ; send 8 bits of dat2send ; enable the data output, TDI=0 and make a pulse at TMS ; set TDI low mvpcr +2, return3 jmp cc_uncond, j2c_clr_tdi ; TDI=0 mvpcr +2, return2 ; return address jmp cc_uncond, j2c_tmsp ; tms pulse ; store the result back jmpr cc_busy, 0 iext srv_outdata sgio rec_data, srv_outdata jmpr cc_busy, 0 jmp cc_uncond, return1 nop ; send a bitstream using TCK and TDI and receive the data from TDI ; ; The slave pulls TDI low only when TCK=1 and its output data is 0 ; ; The master pulls TDI low before the rising edge of TCK if its output data is 0 ; ; The master stores the TDI before the falling edge of TCK ; ; data to be sent : dat2send ; bits to be sent : bit2send ; received data : rec_data ; ; Data are sent LSB first, 4 bit command and 8 bit data j2c_sendd: mvpcr +2, return3 jmp cc_uncond, j2c_ena_tdi mvpcr +4, return3 shl -1, dat2send, dat2send jmp cc_carry, j2c_set_tdi jmp cc_uncond, j2c_clr_tdi mvpcr +2, return3 jmp cc_uncond, j2c_delay ; rising edge of TCK -- TDI must be active, not open drain! ; TDO in simulation must be weak pull up/down! -- not directly attached to TDI! mvpcr +2, return3 jmp cc_uncond, j2c_set_tck mvpcr +2, return3 jmp cc_uncond, j2c_dis_tdi mvpcr +2, return3 jmp cc_uncond, j2c_delay iext SEBDIN ; read the TDI lgio 0, SEBDIN jmpr cc_busy, 0 lpio 0x300, j2c_wrk ; mov tdo_msk, r4 ; and r4, j2c_wrk, j2c_wrk #ifdef tdo_pos shl tdo_pos, j2c_wrk, j2c_wrk #endif and j2c_wrk, c1, j2c_wrk shl 7, j2c_wrk, j2c_wrk ; now the received data is bit 7 shl -1, rec_data, rec_data ; shift right the serial register or j2c_wrk, rec_data, rec_data ; put the new input data as bit 7 ; falling edge of TCK mvpcr +2, return3 jmp cc_uncond, j2c_clr_tck sub bit2send, c1, bit2send ; dec the bit counter jmp cc_nzero, j2c_sendd ; loop mvpcr +2, return3 jmp cc_uncond, j2c_ena_tdi jmp cc_uncond, return2 ; return ; make a negative strobe pulse at TMS ; return address in return2 j2c_tmsp: ; falling edge of TCK mvpcr +2, return3 jmp cc_uncond, j2c_clr_tms mvpcr +2, return3 jmp cc_uncond, j2c_delay mvpcr +2, return3 jmp cc_uncond, j2c_set_tms jmp cc_uncond, return2 ; return j2c_delay: mov j2c_timed, j2c_wrk sub j2c_wrk, c1, j2c_wrk jmpr cc_nzero, -1 jmp cc_uncond, return3 j2c_set_tck: mov tck_1, j2c_wrk jmp cc_uncond, j2c_set_ttt j2c_clr_tck: mov tck_0, j2c_wrk jmp cc_uncond, j2c_clr_ttt j2c_set_tms: mov tms_1, j2c_wrk jmp cc_uncond, j2c_set_ttt j2c_clr_tms: mov tms_0, j2c_wrk jmp cc_uncond, j2c_clr_ttt j2c_set_tdi: mov tdi_1, j2c_wrk jmp cc_uncond, j2c_set_ttt j2c_clr_tdi: mov tdi_0, j2c_wrk jmp cc_uncond, j2c_clr_ttt j2c_set_ttt: or oportd, j2c_wrk, oportd iext SEBDOU sgio oportd, SEBDOU jmpr cc_busy, 0 jmp cc_uncond, return3 ; return j2c_clr_ttt: and oportd, j2c_wrk, oportd iext SEBDOU sgio oportd, SEBDOU jmpr cc_busy, 0 jmp cc_uncond, return3 ; return j2c_ena_tdi: mov 7, j2c_wrk iext SEBDEN sgio j2c_wrk, SEBDEN jmpr cc_busy, 0 jmp cc_uncond, return3 ; return j2c_dis_tdi: mov tdi_off, j2c_wrk iext SEBDEN sgio j2c_wrk, SEBDEN jmpr cc_busy, 0 jmp cc_uncond, return3 ; return nop