SETWATCH1 = 0xa2
CHAIN0 = 0xa3
+
+MSB = 0
+LSB = 1
+NOEND = 2
+NORETIDLE = 4
+
PM_usr = 0b10000
PM_fiq = 0b10001
PM_irq = 0b10010
return (self.data)
def ARM_nop(self, bkpt):
return self.ARMdebuginstr(ARM_INSTR_NOP, bkpt)
- def ARMset_IR(self, IR, RETIDLE=1):
- self.writecmd(0x13,SET_IR,2, [IR, RETIDLE])
+ def ARMset_IR(self, IR, noretidle=0):
+ self.writecmd(0x13,SET_IR,2, [IR, LSB|noretidle])
return self.data
- def ARMshiftDR(self, data, bits, LSB, END, RETIDLE):
- self.writecmd(0x13,SHIFT_DR,8,[bits&0xff, LSB&0xff, END&0xff, RETIDLE&0xff, data&0xff,(data>>8)&0xff,(data>>16)&0xff,(data>>24)&0xff])
+ def ARMshiftDR(self, data, bits, flags):
+ self.writecmd(0x13,SHIFT_DR,8,[bits&0xff, flags&0xff, 0, 0, data&0xff,(data>>8)&0xff,(data>>16)&0xff,(data>>24)&0xff])
return self.data
def ARMwaitDBG(self, timeout=0xff):
self.writecmd(0x13,WAIT_DBG,2,[timeout&0xf,timeout>>8])
msdelay(100);
}
+/************************** JTAG Primitives ****************************/
+// these have been turned into functions to save flash space
+void jtag_tcktock() {
+ //delay(1); // FIXME: Should never wait this long...
+ CLRTCK;
+ PLEDOUT^=PLEDPIN;
+ //delay(1); // FIXME: Should never wait this long...
+ SETTCK;
+ PLEDOUT^=PLEDPIN;
+}
+
+void jtag_goto_shift_ir() {
+ SETTMS;
+ jtag_tcktock();
+ jtag_tcktock();
+ CLRTMS;
+ jtag_tcktock();
+ jtag_tcktock();
+
+}
+void jtag_goto_shift_dr() {
+ SETTMS;
+ jtag_tcktock();
+ CLRTMS;
+ jtag_tcktock();
+ jtag_tcktock();
+}
+
+void jtag_reset_to_runtest_idle() {
+ SETTMS;
+ jtag_tcktock();
+ jtag_tcktock();
+ jtag_tcktock();
+ jtag_tcktock();
+ jtag_tcktock(); // now in Reset state
+ CLRTMS;
+ jtag_tcktock(); // now in Run-Test/Idle state
+}
+
+
int savedtclk=0;
+// NOTE: important: THIS MODULE REVOLVES AROUND RETURNING TO RUNTEST/IDLE, OR THE FUNCTIONAL EQUIVALENT
+//! Shift N bits over TDI/TDO. May choose LSB or MSB, and select whether to terminate (TMS-high on last bit) and whether to return to RUNTEST/IDLE
+// flags should be 0 for most uses.
+// for the extreme case, flags should be (NOEND|NORETDLE|LSB)
+// other edge cases can involve a combination of those three flags
+//
+// the max bit-size that can be be shifted is 32-bits.
+// for longer shifts, use the NOEND flag (which infers NORETIDLE so the additional flag is unnecessary)
+//
+// NORETIDLE is used for special cases where (as with arm) the debug subsystem does not want to
+// return to the RUN-TEST/IDLE state between setting IR and DR
+unsigned long jtagtransn(unsigned long word, unsigned char bitcount, unsigned char flags){
+ unsigned char bit;
+ unsigned long high = 1L;
+ unsigned long mask;
+
+ //for (bit=(bitcount-1)/8; bit>0; bit--)
+ // high <<= 8;
+ //high <<= ((bitcount-1)%8);
+ high <<= (bitcount-1);
+
+ mask = high-1;
+
+ SAVETCLK;
+ if (flags & LSB) {
+ for (bit = bitcount; bit > 0; bit--) {
+ /* write MOSI on trailing edge of previous clock */
+ if (word & 1)
+ {SETMOSI;}
+ else
+ {CLRMOSI;}
+ word >>= 1;
+
+ if (bit==1 && !(flags & NOEND))
+ SETTMS;//TMS high on last bit to exit.
+
+ jtag_tcktock();
+
+ /* read MISO on trailing edge */
+ if (READMISO){
+ word += (high);
+ }
+ }
+ } else {
+ for (bit = bitcount; bit > 0; bit--) {
+ /* write MOSI on trailing edge of previous clock */
+ if (word & high)
+ {SETMOSI;}
+ else
+ {CLRMOSI;}
+ word = (word & mask) << 1;
+
+ if (bit==1 && !(flags & NOEND))
+ SETTMS;//TMS high on last bit to exit.
+
+ jtag_tcktock();
+
+ /* read MISO on trailing edge */
+ word |= (READMISO);
+ }
+ }
+
+
+ RESTORETCLK;
+ //SETMOSI;
+
+ if (!(flags & NOEND)){
+ // exit state
+ jtag_tcktock();
+ // update state
+ if (!(flags & NORETIDLE)){
+ CLRTMS;
+ jtag_tcktock();
+ }
+ }
+ return word;
+}
+
//! Shift 8 bits in and out.
unsigned char jtagtrans8(unsigned char byte){
unsigned int bit;
}
//! Shift n bits in and out.
-unsigned long jtagtransn(unsigned long word,
+/*unsigned long jtagtransn(unsigned long word,
unsigned int bitcount){
unsigned int bit;
//0x8000
SAVETCLK;
for (bit = 0; bit < bitcount; bit++) {
- /* write MOSI on trailing edge of previous clock */
+ //* write MOSI on trailing edge of previous clock *
if (word & high)
{SETMOSI;}
else
SETTMS;//TMS high on last bit to exit.
TCKTOCK;
- /* read MISO on trailing edge */
+ //* read MISO on trailing edge *
word |= READMISO;
}
return word;
}
-
+*/
//! Stop JTAG, release pins
void jtag_stop(){
TCKTOCK;
// shift DR, then idle
- return(jtagtransn(in,20));
+ return(jtagtransn(in,20,0));
}
TCKTOCK;
// shift DR, then idle
- return(jtagtransn(in,16));
+ return(jtagtransn(in,16,0));
}
//! Shift native width of the DR
TCKTOCK;
- out=jtagtransn(in,drwidth);
+ out=jtagtransn(in,drwidth,0);
// shift DR, then idle
return(out);
-/************************** JTAGARM7TDMI Primitives ****************************/
-void jtag_goto_shift_ir() {
- SETTMS;
- jtag_arm_tcktock();
- jtag_arm_tcktock();
- CLRTMS;
- jtag_arm_tcktock();
- jtag_arm_tcktock();
-
-}
-void jtag_goto_shift_dr() {
- SETTMS;
- jtag_arm_tcktock();
- CLRTMS;
- jtag_arm_tcktock();
- jtag_arm_tcktock();
-}
-
-void jtag_reset_to_runtest_idle() {
- SETTMS;
- jtag_arm_tcktock();
- jtag_arm_tcktock();
- jtag_arm_tcktock();
- jtag_arm_tcktock();
- jtag_arm_tcktock(); // now in Reset state
- CLRTMS;
- jtag_arm_tcktock(); // now in Run-Test/Idle state
-}
-
-void jtag_arm_tcktock() {
- delay(1); // FIXME: Should never wait this long...
- CLRTCK;
- PLEDOUT^=PLEDPIN;
- delay(1); // FIXME: Should never wait this long...
- SETTCK;
- PLEDOUT^=PLEDPIN;
-}
-
// ! Start JTAG, setup pins, reset TAP and return IDCODE
unsigned long jtagarm7tdmi_start() {
// NOTE: important: THIS MODULE REVOLVES AROUND RETURNING TO RUNTEST/IDLE, OR THE FUNCTIONAL EQUIVALENT
-
+/*
//! Shift N bits over TDI/TDO. May choose LSB or MSB, and select whether to terminate (TMS-high on last bit) and whether to return to RUNTEST/IDLE
unsigned long jtagarmtransn(unsigned long word, unsigned char bitcount, unsigned char lsb, unsigned char end, unsigned char retidle){ // PROVEN
unsigned char bit;
mask = high-1;
+ SAVETCLK;
if (lsb) {
for (bit = bitcount; bit > 0; bit--) {
- /* write MOSI on trailing edge of previous clock */
+ /* write MOSI on trailing edge of previous clock *
if (word & 1)
{SETMOSI;}
else
jtag_arm_tcktock();
- /* read MISO on trailing edge */
+ //* read MISO on trailing edge *
if (READMISO){
word += (high);
}
}
} else {
for (bit = bitcount; bit > 0; bit--) {
- /* write MOSI on trailing edge of previous clock */
+ //* write MOSI on trailing edge of previous clock *
if (word & high)
{SETMOSI;}
else
jtag_arm_tcktock();
- /* read MISO on trailing edge */
+ //* read MISO on trailing edge *
word |= (READMISO);
}
}
- SETMOSI;
+ RESTORETCLK;
+ //SETMOSI;
if (end){
// exit state
}
return word;
}
-
+*/
/************************************************************************
unsigned long jtagarm7tdmi_idcode(){ // PROVEN
jtagarm7tdmi_resettap();
jtag_goto_shift_ir();
- jtagarmtransn(ARM7TDMI_IR_IDCODE, 4, LSB, END, RETIDLE);
+ jtagtransn(ARM7TDMI_IR_IDCODE, 4, LSB);
jtag_goto_shift_dr();
- return jtagarmtransn(0,32, LSB, END, RETIDLE);
+ return jtagtransn(0,32, LSB);
}
//! Connect Bypass Register to TDO/TDI
unsigned long jtagarm7tdmi_restart() {
unsigned long retval;
jtag_goto_shift_ir();
- retval = jtagarmtransn(ARM7TDMI_IR_RESTART, 4, LSB, END, RETIDLE);
+ retval = jtagtransn(ARM7TDMI_IR_RESTART, 4, LSB);
current_chain = -1;
//jtagarm7tdmi_resettap();
return retval;
//if (current_chain != chain) {
// //debugstr("===change chains===");
jtag_goto_shift_ir();
- jtagarmtransn(ARM7TDMI_IR_SCAN_N, 4, LSB, END, NORETIDLE);
+ jtagtransn(ARM7TDMI_IR_SCAN_N, 4, LSB | NORETIDLE);
jtag_goto_shift_dr();
- retval = jtagarmtransn(chain, 4, LSB, END, NORETIDLE);
+ retval = jtagtransn(chain, 4, LSB | NORETIDLE);
// put in test mode...
//jtag_goto_shift_ir();
//jtagarmtransn(testmode, 4, LSB, END, RETIDLE);
//}
// put in test mode...
jtag_goto_shift_ir();
- jtagarmtransn(testmode, 4, LSB, END, RETIDLE);
+ jtagtransn(testmode, 4, LSB);
return(retval);
}
CLRMOSI;
count_dbgspd_instr_since_debug++;
}
- jtag_arm_tcktock();
+ jtag_tcktock();
// Now shift in the 32 bits
- retval = jtagarmtransn(instr, 32, MSB, END, RETIDLE); // Must return to RUN-TEST/IDLE state for instruction to enter pipeline, and causes debug clock.
+ retval = jtagtransn(instr, 32, 0); // Must return to RUN-TEST/IDLE state for instruction to enter pipeline, and causes debug clock.
return(retval);
}
jtagarm7tdmi_scan_intest(2);
// Now shift in the 32 bits
jtag_goto_shift_dr();
- retval = jtagarmtransn(data, 32, LSB, NOEND, NORETIDLE); // send in the data - 32-bits lsb
- temp = jtagarmtransn(reg, 5, LSB, NOEND, NORETIDLE); // send in the register address - 5 bits lsb
- jtagarmtransn(1, 1, LSB, END, RETIDLE); // send in the WRITE bit
+ retval = jtagtransn(data, 32, LSB| NOEND| NORETIDLE); // send in the data - 32-bits lsb
+ temp = jtagtransn(reg, 5, LSB| NOEND| NORETIDLE); // send in the register address - 5 bits lsb
+ jtagtransn(1, 1, LSB); // send in the WRITE bit
return(retval);
}
// send in the register address - 5 bits LSB
jtag_goto_shift_dr();
- temp = jtagarmtransn(reg, 5, LSB, NOEND, NORETIDLE);
+ temp = jtagtransn(reg, 5, LSB| NOEND| NORETIDLE);
// clear TDI to select "read only"
- jtagarmtransn(0L, 1, LSB, END, RETIDLE);
+ jtagtransn(0L, 1, LSB);
jtag_goto_shift_dr();
// Now shift out the 32 bits
- retval = jtagarmtransn(0L, 32, LSB, END, RETIDLE); // atmel arm jtag docs pp.10-11: LSB first
+ retval = jtagtransn(0L, 32, LSB); // atmel arm jtag docs pp.10-11: LSB first
//debughex32(retval);
return(retval); // atmel arm jtag docs pp.10-11: LSB first
case JTAGARM7TDMI_SET_IR:
//jtagarm7tdmi_resettap();
jtag_goto_shift_ir();
- cmddataword[0] = jtagarmtransn(cmddata[0], 4, LSB, END, cmddata[1]);
+ cmddataword[0] = jtagtransn(cmddata[0], 4, cmddata[1]);
current_chain = -1;
txdata(app,verb,2);
break;
case JTAGARM7TDMI_SHIFT_DR:
jtagarm7tdmi_resettap();
jtag_goto_shift_dr();
- cmddatalong[0] = jtagarmtransn(cmddatalong[1],cmddata[0],cmddata[1],cmddata[2],cmddata[3]);
+ cmddatalong[0] = jtagtransn(cmddatalong[1],cmddata[0],cmddata[1]);
txdata(app,verb,4);
break;
case JTAGARM7TDMI_CHAIN0:
debughex(cmddataword[4]);
debughex32(cmddatalong[1]);
debughex32(cmddatalong[3]);
- cmddatalong[0] = jtagarmtransn(cmddatalong[0], 32, LSB, NOEND, NORETIDLE);
- cmddatalong[2] = jtagarmtransn(cmddataword[4], 9, MSB, NOEND, NORETIDLE);
- cmddatalong[1] = jtagarmtransn(cmddatalong[1], 32, MSB, NOEND, NORETIDLE);
- cmddatalong[3] = jtagarmtransn(cmddatalong[3], 32, MSB, END, RETIDLE);
+ cmddatalong[0] = jtagtransn(cmddatalong[0], 32, LSB| NOEND| NORETIDLE);
+ cmddatalong[2] = jtagtransn(cmddataword[4], 9, MSB| NOEND| NORETIDLE);
+ cmddatalong[1] = jtagtransn(cmddatalong[1], 32, MSB| NOEND| NORETIDLE);
+ cmddatalong[3] = jtagtransn(cmddatalong[3], 32, MSB);
txdata(app,verb,16);
break;
case JTAGARM7TDMI_SETWATCH0: