Hi All. I've hacked together a bit of flashing code across JTAG on ARM920T - very simple stuff using a semaphore to indicate a service request. It all seems to work seamlessly ( at least for the copy code ), and it resumes execution properly after each block of data. Unfortunately, once it leaves the "copy" code I hit a snag : PC becomes corrupt. I'm currently thinking I've mucked up the instruction count for the final PC fixup, and that I'm off by one or two which means in more complex code ( ie : not the semaphore polling code )I've a higher chance of executing code out of sequence. //Halt code /* STR r0, [r0] - Save R0 before use */ Data[0] = 0xe5800000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); /* STR r1, [r0] - Save R1 before use */ Data[0] = 0xe5801000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); /* STR r2, [r0] - Save R2 before use */ Data[0] = 0xe5802000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); /* MOV r0, PC - Copy PC to R0 */ Data[0] = 0xe1a0000f; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); regs->r[0]=Data[1]; //Read out R0 /* STR r0, [r0] - Save PC into R0 */ Data[0] = 0xe5800000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); regs->r[1]=Data[1]; //Read out R1 /* NOP - Read out R2 */ Data[0] = 0xe1a00000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); regs->r[2]=Data[1]; //Read out R2 /* NOP */ Data[0] = 0xe1a00000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); /* NOP - Read out R1 */ Data[0] = 0xe1a00000; Data[1] = 0x00; debug_exec(Data, DEBUG_SPEED); regs->pc=Data[1]-0xXX; //Read out PC //Halt Code Ends //Resume Code /* LDR r2, [r0] - restore R2 */ Data[0] = 0xe5902000; Data[1]=0; debug_exec(Data, DEBUG_SPEED); /* LDR r1, [r0] - restore R1 */ Data[0] = 0xe5901000; Data[1]=0; debug_exec(Data, DEBUG_SPEED); /* LDR r0, [r0] */ Data[0] = 0xe5900000; Data[1]=0; debug_exec(Data, DEBUG_SPEED); /* NOP - scan in value for r2 */ Data[0] = 0xe1a00000; Data[1] = regs->r[2]; debug_exec(Data, DEBUG_SPEED); /* MOV PC, r0 - put r0 into PC */ /* - scan in value for r1 */ Data[0] = 0xe1a0f000; Data[1] = regs->r[1]; debug_exec(Data, DEBUG_SPEED); /* LDR r0, [r0] */ /* - scan in value for pc */ Data[0] = 0xe5900000; Data[1] = regs->pc; debug_exec(Data, DEBUG_SPEED); /* NOP */ Data[0] = 0xe1a00000; Data[1]=0; debug_exec(Data, DEBUG_SPEED); /* NOP */ Data[0] = 0xe1a00000; Data[1]=0; debug_exec(Data, DEBUG_SPEED); /* NOP - scan in value for r0 */ Data[0] = 0xe1a00000; Data[1] = regs->r[0]; debug_exec(Data, DEBUG_SPEED); /* SUB PC, PC, #0xXX - jump back PC */ Data[0] = 0xe24ff0XX; Data[1]=0; debug_exec(Data, DEBUG_SPEED); Data[0] = 0xe1a00000; Data[1]=0; debug_exec(Data, SYSTEM_SPEED); //Resume Code Ends. The code I'm injecting into the cache only ever affects R0-R2, and PC. So : My question is - what are the two vlues of 0xXX above ? in the Halt code section, does the count start with "MOV r0, PC" , or 4 execs later, with the value of R0 being read ? I _think_ its the former, and the fixup is 0x20. More confusingly , in the resume secion - where do you start counting the instructions from : "MOV PC, r0" , or again 4 exec later, with the data being loaded in ? Any suggestions/corrections gratefully recieved. J
JTAG pause and resume ?
Started by ●January 3, 2007
Reply by ●January 3, 20072007-01-03