JTAGfunc430.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2016 Texas Instruments Incorporated - http://www.ti.com/
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * Redistributions of source code must retain the above copyright
9  * notice, this list of conditions and the following disclaimer.
10  *
11  * Redistributions in binary form must reproduce the above copyright
12  * notice, this list of conditions and the following disclaimer in the
13  * documentation and/or other materials provided with the
14  * distribution.
15  *
16  * Neither the name of Texas Instruments Incorporated nor the names of
17  * its contributors may be used to endorse or promote products derived
18  * from this software without specific prior written permission.
19  *
20  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
21  * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
23  * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
24  * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
25  * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
26  * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
27  * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
28  * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
29  * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
30  * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
31  *
32 */
33 /*==========================================================================*\
34 | |
35 | JTAGfunc430.c |
36 | |
37 | JTAG Control Sequences for Erasing / Programming / Fuse Burning |
38 |----------------------------------------------------------------------------|
39 | Project: JTAG Functions |
40 | Developed using: IAR Embedded Workbench 6.20 |
41 | and: Code Composer Eessentials 6.0 |
42 |----------------------------------------------------------------------------|
43 | Version history: |
44 | 1.0 04/02 FRGR Initial version. |
45 | 1.1 04/02 ALB2 Formatting changes, added comments. |
46 | 1.2 08/02 ALB2 Initial code release with Lit# SLAA149. |
47 | 1.3 09/05 JDI 'ResetTAP': added SetTDI for fuse check |
48 | search for F2xxx to find respective modifications in |
49 | 'SetPC', 'HaltCPU', 'VerifyPSA', 'EraseFLASH' |
50 | 'WriteFLASH' |
51 | SUN1 Software delays redesigned to use TimerA harware; |
52 | see MsDelay() routine. |
53 | 1.4 01/06 STO Added entry sequence for SpyBiWire devices |
54 | Minor cosmetic changes |
55 | 1.5 03/06 STO BlowFuse() make correct fuse check after blowing. |
56 | 1.6 07/06 STO Loop in WriteFLASH() changed. |
57 | 1.7 04/06 WLUT 'VerifyPSA', 'ReadMemQuick' changed to TCLK high. |
58 | JTAG4 sequence changed according to figure 10 in |
59 | Lit# SLAA149. |
60 | WriteFLASHallSections changed due to spec of srec_cat|
61 | Renamed 'ExecutePUC' to 'ExecutePOR'. |
62 | 1.8 01/08 WLUT Added usDelay(5) in ResetTAP() to ensure at least |
63 | 5us low phase of TMS during JTAG fuse check. |
64 | 1.9 08/08 WLUT Added StartJtag() and StopJtag() for a clean init |
65 | sequence. |
66 | 2.0 07/09 FB Added support for Spy-Bi-Wire and new replecator |
67 | 2.1 06/12 RL/GC (Elprotronic) Updated commentaries/Added Fuse Blow via SBW |
68 | 2.2 03/13 RL/MD Added unlock function for Info A |
69 | 2.3 07/13 RL Fixed unlock function for Info A |
70 | 2.4 02/14 RL Fixed flow in SetPC() |
71 | 2.5 04/02 RL Updated SBW entry sequence to support i2040 |
72 |----------------------------------------------------------------------------|
73 | Designed 2002 by Texas Instruments Germany |
74 \*==========================================================================*/
77 /****************************************************************************/
78 /* INCLUDES */
79 /****************************************************************************/
80 
81 #include "JTAGfunc430.h"
82 #include "LowLevelFunc430.h"
83 #include "Devices430.h"
84 
85 /****************************************************************************/
86 /* Low level routines for accessing the target device via JTAG: */
87 /****************************************************************************/
88 
89 //----------------------------------------------------------------------------
94 word DR_Shift16(word data)
95 {
96 #ifdef SPYBIWIRE_MODE
97 
98  // JTAG FSM state = Run-Test/Idle
99  if (TCLK_saved & SBWDATO)
100  {
101  TMSH_TDIH();
102  }
103  else
104  {
105  TMSH_TDIL();
106  }
107  // JTAG FSM state = Select DR-Scan
108  TMSL_TDIH();
109  // JTAG FSM state = Capture-DR
110  TMSL_TDIH();
111 #else
112  // JTAG FSM state = Run-Test/Idle
113  SetTMS();
114  ClrTCK();
115  SetTCK();
116 
117  // JTAG FSM state = Select DR-Scan
118  ClrTMS();
119  ClrTCK();
120  SetTCK();
121  // JTAG FSM state = Capture-DR
122  ClrTCK();
123  SetTCK();
124 #endif
125  // JTAG FSM state = Shift-DR, Shift in TDI (16-bit)
126  return(Shift(F_WORD, data));
127  // JTAG FSM state = Run-Test/Idle
128 
129 }
130 
131 //----------------------------------------------------------------------------
137 word IR_Shift(byte instruction)
138 {
139 #ifdef SPYBIWIRE_MODE
140  // JTAG FSM state = Run-Test/Idle
141  if (TCLK_saved & SBWDATO)
142  {
143  TMSH_TDIH();
144  }
145  else
146  {
147  TMSH_TDIL();
148  }
149  // JTAG FSM state = Select DR-Scan
150  TMSH_TDIH();
151 
152  // JTAG FSM state = Select IR-Scan
153  TMSL_TDIH();
154  // JTAG FSM state = Capture-IR
155  TMSL_TDIH();
156 #else
157  // JTAG FSM state = Run-Test/Idle
158  SetTMS();
159  ClrTCK();
160  SetTCK();
161  // JTAG FSM state = Select DR-Scan
162  ClrTCK();
163  SetTCK();
164 
165  // JTAG FSM state = Select IR-Scan
166  ClrTMS();
167  ClrTCK();
168  SetTCK();
169  // JTAG FSM state = Capture-IR
170  ClrTCK();
171  SetTCK();
172 #endif
173  // JTAG FSM state = Shift-IR, Shift in TDI (8-bit)
174  return(Shift(F_BYTE, instruction));
175  // JTAG FSM state = Run-Test/Idle
176 }
177 
178 //----------------------------------------------------------------------------
180 void ResetTAP(void)
181 {
182  word i;
183 
184 #ifdef SPYBIWIRE_MODE
185  // Reset JTAG FSM
186  for (i = 6; i > 0; i--)
187  {
188  TMSH_TDIH();
189  }
190  // JTAG FSM is in Test-Logic-Reset now
191  TMSL_TDIH();
192 
193  // JTAG FSM is in Run-Test/IDLE
194 
195  // Perform fuse check
196  TMSH_TDIH();
197  TMSL_TDIH();
198  TMSH_TDIH();
199  TMSL_TDIH();
200  TMSH_TDIH();
201  // In every TDI slot a TCK for the JTAG machine is generated.
202  // Thus we need to get TAP in Run/Test Idle state back again.
203  TMSH_TDIH();
204  TMSL_TDIH(); // now in Run/Test Idle
205 #else
206  // process TDI first to settle fuse current
207  SetTDI();
208  SetTMS();
209  SetTCK();
210 
211  // Reset JTAG FSM
212  for (i = 6; i > 0; i--)
213  {
214  ClrTCK();
215  SetTCK();
216  }
217  // JTAG FSM is now in Test-Logic-Reset
218  ClrTCK();
219  ClrTMS();
220  SetTCK();
221  SetTMS();
222  // JTAG FSM is now in Run-Test/IDLE
223 
224  // Perform fuse check
225  ClrTMS();
226  usDelay(5); // at least 5us low required
227  SetTMS();
228  ClrTMS();
229  usDelay(5); // at least 5us low required
230  SetTMS();
231 #endif
232 }
233 
234 //----------------------------------------------------------------------------
239 word ExecutePOR(void)
240 {
241  word JtagVersion;
242 
243  // Perform Reset
245  DR_Shift16(0x2C01); // Apply Reset
246  DR_Shift16(0x2401); // Remove Reset
247  ClrTCLK();
248  SetTCLK();
249  ClrTCLK();
250  SetTCLK();
251  ClrTCLK();
252  JtagVersion = IR_Shift(IR_ADDR_CAPTURE); // read JTAG ID, checked at function end
253  SetTCLK();
254 
255  WriteMem(F_WORD, 0x0120, 0x5A80); // Disable Watchdog on target device
256 
257  if (JtagVersion != JTAG_ID)
258  {
259  return(STATUS_ERROR);
260  }
261  return(STATUS_OK);
262 }
263 
264 //----------------------------------------------------------------------------
267 word SetInstrFetch(void)
268 {
269  word i;
270 
272 
273  // Wait until CPU is in instr. fetch state, timeout after limited attempts
274  for (i = 50; i > 0; i--)
275  {
276  if (DR_Shift16(0x0000) & 0x0080)
277  {
278  return(STATUS_OK);
279  }
280  ClrTCLK();
281  SetTCLK();
282  }
283  return(STATUS_ERROR);
284 }
285 
286 //----------------------------------------------------------------------------
289 void SetPC(word Addr)
290 {
291  SetInstrFetch(); // Set CPU into instruction fetch mode, TCLK=1
292 
293  // Load PC with address
295  DR_Shift16(0x3401); // CPU has control of RW & BYTE.
297  DR_Shift16(0x4030); // "mov #addr,PC" instruction
298  ClrTCLK();
299  SetTCLK(); // F2xxx
300  DR_Shift16(Addr); // "mov #addr,PC" instruction
301  ClrTCLK();
302  SetTCLK();
304  ClrTCLK(); // Now the PC should be on Addr
306  DR_Shift16(0x2401); // JTAG has control of RW & BYTE.
307 }
308 
309 //----------------------------------------------------------------------------
311 void HaltCPU(void)
312 {
313  SetInstrFetch(); // Set CPU into instruction fetch mode
314 
316  DR_Shift16(0x3FFF); // Send JMP $ instruction
317  ClrTCLK();
319  DR_Shift16(0x2409); // Set JTAG_HALT bit
320  SetTCLK();
321 }
322 
323 //----------------------------------------------------------------------------
325 void ReleaseCPU(void)
326 {
327  ClrTCLK();
329  DR_Shift16(0x2401); // Clear the HALT_JTAG bit
331  SetTCLK();
332 }
333 #ifdef SPYBIWIRE_MODE
334 //----------------------------------------------------------------------------
342 static word VerifyPSA(word StartAddr, word Length, word *DataArray)
343 {
344  word TDOword, i;
345  word POLY = 0x0805; // Polynom value for PSA calculation
346  word PSA_CRC = StartAddr-2; // Start value for PSA calculation
347 
348  ExecutePOR();
349 
350  if(DeviceHas_EnhVerify())
351  {
352  SetPC(StartAddr-4);
353  HaltCPU();
354  ClrTCLK();
356  DR_Shift16(StartAddr-2);
357  }
358  else
359  {
360  SetPC(StartAddr-2);
361  SetTCLK();
362  ClrTCLK();
363  }
365 
366  for (i = 0; i < Length; i++)
367  {
368  // Calculate the PSA (Pseudo Signature Analysis) value
369  if ((PSA_CRC & 0x8000) == 0x8000)
370  {
371  PSA_CRC ^= POLY;
372  PSA_CRC <<= 1;
373  PSA_CRC |= 0x0001;
374  }
375  else
376  {
377  PSA_CRC <<= 1;
378  }
379  // if pointer is 0 then use erase check mask, otherwise data
380  if (DataArray == 0)
381  {
382  PSA_CRC ^= 0xFFFF;
383  }
384  else
385  {
386  PSA_CRC ^= DataArray[i];
387  }
388 
389  // Clock through the PSA
390  SetTCLK();
391 
392  TMSH_TDIH();
393  TMSL_TDIH();
394  TMSL_TDIH();
395  TMSH_TDIH();
396  TMSH_TDIH();
397  TMSL_TDIH();
398 
399  ClrTCLK();
400  }
402  TDOword = DR_Shift16(0x0000); // Read out the PSA value
403  SetTCLK();
404 
405  if(DeviceHas_EnhVerify())
406  {
407  ReleaseCPU();
408  }
409 
410  ExecutePOR();
411 
412  return((TDOword == PSA_CRC) ? STATUS_OK : STATUS_ERROR);
413 }
414 #else
415 
423 word VerifyPSA(word StartAddr, word Length, word *DataArray)
424 {
425  word TDOword, i;
426  word POLY = 0x0805; // Polynom value for PSA calculation
427  word PSA_CRC = StartAddr-2; // Start value for PSA calculation
428 
429  ExecutePOR();
430 
431  if(DeviceHas_EnhVerify())
432  {
433  SetPC(StartAddr-4);
434  HaltCPU();
435  ClrTCLK();
437  DR_Shift16(StartAddr-2);
438  }
439  else
440  {
441  SetPC(StartAddr-2);
442  SetTCLK();
443  ClrTCLK();
444  }
446  for (i = 0; i < Length; i++)
447  {
448  // Calculate the PSA (Pseudo Signature Analysis) value
449  if ((PSA_CRC & 0x8000) == 0x8000)
450  {
451  PSA_CRC ^= POLY;
452  PSA_CRC <<= 1;
453  PSA_CRC |= 0x0001;
454  }
455  else
456  {
457  PSA_CRC <<= 1;
458  }
459  // if pointer is 0 then use erase check mask, otherwise data
460  &DataArray[0] == 0 ? (PSA_CRC ^= 0xFFFF) : (PSA_CRC ^= DataArray[i]);
461 
462  // Clock through the PSA
463  SetTCLK();
464 // ClrTCLK(); // set here -> Fixes problem with F123 PSA in RAM
465 
466  ClrTCK();
467 
468  SetTMS();
469  SetTCK(); // Select DR scan
470  ClrTCK();
471  ClrTMS();
472 
473  SetTCK(); // Capture DR
474  ClrTCK();
475 
476  SetTCK(); // Shift DR
477  ClrTCK();
478 
479  SetTMS();
480  SetTCK(); // Exit DR
481  ClrTCK();
482  SetTCK();
483  ClrTMS();
484  ClrTCK();
485  SetTCK();
486 
487  ClrTCLK(); // set here -> future purpose
488  }
490  TDOword = DR_Shift16(0x0000); // Read out the PSA value
491  SetTCLK();
492 
493  if(DeviceHas_EnhVerify())
494  {
495  ReleaseCPU();
496  }
497  ExecutePOR();
498  return((TDOword == PSA_CRC) ? STATUS_OK : STATUS_ERROR);
499 }
500 #endif
501 
502 /****************************************************************************/
503 /* High level routines for accessing the target device via JTAG: */
504 /* */
505 /* From the following, the user is relieved from coding anything. */
506 /* To provide better understanding and clearness, some functionality is */
507 /* coded generously. (Code and speed optimization enhancements may */
508 /* be desired) */
509 /****************************************************************************/
510 static void CheckJtagFuse_SBW(void)
511 {
512  TMSL_TDIH(); // now in Run/Test Idle
513 
514  // Fuse check
515  TMSH_TDIH();
516  TMSL_TDIH();
517  TMSH_TDIH();
518  TMSL_TDIH();
519  TMSH_TDIH();
520  // In every TDI slot a TCK for the JTAG machine is generated.
521  // Thus we need to get TAP in Run/Test Idle state back again.
522  TMSH_TDIH();
523  TMSL_TDIH();
524 }
525 
526 static void CheckJtagFuse_JTAG(void)
527 {
528  // perform a JTAG fuse check
529  SetTMS();_NOP();_NOP();_NOP();
530  ClrTMS();_NOP();_NOP();_NOP();
531  usDelay(15);
532  SetTMS();_NOP();_NOP();_NOP();
533  ClrTMS();_NOP();_NOP();_NOP();
534  usDelay(15);
535  SetTMS();_NOP();_NOP();_NOP();
536 }
537 
540 static void EntrySequences_RstHigh_SBW()
541 {
542  ClrSBWTCK(); //1
543  MsDelay(4); // reset TEST logic
544 
545  SetSBWTDIO(); //2
546 
547  SetSBWTCK(); //3
548  MsDelay(20); // activate TEST logic
549 
550  // phase 1
551  SetSBWTDIO(); //4
552  usDelay(60);
553 
554  // phase 2 -> TEST pin to 0, no change on RST pin
555  // for Spy-Bi-Wire
556  _DINT();
557  //(*_Jtag.Out) &= ~_Jtag.TST; //5
558  ClrSBWTCK();
559 
560  // phase 3
561  usDelay(1);
562  // phase 4 -> TEST pin to 1, no change on RST pin
563  // for Spy-Bi-Wire
564  //(*_Jtag.Out) |= _Jtag.TST; //7
565  SetSBWTCK();
566  _EINT();
567  //_EINT_FET();
568  usDelay(60);
569 
570  // phase 5
571  MsDelay(5);
572 }
573 
576 static void EntrySequences_RstHigh_JTAG()
577 {
578  ClrTST(); //1
579  MsDelay(4); // reset TEST logic
580 
581  SetRST(); //2
582 
583  SetTST(); //3
584  MsDelay(20); // activate TEST logic
585 
586  // phase 1
587  ClrRST(); //4
588  usDelay(60);
589 
590  // phase 2 -> TEST pin to 0, no change on RST pin
591  // for 4-wire JTAG clear Test pin
592  ClrTST(); //5
593 
594  // phase 3
595  usDelay(1);
596 
597  // phase 4 -> TEST pin to 1, no change on RST pin
598  // for 4-wire JTAG
599  SetTST();//7
600  usDelay(60);
601 
602  // phase 5
603  SetRST();
604  MsDelay(5);
605 }
606 
607 //----------------------------------------------------------------------------
609 static word StartJtag(void)
610 {
611  // drive JTAG/TEST signals
612  DrvSignals();
613  MsDelay(10); // delay 10ms
614 
615  if(INTERFACE == SPYBIWIRE_IF)
616  {
617  EntrySequences_RstHigh_SBW();
618  }
619  else if(INTERFACE == SPYBIWIREJTAG_IF)
620  {
621  EntrySequences_RstHigh_JTAG();
622  }
623  else // JTAG_IF
624  {
625  SetRST();
626  SetTST();
627  }
628 
629  ResetTAP(); // reset TAP state machine -> Run-Test/Idle
630 
631  if(INTERFACE == SPYBIWIRE_IF)
632  {
633  CheckJtagFuse_SBW();
634  }
635  else
636  {
637  CheckJtagFuse_JTAG();
638  }
639  return IR_Shift(IR_BYPASS);
640 }
641 
642 //----------------------------------------------------------------------------
644 static void StopJtag (void)
645 {
646  // release JTAG/TEST signals
647  {
648  RlsSignals();
649  MsDelay(10); // delay 10ms
650  }
651 }
652 
653 //----------------------------------------------------------------------------
659 word GetDevice(void)
660 {
661  word JtagId = 0; // initialize JtagId with an invalid value
662  word i;
663  for (i = 0; i < MAX_ENTRY_TRY; i++)
664  {
665 
666  StopJtag(); // release JTAG/TEST signals to savely reset the test logic
667  JtagId = StartJtag(); // establish the physical connection to the JTAG interface
668  if(JtagId == JTAG_ID) // break if a valid JTAG ID is being returned
669  {
670  break;
671  }
672  }
673  if(i >= MAX_ENTRY_TRY)
674  {
675  return(STATUS_ERROR);
676  }
677 
678  if (IsFuseBlown()) // Stop here if fuse is already blown
679  {
680  return(STATUS_FUSEBLOWN);
681  }
683  DR_Shift16(0x2401); // Set device into JTAG mode + read
685  {
686  return(STATUS_ERROR);
687  }
688 
689  // Wait until CPU is synchronized, timeout after a limited # of attempts
690  for (i = 50; i > 0; i--)
691  {
692  if (DR_Shift16(0x0000) & 0x0200)
693  {
694  word DeviceId;
695  DeviceId = ReadMem(F_WORD, 0x0FF0);// Get target device type
696  //(bytes are interchanged)
697  DeviceId = (DeviceId << 8) + (DeviceId >> 8); // swop bytes
698  //Set Device index, which is used by functions in Device.c
699  SetDevice(DeviceId);
700  break;
701  }
702  else
703  {
704  if (i == 1)
705  {
706  return(STATUS_ERROR); // Timeout reached, return false
707  }
708  }
709  }
710  if (!ExecutePOR()) // Perform PUC, Includes
711  {
712  return(STATUS_ERROR); // target Watchdog disable.
713  }
714  return(STATUS_OK);
715 }
716 
717 //----------------------------------------------------------------------------
721 void ReleaseDevice(word Addr)
722 {
723  if (Addr == V_RESET)
724  {
726  DR_Shift16(0x2C01); // Perform a reset
727  DR_Shift16(0x2401);
728  }
729  else
730  {
731  SetPC(Addr); // Set target CPU's PC
732  }
734 }
735 
736 //----------------------------------------------------------------------------
741 void WriteMem(word Format, word Addr, word Data)
742 {
743  HaltCPU();
744 
745  ClrTCLK();
747  if (Format == F_WORD)
748  {
749  DR_Shift16(0x2408); // Set word write
750  }
751  else
752  {
753  DR_Shift16(0x2418); // Set byte write
754  }
756  DR_Shift16(Addr); // Set addr
758  DR_Shift16(Data); // Shift in 16 bits
759  SetTCLK();
760 
761  ReleaseCPU();
762 }
763 
764 //----------------------------------------------------------------------------
769 void WriteMemQuick(word StartAddr, word Length, word *DataArray)
770 {
771  word i;
772 
773  // Initialize writing:
774  SetPC((word)(StartAddr-4));
775  HaltCPU();
776 
777  ClrTCLK();
779  DR_Shift16(0x2408); // Set RW to write
781  for (i = 0; i < Length; i++)
782  {
783  DR_Shift16(DataArray[i]); // Shift in the write data
784  SetTCLK();
785  ClrTCLK(); // Increment PC by 2
786  }
787  ReleaseCPU();
788 }
789 
790 #ifdef SPYBIWIRE_MODE
791 //----------------------------------------------------------------------------
797 void WriteFLASH(word StartAddr, word Length, word *DataArray)
798 {
799  word i; // Loop counter
800  word addr = StartAddr; // Address counter
801  word FCTL3_val = SegmentInfoAKey; // SegmentInfoAKey holds Lock-Key for Info
802  // Seg. A
803 
804  HaltCPU();
805 
806  ClrTCLK();
808  DR_Shift16(0x2408); // Set RW to write
810  DR_Shift16(0x0128); // FCTL1 register
812  DR_Shift16(0xA540); // Enable FLASH write
813  SetTCLK();
814 
815  ClrTCLK();
817  DR_Shift16(0x012A); // FCTL2 register
819  DR_Shift16(0xA540); // Select MCLK as source, DIV=1
820  SetTCLK();
821 
822  ClrTCLK();
824  DR_Shift16(0x012C); // FCTL3 register
826  DR_Shift16(FCTL3_val); // Clear FCTL3; F2xxx: Unlock Info-Seg.
827  // A by toggling LOCKA-Bit if required,
828  SetTCLK();
829 
830  ClrTCLK();
832 
833  for (i = 0; i < Length; i++, addr += 2)
834  {
835  DR_Shift16(0x2408); // Set RW to write
837  DR_Shift16(addr); // Set address
839  DR_Shift16(DataArray[i]); // Set data
840  SetTCLK();
841  ClrTCLK();
843  DR_Shift16(0x2409); // Set RW to read
844 
845  TCLKstrobes(35); // Provide TCLKs, min. 33 for F149 and F449
846  // F2xxx: 29 are ok
847  }
848 
850  DR_Shift16(0x2408); // Set RW to write
852  DR_Shift16(0x0128); // FCTL1 register
854  DR_Shift16(0xA500); // Disable FLASH write
855  SetTCLK();
856 
857  // set LOCK-Bits again
858  ClrTCLK();
860  DR_Shift16(0x012C); // FCTL3 address
862  DR_Shift16(FCTL3_val | 0x0010); // Lock Inf-Seg. A by toggling LOCKA and set LOCK again
863  SetTCLK();
864 
865  ReleaseCPU();
866 }
867 #else
868 
869 //----------------------------------------------------------------------------
875 void WriteFLASH(word StartAddr, word Length, word *DataArray)
876 {
877  word i; // Loop counter
878  word addr = StartAddr; // Address counter
879  word FCTL3_val = SegmentInfoAKey; // SegmentInfoAKey holds Lock-Key for Info
880  // Seg. A
881 
882  HaltCPU();
883 
884  ClrTCLK();
886  DR_Shift16(0x2408); // Set RW to write
888  DR_Shift16(0x0128); // FCTL1 register
890  DR_Shift16(0xA540); // Enable FLASH write
891  SetTCLK();
892 
893  ClrTCLK();
895  DR_Shift16(0x012A); // FCTL2 register
897  DR_Shift16(0xA540); // Select MCLK as source, DIV=1
898  SetTCLK();
899 
900  ClrTCLK();
902  DR_Shift16(0x012C); // FCTL3 register
904  DR_Shift16(FCTL3_val); // Clear FCTL3; F2xxx: Unlock Info-Seg.
905  // A by toggling LOCKA-Bit if required,
906  SetTCLK();
907 
908  ClrTCLK();
910 
911  for (i = 0; i < Length; i++, addr += 2)
912  {
913  DR_Shift16(0x2408); // Set RW to write
915  DR_Shift16(addr); // Set address
917  DR_Shift16(DataArray[i]); // Set data
918  SetTCLK();
919  ClrTCLK();
921  DR_Shift16(0x2409); // Set RW to read
922 
923  TCLKstrobes(35); // Provide TCLKs, min. 33 for F149 and F449
924  // F2xxx: 29 are ok
925  }
926 
928  DR_Shift16(0x2408); // Set RW to write
930  DR_Shift16(0x0128); // FCTL1 register
932  DR_Shift16(0xA500); // Disable FLASH write
933  SetTCLK();
934 
935  // set LOCK-Bits again
936  ClrTCLK();
938  DR_Shift16(0x012C); // FCTL3 address
940  DR_Shift16(FCTL3_val | 0x0010); // Lock Inf-Seg. A by toggling LOCKA and set LOCK again
941  SetTCLK();
942 
943  ReleaseCPU();
944 }
945 #endif
946 
947 //----------------------------------------------------------------------------
957 word WriteFLASHallSections(const unsigned int *data, const unsigned long *address, const unsigned long *length_of_sections, const unsigned long sections)
958 {
959  int i, init = 1;
960 
961  for(i = 0; i < sections; i++)
962  {
963  // Write/Verify(PSA) one FLASH section
964  WriteFLASH(address[i], length_of_sections[i], (word*)&data[init-1]);
965  if (!VerifyMem(address[i], length_of_sections[i], (word*)&data[init-1]))
966  {
967  return(STATUS_ERROR);
968  }
969  init += length_of_sections[i];
970  }
971 
972  return(STATUS_OK);
973 }
974 
975 //----------------------------------------------------------------------------
980 word ReadMem(word Format, word Addr)
981 {
982  word TDOword;
983 
984  HaltCPU();
985 
986  ClrTCLK();
988  if (Format == F_WORD)
989  {
990  DR_Shift16(0x2409); // Set word read
991  }
992  else
993  {
994  DR_Shift16(0x2419); // Set byte read
995  }
997  DR_Shift16(Addr); // Set address
999  SetTCLK();
1000 
1001  ClrTCLK();
1002  TDOword = DR_Shift16(0x0000); // Shift out 16 bits
1003 
1004  ReleaseCPU();
1005  return(Format == F_WORD ? TDOword : TDOword & 0x00FF);
1006 }
1007 
1008 //----------------------------------------------------------------------------
1013 void ReadMemQuick(word StartAddr, word Length, word *DataArray)
1014 {
1015  word i;
1016 
1017  // Initialize reading:
1018  SetPC(StartAddr-4);
1019  HaltCPU();
1020 
1021  ClrTCLK();
1023  DR_Shift16(0x2409); // Set RW to read
1025 
1026  for (i = 0; i < Length; i++)
1027  {
1028  SetTCLK();
1029  DataArray[i] = DR_Shift16(0x0000); // Shift out the data
1030  // from the target.
1031  ClrTCLK();
1032  }
1033  ReleaseCPU();
1034 }
1035 
1036 #ifdef SPYBIWIRE_MODE
1037 //----------------------------------------------------------------------------
1044 void EraseFLASH(word EraseMode, word EraseAddr)
1045 {
1046 #ifdef ixx_family
1047  word StrobeAmount = 9628; // ixx family requires additional TCLKs due
1048  // due to larger segment size
1049 #else
1050  word StrobeAmount = 4820; // default for Segment Erase
1051 #endif
1052  word i, loopcount = 1; // erase cycle repeating for Mass Erase
1053  word FCTL3_val = SegmentInfoAKey; // SegmentInfoAKey holds Lock-Key for Info
1054  // Seg. A
1055 
1056  if ((EraseMode == ERASE_MASS) || (EraseMode == ERASE_MAIN))
1057  {
1058  if(DeviceHas_FastFlash())
1059  {
1060  StrobeAmount = 10600; // Larger Flash memories require
1061  }
1062  else
1063  {
1064  StrobeAmount = 5300; // Larger Flash memories require
1065  loopcount = 19; // additional cycles for erase.
1066  }
1067  }
1068  HaltCPU();
1069 
1070  for (i = loopcount; i > 0; i--)
1071  {
1072  ClrTCLK();
1074  DR_Shift16(0x2408); // set RW to write
1076  DR_Shift16(0x0128); // FCTL1 address
1078  DR_Shift16(EraseMode); // Enable erase mode
1079  SetTCLK();
1080 
1081  ClrTCLK();
1083  DR_Shift16(0x012A); // FCTL2 address
1085  DR_Shift16(0xA540); // MCLK is source, DIV=1
1086  SetTCLK();
1087 
1088  ClrTCLK();
1090  DR_Shift16(0x012C); // FCTL3 address
1092  DR_Shift16(FCTL3_val); // Clear FCTL3; F2xxx: Unlock Info-Seg. A by toggling LOCKA-Bit if required,
1093  SetTCLK();
1094 
1095  ClrTCLK();
1097  DR_Shift16(EraseAddr); // Set erase address
1099  DR_Shift16(0x55AA); // Dummy write to start erase
1100  SetTCLK();
1101 
1102  ClrTCLK();
1104  DR_Shift16(0x2409); // Set RW to read
1105  TCLKstrobes(StrobeAmount); // Provide TCLKs
1107  DR_Shift16(0x2408); // Set RW to write
1109  DR_Shift16(0x0128); // FCTL1 address
1111  DR_Shift16(0xA500); // Disable erase
1112  SetTCLK();
1113  }
1114  // set LOCK-Bits again
1115  ClrTCLK();
1117  DR_Shift16(0x012C); // FCTL3 address
1119  DR_Shift16(FCTL3_val | 0x0010); // Lock Inf-Seg. A by toggling LOCKA (F2xxx) and set LOCK again
1120  SetTCLK();
1121 
1122  ReleaseCPU();
1123 }
1124 #else
1125 //----------------------------------------------------------------------------
1132 void EraseFLASH(word EraseMode, word EraseAddr)
1133 {
1134 #ifdef ixx_family
1135  word StrobeAmount = 9628; // ixx family requires additional TCLKs due
1136  // due to larger segment size
1137 #else
1138  word StrobeAmount = 4820; // default for Segment Erase
1139 #endif
1140  word i, loopcount = 1; // erase cycle repeating for Mass Erase
1141  word FCTL3_val = SegmentInfoAKey; // SegmentInfoAKey holds Lock-Key for Info
1142  // Seg. A
1143 
1144  if ((EraseMode == ERASE_MASS) || (EraseMode == ERASE_MAIN))
1145  {
1146  if(DeviceHas_FastFlash())
1147  {
1148  StrobeAmount = 10600; // Larger Flash memories require
1149  }
1150  else
1151  {
1152  StrobeAmount = 5300; // Larger Flash memories require
1153  loopcount = 19; // additional cycles for erase.
1154  }
1155  }
1156  HaltCPU();
1157 
1158  for (i = loopcount; i > 0; i--)
1159  {
1160  ClrTCLK();
1162  DR_Shift16(0x2408); // set RW to write
1164  DR_Shift16(0x0128); // FCTL1 address
1166  DR_Shift16(EraseMode); // Enable erase mode
1167  SetTCLK();
1168 
1169  ClrTCLK();
1171  DR_Shift16(0x012A); // FCTL2 address
1173  DR_Shift16(0xA540); // MCLK is source, DIV=1
1174  SetTCLK();
1175 
1176  ClrTCLK();
1178  DR_Shift16(0x012C); // FCTL3 address
1180  DR_Shift16(FCTL3_val); // Clear FCTL3; F2xxx: Unlock Info-Seg. A by toggling LOCKA-Bit if required,
1181  SetTCLK();
1182 
1183  ClrTCLK();
1185  DR_Shift16(EraseAddr); // Set erase address
1187  DR_Shift16(0x55AA); // Dummy write to start erase
1188  SetTCLK();
1189 
1190  ClrTCLK();
1192  DR_Shift16(0x2409); // Set RW to read
1193  TCLKstrobes(StrobeAmount); // Provide TCLKs
1195  DR_Shift16(0x2408); // Set RW to write
1197  DR_Shift16(0x0128); // FCTL1 address
1199  DR_Shift16(0xA500); // Disable erase
1200  SetTCLK();
1201  }
1202  // set LOCK-Bits again
1203  ClrTCLK();
1205  DR_Shift16(0x012C); // FCTL3 address
1207  DR_Shift16(FCTL3_val | 0x0010); // Lock Inf-Seg. A by toggling LOCKA (F2xxx) and set LOCK again
1208  SetTCLK();
1209 
1210  ReleaseCPU();
1211 }
1212 #endif
1213 
1214 //----------------------------------------------------------------------------
1220 word EraseCheck(word StartAddr, word Length)
1221 {
1222  return (VerifyPSA(StartAddr, Length, 0));
1223 }
1224 
1225 //----------------------------------------------------------------------------
1232 word VerifyMem(word StartAddr, word Length, word *DataArray)
1233 {
1234  return (VerifyPSA(StartAddr, Length, DataArray));
1235 }
1236 
1237 //------------------------------------------------------------------------
1240 word BlowFuse(void)
1241 {
1242 #ifdef SPYBIWIRE_MODE
1243 
1244  IR_Shift(IR_PREPARE_BLOW); // Initialize fuse blowing
1245  MsDelay(1);
1246 
1248  MsDelay(1);
1249  VPPon( VPP_ON_TEST ); // Switch VPP onto selected pin
1250  MsDelay(3);
1251  JTAGOUT |= SBWDATO; // Execute fuse blowing
1252  MsDelay(1);
1253 
1254 #else
1255 
1256  word mode = VPP_ON_TEST; // Devices with TEST pin: VPP to TEST
1257 
1258  if(!DeviceHas_TestPin())
1259  {
1260  // Devices without TEST pin
1261  IR_Shift(IR_CNTRL_SIG_16BIT);// TDO becomes TDI functionality
1262  DR_Shift16(0x7201);
1263  TDOisInput();
1264  mode = VPP_ON_TDI; // Enable VPP on TDI
1265  }
1266 
1267  IR_Shift(IR_PREPARE_BLOW); // Initialize fuse blowing
1268  MsDelay(1);
1269  VPPon(mode); // Switch VPP onto selected pin
1270  MsDelay(5);
1271  IR_Shift(IR_EX_BLOW); // Execute fuse blowing
1272  MsDelay(1);
1273 
1274 #endif
1275 
1276  // Switch off power to target and wait
1277  ReleaseTarget(); // switch VPP and VCC target off
1278  MsDelay(200);
1279 
1280  // Check fuse: switch power on, simulate an initial JTAG entry
1281  InitTarget(); // Supply and preset Target Board
1282 
1283  // Return result of "is fuse blown?"
1284  return(GetDevice() == STATUS_FUSEBLOWN);
1285 }
1286 
1287 //------------------------------------------------------------------------
1290 word IsFuseBlown(void)
1291 {
1292  word i;
1293 
1294  for (i = 3; i > 0; i--) // First trial could be wrong
1295  {
1297  if (DR_Shift16(0xAAAA) == 0x5555)
1298  {
1299  return(STATUS_OK); // Fuse is blown
1300  }
1301  }
1302  return(STATUS_ERROR); // fuse is not blown
1303 }
1304 
1305 //------------------------------------------------------------------------
1307 void UnlockInfoA(void)
1308 {
1309  SegmentInfoAKey = 0xA540;
1310 }
1311 
1312 /****************************************************************************/
1313 /* END OF SOURCE FILE */
1314 /****************************************************************************/
void UnlockInfoA(void)
This Function unlocks segment A of the InfoMemory (Flash)
Definition: JTAGfunc430.c:1307
word ReadMem(word Format, word Addr)
This function reads one byte/word from a given address in memory.
Definition: JTAGfunc430.c:980
word BlowFuse(void)
This function blows the security fuse.
Definition: JTAGfunc430.c:1240
void WriteMem(word Format, word Addr, word Data)
This function writes one byte/word at a given address ( <0xA00)
Definition: JTAGfunc430.c:741
void ReleaseCPU(void)
Function to release the target CPU from the controlled stop state.
Definition: JTAGfunc430.c:325
void SetPC(word Addr)
Load a given address into the target CPU's program counter (PC).
Definition: JTAGfunc430.c:289
#define VPP_ON_TEST
Fuse blow voltage is supplied via the TEST pin.
Definition: JTAGfunc430.h:134
word Shift(word Format, word Data)
Shift a value into TDI (MSB first) and simultaneously shift out a value from TDO (MSB first)...
#define IR_DATA_16BIT
Set the MSP430 MDB to a specific 16-bit value with the next 16-bit data access.
Definition: JTAGfunc430.h:99
word IsFuseBlown(void)
This function checks if the JTAG access security fuse is blown.
Definition: JTAGfunc430.c:1290
void ReadMemQuick(word StartAddr, word Length, word *DataArray)
This function reads an array of words from the memory.
Definition: JTAGfunc430.c:1013
#define IR_DATA_PSA
Switch JTAG data register to PSA mode.
Definition: JTAGfunc430.h:105
#define ClrSBWTCK()
SBW macro: clear TCK signal.
void HaltCPU(void)
Function to set the CPU into a controlled stop state.
Definition: JTAGfunc430.c:311
JTAG Function Prototypes and Definitions.
word EraseCheck(word StartAddr, word Length)
This function performs an Erase Check over the given memory range.
Definition: JTAGfunc430.c:1220
#define SetTST()
JTAG macro: set TST signal.
Device Function Prototypes and Definitions for FLASH programming.
#define SetSBWTDIO()
SBW macro: set TDIO signal.
#define VPP_ON_TDI
Fuse blow voltage is supplied via the TDI pin.
Definition: JTAGfunc430.h:132
void ReleaseDevice(word Addr)
Function to release the target device from JTAG control.
Definition: JTAGfunc430.c:721
word ExecutePOR(void)
Function to execute a Power-On Reset (POR) using JTAG CNTRL SIG register.
Definition: JTAGfunc430.c:239
#define SetTMS()
JTAG macro: set TMS signal.
void DrvSignals(void)
Set up I/O pins for JTAG communication.
void TMSH_TDIH(void)
Combination of SBW macros: TMS high, TDI high, no TDO read.
bool DeviceHas_FastFlash(void)
Function to check if current device supports FastFlash.
Definition: Devices430.c:178
void IR_Ex_Blow_SBW_Shift(void)
Provide JTAG fuse blow instruction.
#define STATUS_FUSEBLOWN
GetDevice returns this if the security fuse is blown.
void ReleaseTarget(void)
Release Target Board (switch voltages off, JTAG pins are HI-Z)
#define STATUS_ERROR
return 0 = error
#define SPYBIWIREJTAG_IF
JTAG interface on a device that supports JTAG and SBW.
void EraseFLASH(word EraseMode, word EraseAddr)
This function performs a mass erase (with and w/o info memory) or a segment erase of a FLASH module s...
Definition: JTAGfunc430.c:1044
#define ClrRST()
JTAG macro: clear RST signal.
void MsDelay(word milliseconds)
Delay function (resolution is 1 ms)
#define ClrTMS()
JTAG macro: clear TMS signal.
void TDOisInput(void)
This function switches TDO to Input (used for fuse blowing)
#define SetSBWTCK()
SBW macro: set TCK signal.
#define ClrTCK()
JTAG macro: clear TCK signal.
#define INTERFACE
Select the interface to be used to communicate with the device.
Definition: Config430.h:65
#define ClrTCLK()
SBW macro: clear TCLK signal.
#define SPYBIWIRE_IF
Spy-Bi-Wire interface.
#define IR_DATA_QUICK
Set the MSP430 MDB to a specific 16-bit value (RAM only)
Definition: JTAGfunc430.h:101
#define JTAG_ID
JTAG identification value for MSP430 architecture devices.
Definition: JTAGfunc430.h:123
#define VPPon(x)
Supply fuse blow voltage based on TEST or TDI pin (based on input: x(.
bool DeviceHas_TestPin(void)
Function to check if current device has a test pin.
Definition: Devices430.c:157
void TMSL_TDIH(void)
Combination of SBW macros: TMS low, TDI high, no TDO read.
#define SBWDATO
JTAG data_out pin in SBW mode -separate pin in MSP430F5437 - common IO translator.
#define IR_ADDR_16BIT
Set the MSP430 MAB to a specific 16-bit value.
Definition: JTAGfunc430.h:112
word SetInstrFetch(void)
Function to set target CPU JTAG FSM into the instruction fetch state.
Definition: JTAGfunc430.c:267
#define IR_SHIFT_OUT_PSA
Shift out the PSA pattern generated by IR_DATA_PSA.
Definition: JTAGfunc430.h:107
#define IR_ADDR_CAPTURE
Read out the MAB data on the next 16/20-bit data access.
Definition: JTAGfunc430.h:114
word DR_Shift16(word data)
Function for shifting a given 16-bit word into the JTAG data register through TDI.
Definition: JTAGfunc430.c:94
#define JTAGOUT
JTAG output register.
void InitTarget(void)
Initialization of the Target Board (switch voltages on, preset JTAG pins)
void usDelay(word microseconds)
Delay function (resolution is ~1 us)
#define ClrTST()
JTAG macro: clear TST signal.
void ResetTAP(void)
Reset target JTAG interface and perform fuse-HW check.
Definition: JTAGfunc430.c:180
#define STATUS_OK
return 1 = no error
#define ERASE_MASS
Constant for flash erase: main & info of SELECTED mem arrays.
Definition: Devices430.h:76
byte TCLK_saved
Holds the last value of TCLK before entering a JTAG sequence.
word VerifyMem(word StartAddr, word Length, word *DataArray)
This function performs a Verification over the given memory range.
Definition: JTAGfunc430.c:1232
void WriteMemQuick(word StartAddr, word Length, word *DataArray)
This function writes an array of words into the target memory.
Definition: JTAGfunc430.c:769
#define IR_EX_BLOW
Perform JTAG fuse blow.
Definition: JTAGfunc430.h:94
#define SetTCLK()
SBW macro: set TCLK signal.
#define IR_CNTRL_SIG_16BIT
Set the JTAG control signal register.
Definition: JTAGfunc430.h:84
#define IR_CNTRL_SIG_RELEASE
Release the CPU from JTAG control.
Definition: JTAGfunc430.h:88
bool DeviceHas_EnhVerify(void)
Function to check if current device supports EnhVerify.
Definition: Devices430.c:185
word WriteFLASHallSections(const unsigned int *data, const unsigned long *address, const unsigned long *length_of_sections, const unsigned long sections)
This function programs/verifies a set of data arrays of words into a FLASH memory by using the "Write...
Definition: JTAGfunc430.c:957
#define ERASE_MAIN
Constant for flash erase: main of SELECTED mem arrays.
Definition: Devices430.h:78
#define SetRST()
JTAG macro: set RST signal.
#define IR_DATA_TO_ADDR
Set the MSP430 MDB with a specific 16-bit value and write it to the memory address which is currently...
Definition: JTAGfunc430.h:117
#define IR_PREPARE_BLOW
Prepare for JTAG fuse blow.
Definition: JTAGfunc430.h:92
#define SetTCK()
JTAG macro: set TCK signal.
void SetDevice(word wDeviceId)
This function accepts a Device ID and extracts the corresponding device information from the sDeviceF...
Definition: Devices430.c:144
void WriteFLASH(word StartAddr, word Length, word *DataArray)
This function programs/verifies an array of words into the FLASH memory by using the FLASH controller...
Definition: JTAGfunc430.c:797
word GetDevice(void)
Function to take target device under JTAG control. Disables the target watchdog. Sets the global DEVI...
Definition: JTAGfunc430.c:659
void RlsSignals(void)
Release I/O pins.
#define IR_BYPASS
Bypass instruction - TDI input is shifted to TDO as an output.
Definition: JTAGfunc430.h:119
#define MAX_ENTRY_TRY
Maximum number of tries for the determination of the core identification info.
Definition: Config430.h:86
word IR_Shift(byte instruction)
Function for shifting a new instruction into the JTAG instruction register through TDI (MSB first...
Definition: JTAGfunc430.c:137
#define SetTDI()
JTAG macro: set TDI signal.
#define IR_CNTRL_SIG_CAPTURE
Read out the JTAG control signal register.
Definition: JTAGfunc430.h:86
Low Level function prototypes, macros, and pin-to-signal assignments regarding to user's hardware...
void TMSH_TDIL(void)
Combination of SBW macros: TMS high, TDI low, no TDO read.

Copyright 2016, Texas Instruments Incorporated