⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 jtagfunc.cpp

📁 TI MSP430 JTAG program for internal flash upgarde from PC printer port
💻 CPP
📖 第 1 页 / 共 2 页
字号:
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    JTAGVERSION = IR_Shift(IR_ADDR_CAPTURE);
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
	
    WriteMem(F_WORD, 0x0120, 0x5A80); // Disable Watchdog on target device  
		
    if (JTAGVERSION != JTAG_ID)
        return(STATUS_ERROR); 
		
    return(STATUS_OK);
}

//----------------------------------------------------------------------------
/* Function to take target device under JTAG control. Disables the target
   watchdog. Sets the global DEVICE variable as read from the target device.	
   Arguments: None
   Result:    word (STATUS_ERROR if fuse is blown, incorrect JTAG ID or
                    synchronizing time-out; STATUS_OK otherwise)
*/
word GetDevice(void)
{
    word i;
  
    DEVICE = 0;             // Preset DEVICE with "not a device"
    ResetTAP();             // Reset JTAG state machine, check fuse HW
    if (IsFuseBlown())      // Stop here if fuse is already blown
        return(STATUS_ERROR);
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2401);     // Set device into JTAG mode + read
    if (IR_Shift(IR_CNTRL_SIG_CAPTURE) != JTAG_ID)
        return(STATUS_ERROR);
    // Wait until CPU is synchronized, timeout after a limited # of attempts
    for (i = 50; i > 0; i--) {
  	    if ((DR_Shift16(0x0000) & 0x0200) == 0x0200)  {
  		    DEVICE = ReadMem(F_WORD, 0x0FF0);   // Get target device type 
  		                                        //(bytes are interchanged)
  		    DEVICE = (DEVICE << 8) + (DEVICE >> 8);	// Set global DEVICE type
  		    if (DEVICE != DEVICE_ID) error_out("Error, DEVICE_ID no match");
  		    printf("DEVICE = %x\n",DEVICE);
  		    break;
	    }
	    else if (i == 1)
		    return(STATUS_ERROR);       // Timeout reached, return false		    		
    }
    if (!ExecutePUC())                  // Perform PUC, Includes  
	    return(STATUS_ERROR);           // target Watchdog disable.
	    
    return(STATUS_OK);		
}

/*---------------------------------------------------------------------------
   This function generates Amount strobes with the Flash Timing Generator
   Frequency fFTG = 257..476kHz (t = 3.9..2.1us).
   User knows target frequency, instruction cycles, C implementation.
   Arguments: word Amount (number of strobes to be generated)
*/
void TCLKstrobes(word Amount)
{
	word i;
	
	for (i = Amount; i > 0; i--)        // This implementation has 14 body cycles!	
	{
		putp1(g_tck,g_tms,1,1);         //JTAGOUT |=  TCLK;		// Set TCLK
		putp1(g_tck,g_tms,0,1);         //JTAGOUT &= ~TCLK;		// Reset TCLK
	}
}
//----------------------------------------------------------------------------
/* This function compares the computed PSA (Pseudo Signature Analysis) value
   to the PSA value shifted out from the target device.
   It is used for very fast data block write or erasure verification.
   Arguments: word StartAddr (Start address of data block to be checked)
              word Length (Number of words within data block)
              word *DataArray (Pointer to array with the data, 0 for Erase Check)
   Result:    word (STATUS_OK if comparison was successful, STATUS_ERROR otherwise)
*/
word VerifyPSA(word StartAddr, word Length, word *DataArray)
{
  word TDOword, i;
  word POLY = 0x0805;           // Polynom value for PSA calculation
  word PSA_CRC = StartAddr-2;   // Start value for PSA calculation

  ExecutePUC();          
  IR_Shift(IR_CNTRL_SIG_16BIT);
  DR_Shift16(0x2401);
  SetInstrFetch();
  IR_Shift(IR_DATA_16BIT);
  DR_Shift16(0x4030);
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  DR_Shift16(StartAddr-2);
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  IR_Shift(IR_ADDR_CAPTURE);
  DR_Shift16(0x0000);
  IR_Shift(IR_DATA_PSA);
  for (i = 0; i < Length; i++)
  {
  // Calculate the PSA (Pseudo Signature Analysis) value  
    if ((PSA_CRC & 0x8000) == 0x8000)
    {
      PSA_CRC ^= POLY;
      PSA_CRC <<= 1;
      PSA_CRC |= 0x0001;
    }
    else
    {
      PSA_CRC <<= 1;
    }
    // if pointer is 0 then use erase check mask, otherwise data  
    &DataArray[0] == 0 ? (PSA_CRC ^= 0xFFFF) : (PSA_CRC ^= DataArray[i]);
    
    // Clock through the PSA  
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    g_tms = 1;                  //SetTMS();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();		      // Select DR scan
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    g_tms = 0;                  //ClrTMS();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();		      // Capture DR
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();		      // Shift DR
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    g_tms = 1;                  //SetTMS();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();		      // Exit DR
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();
    g_tms = 0;                  //ClrTMS();
    putp1(0,g_tms,g_tdi,1);     //ClrTCK();
    putp1(1,g_tms,g_tdi,1);     //SetTCK();
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
  }
  IR_Shift(IR_SHIFT_OUT_PSA);
  TDOword = DR_Shift16(0x0000);	// Read out the PSA value
  putp1(g_tck,g_tms,1,1);       //SetTCLK();
  printf("%x\n",TDOword);
  printf("%x\n",PSA_CRC);
  return((TDOword == PSA_CRC) ? STATUS_OK : STATUS_ERROR);
}

//----------------------------------------------------------------------------
/* This function performs a mass erase (with and w/o info memory) or a segment
   erase of a FLASH module specified by the given mode and address.
   Large memory devices get additional mass erase operations to meet the spec.
   Arguments: word Mode (could be ERASE_MASS or ERASE_MAIN or ERASE_SGMT)
              word Addr (any address within the selected segment)   				
   Result:    None
   Remark:    Could be extended with erase check via PSA.
*/
void EraseFLASH(word EraseMode, word EraseAddr)
{
  word StrobeAmount = 4820;	    // default for Segment Erase  
  word i, loopcount = 1;        // erase cycle repeating for Mass Erase
  
  if ((EraseMode == ERASE_MASS) || (EraseMode == ERASE_MAIN))
  {  
	StrobeAmount = 5300;        // Larger Flash memories require
	loopcount = 19;             // additional cycles for erase.
  }  	  
  
  for (i = loopcount; i > 0; i--)
  {
    HaltCPU();
    
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2408);	        // set RW to write
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(0x0128);         // FCTL1 address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(EraseMode);      // Enable erase mode
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(0x012A);         // FCTL2 address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(0xA540);         // MCLK is source, DIV=1
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(0x012C);         // FCTL3 address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(0xA500);         // Clear FCTL3
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(EraseAddr);      // Set erase address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(0x55AA);         // Dummy write to start erase
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2409);	        // Set RW to read
    TCLKstrobes(StrobeAmount);  // Provide TCLKs
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2408);         // Set RW to write
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(0x0128);         // FCTL1 address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(0xA500);         // Disable erase
    putp1(g_tck,g_tms,1,1);     //SetTCLK();

    ReleaseCPU();
  }
}

//----------------------------------------------------------------------------
/* This function performs an Erase Check over the given memory range
   Arguments: word StartAddr (Start address of memory to be checked)
              word Length (Number of words to be checked)
   Result:    word (STATUS_OK if erase check was successful, STATUS_ERROR otherwise)
*/
word EraseCheck(word StartAddr, word Length)
{
  return (VerifyPSA(StartAddr, Length, 0));
}

//----------------------------------------------------------------------------
/* This function performs a Verification over the given memory range
   Arguments: word StartAddr (Start address of memory to be verified)
              word Length (Number of words to be verified)
              word *DataArray (Pointer to array with the data)
   Result:    word (STATUS_OK if verification was successful, STATUS_ERROR otherwise)
*/
word VerifyMem(word StartAddr, word Length, word *DataArray)
{
  return (VerifyPSA(StartAddr, Length, &DataArray[0]));
}

//----------------------------------------------------------------------------
/* Function to release the target device from JTAG control
   Argument: word Addr (0xFFFE: Perform Reset, means Load Reset Vector into PC,
                        otherwise: Load Addr into PC)
   Result:   None
*/
void ReleaseDevice(word Addr)
{
  if (Addr == V_RESET)
  {	
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2C01);     // Perform a reset
    DR_Shift16(0x2401);
  }
  else
    SetPC(Addr);            // Set target CPU's PC
  IR_Shift(IR_CNTRL_SIG_RELEASE);
}

/*----------------------------------------------------------------------------
   Release Target Board (switch voltages off, JTAG pins are HI-Z)	
*/
void ReleaseTarget(void)
{
     //Power off, TCK=0, TMS=0, TDI=0
    _outp(lpt_address, 4+2+1);
    
	//VPPoff();				// VPPs are off (safety)
	//Delay(5);				// Settle MOS relays
	//JTAGDIR  =  0x00;		// VCC is off, all I/Os are HI-Z
	//Delay(5);				// Settle MOS relays
}

//----------------------------------------------------------------------------
/* This function programs/verifies an array of words into an FLASH by
   using the FLASH controller. The JTAG FLASH register isn't needed.
   Arguments: word StartAddr (Start address of FLASH memory)
              word Length (Number of words to be programmed)
              word *DataArray (Pointer to array with the data)
   Result:    None
*/
void WriteFLASH(word StartAddr, word Length, word *DataArray)
{
  word i;			// Loop counter
  word addr = StartAddr;	// Address counter
  
  HaltCPU();
  
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  IR_Shift(IR_CNTRL_SIG_16BIT);
  DR_Shift16(0x2408);       // Set RW to write
  IR_Shift(IR_ADDR_16BIT);
  DR_Shift16(0x0128);       // FCTL1 register
  IR_Shift(IR_DATA_TO_ADDR);
  DR_Shift16(0xA540);       // Enable FLASH write
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  IR_Shift(IR_ADDR_16BIT);
  DR_Shift16(0x012A);       // FCTL2 register
  IR_Shift(IR_DATA_TO_ADDR);
  DR_Shift16(0xA540);       // Select MCLK as source, DIV=1
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  IR_Shift(IR_ADDR_16BIT);
  DR_Shift16(0x012C);       // FCTL3 register
  IR_Shift(IR_DATA_TO_ADDR);
  DR_Shift16(0xA500);       // Clear FCTL3 register
  putp1(g_tck,g_tms,1,1);   //SetTCLK();
  
  putp1(g_tck,g_tms,0,1);   //ClrTCLK();
  for (i = 0; i < Length; i++, addr += 2)
  {
    IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2408);     // Set RW to write
    IR_Shift(IR_ADDR_16BIT);
    DR_Shift16(addr);       // Set address
    IR_Shift(IR_DATA_TO_ADDR);
    DR_Shift16(DataArray[i]);   // Set data
    putp1(g_tck,g_tms,1,1);     //SetTCLK();
    putp1(g_tck,g_tms,0,1);     //ClrTCLK();
	IR_Shift(IR_CNTRL_SIG_16BIT);
    DR_Shift16(0x2409);     // Set RW to read
	TCLKstrobes(35);        // Provide TCLKs, min. 33 for F149 and F449 
  }
  IR_Shift(IR_CNTRL_SIG_16BIT);
  DR_Shift16(0x2408);       // Set RW to write
  IR_Shift(IR_ADDR_16BIT);
  DR_Shift16(0x0128);       // FCTL1 register
  IR_Shift(IR_DATA_TO_ADDR);
  DR_Shift16(0xA500);       // Disable FLASH write
  putp1(g_tck,g_tms,1,1);   //SetTCLK();

  ReleaseCPU();
}

//----------------------------------------------------------------------------
/* This function programs/verifies a set of data arrays of words into a FLASH
   memory by using the "WriteFLASH()" function. It conforms with the
   "CodeArray" structure convention of file "Target_Code.s43".
   Arguments: word *DataArray (Pointer to array with the data)
   Result:    word (STATUS_OK if verification was successful,
                    STATUS_ERROR otherwise)
*/
word WriteFLASHallSections(word *CodeArray)
{
  word s;           // Number of sections
  word p;           // Pointer to data
  
  for (s = CodeArray[0], p = 1; s > 0; s--)
  {
    // Write/Verify(PSA) one FLASH section	
    WriteFLASH(CodeArray[p], CodeArray[p+1], &CodeArray[p+2]);
    if (!VerifyMem(CodeArray[p], CodeArray[p+1], &CodeArray[p+2]))
      return(STATUS_ERROR);
    // pointer of next section = old pointer + 2 + length of actual section      
    p += CodeArray[p+1] + 2;
  }
  return(STATUS_OK);
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -