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

📄 main.c

📁 采用IAR在线调试ADI公司基于ARM7内核的ADUC7026的I2CDownloadMaster代码
💻 C
字号:
/*********************************************************************

 Author        : ADI - Apps            www.analog.com/MicroConverter

 Date          : Feb 2007

 File          : main.c

 Hardware      : ADuC702x Rev I silicon

                  ADuC702x        ->      ADuC7026I
                  P1.2  ( SCL )           P1.0
                  P1.3  ( SDA )           P1.1
                  P4.6                    P0.0
                  P4.7                    Reset

                 ADuC7026I Write Address = 0x04
                 ADuC7026I Read  Address = 0x05

 Description   :  This programme demostrates how to use the ADuC702x to download
                  via I2C to an ADuC702xI.

                    1)  A backspace character is transmitted and ID read back
                    2)  Flash/EE is erased
                    3)  Data is written
                    4)  Flash/EE is read and write protected
                    5)  ADuC702xI is reset

                  For more information on the ADuC702x I2C download protocol
                  please refer to the Tech Note AN-806

                  Please note that Timer2 is used to generate a software delay
                  CD changed to zero, I2C configured for 100kHz operation on
                  P1.2 and P1.3. Also, 10kOhm pull-ups are required on I2C Clock
                  and Data lines.

                  Please note 3 #pragma options:

                  #define Full_Chip_Erase
                    Perform Mass Erase of ADuC702xI ( Requires ~2.5s )
                  #define Enable_Protection
                    Enable Read/Write protection
                  #define Write_0x80014
                    Write 0x80014 with 0x00000000;

*********************************************************************/

/* Place Include files here */

#include "ioADuC7026.h"

// Place Function Prototypes here

void Init_ADuC7024(void);
unsigned long ADI_Command_Packet( unsigned char Command, unsigned long laddress, unsigned char cNum_Bytes, unsigned char *cdata );
void Reset_ADuC(void);
void Get_ID_String( unsigned char *c_data );
void delay (int length);
void delay (int length);

// Place Global Variables here

char *ID_String= "ADuC7026i  -62 I51";
char DownloadModeEntered = 0;

const unsigned long BlinkHex[92] = {0x18F09FE5,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF
,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0xFFFFFFFF,0x40000800,0x6C010800,0x68010800
,0x64010800,0x60010800,0x00000000,0x5C010800,0x58010800,0x78009FE5,0x0110A0E3
,0x041480E5,0x0210A0E3,0x081480E5,0xF410A0E3,0x0C1480E5,0x60009FE5,0xDBF021E3
,0x00D0A0E1,0x040040E2,0xD7F021E3,0x00D0A0E1,0x040040E2,0xD1F021E3,0x00D0A0E1
,0x040040E2,0xD2F021E3,0x00D0A0E1,0x800040E2,0xD3F021E3,0x00D0A0E1,0x040040E2
,0x10F021E3,0x00D0A0E1,0x1C009FE5,0x010010E3,0x18E09F05,0x18E09F15,0x10FF2FE1
,0xFEFFFFEA,0xFEE7C046,0x0000FFFF,0x90040100,0xF1000800,0xB8000800,0xBD000800
,0x00000000,0x00000000,0x00000000,0x00000000,0x00E00138,0x011C0029,0xFBDA7047
,0x134806C8,0x0B1C1343,0x05D00023,0x0B70491C,0x9142FBD1,0xF5E70F48,0xC01C0323
,0x984306C8,0x0B1C1343,0x06D00378,0x401C0B70,0x491C9142,0xF9D1F1E7,0x00B50849
,0x08480160,0x084A0748,0x01685140,0x01600748,0xFFF7D4FF,0xF6E700BD,0xD4000800
,0xDC000800,0x00000004,0x60F4FFFF,0x00000400,0x81841E00,0xFEFFFFEA,0xFEFFFFEA
,0xFEFFFFEA,0xFEFFFFEA,0xFEFFFFEA,0xFEFFFFEA};

#define Full_Chip_Erase
//#define Enable_Protection
//#define Write_0x80014

// Main Function

int main()
{
  // Place local variable definitions here
  unsigned char c_data_in[400];
  int i;
  unsigned long lResult=1;  // Non Zero Value
  unsigned char c_data[25];
    
  GP4DAT = 0xFF040000;			// P4.2 Turned off until programme completes	

  // Initialise dummy data
    
  for ( i = 0; i < 92  ; i++)
  {
    c_data_in[(i<<2)] = (BlinkHex[i]>>24   & 0xFF);
    c_data_in[(i<<2)+1] =( BlinkHex[i]>>16 & 0xFF);
    c_data_in[(i<<2)+2] = (BlinkHex[i]>>8 & 0xFF);
    c_data_in[(i<<2)+3] = ( BlinkHex[i]   & 0xFF);        
  }   

  Init_ADuC7024();            // Configure ADuC
  Reset_ADuC();               //  Reset Slave ADuC702xI
  Get_ID_String(c_data) ;     //  Read ID String
    

  for ( i = 0 ; i < 18 ; i++ )
  {
    if (c_data[i] != ID_String[i] )
    {
      while(1)
      {}
    }
  }
  DownloadModeEntered = 1;

  while ( lResult != 0)
  {
    // Erase Flash/EE

#ifdef Full_Chip_Erase 
    c_data[0] = 0x00;                       // 0x00 = Full Chip Erase ( Remove Protection )
#else
    c_data[0] = 0x2;                        // Blink programme only requires 2 pages
#endif

    lResult = ADI_Command_Packet( 'E', 0x00, 1, c_data );  
  
    // Programme Data and Verify
  
    lResult += ADI_Command_Packet( 'W', 0x00, 200, c_data_in );
    lResult += ADI_Command_Packet( 'W', 200, 168, c_data_in +200);
    lResult += ADI_Command_Packet( 'V', 0x00, 200, c_data_in );
    lResult += ADI_Command_Packet( 'V', 200, 168, c_data_in +200);
    
#ifdef Write_0x80014  
    c_data[0] = 0x00;
    c_data[1] = 0x00;
    c_data[2] = 0x00;
    c_data[3] = 0x00;  
    lResult += ADI_Command_Packet( 'W', 0x014, 4, c_data );  
#endif
  }  
#ifdef Enable_Protection  
  // Protect Flash/EE ( Write and Read )

  c_data[0] = 0x00;                       // 0x00 = Begin Flash Procedure
  lResult = ADI_Command_Packet( 'P', 0x00, 1, c_data);
  c_data[0] = 0x0F;                       // Select Pages to Write Protect
  lResult += ADI_Command_Packet( 'P', 0x000, 1, c_data);
  lResult += ADI_Command_Packet( 'P', 0x200, 1, c_data);
                                          // Address = 0x8F800 means read Protect
  lResult += ADI_Command_Packet( 'P', 0x8F800, 1, c_data);

  c_data[0] = 0x1;                        // 0x01 = End Prtoection Sequence
                                          // Address = Key = 0x12345678
  lResult += ADI_Command_Packet( 'P', 0x12345678, 1, c_data);    
#endif    
  
  // Execute User Code
  
  lResult += ADI_Command_Packet( 'R', 0x80001, 0, 0x00);
    
  GP4DAT = 0x04000000;			// P4.2 turned on when programme completed	
    
  while(1)
  {}
}

/*********************************************************************

 Author         : ADI - Apps            www.analog.com/MicroConverter

 Date           : Feb. 2007

 Function Name  : void Init_ADuC7024(void)

 Arguement      : 

 Description    : This function configures ADuC702x for 41.78MHz operation
                  using the internal oscilator, configures I2C1 on P1.2 and 
                  P1.3 and Configures I2C1 for 100kHz master operation.

*********************************************************************/

void Init_ADuC7024(void)
{
    POWKEY1   =   0x1;
    POWCON    =   0x00;   //  Configure Core operation for CD = 0
    POWKEY2   =   0xf4;

    GP1CON = 0x2200;	  // I2C on P1.2 and P1.3

    I2C1CFG = 0x82;	  // Master Enable & Enable Generation of Master Clock
	
    // I2C-Master setup
    I2C1DIV = 0xCFCF;	  
}

/*********************************************************************

 Author         : ADI - Apps            www.analog.com/MicroConverter

 Date           : Feb. 2007

 Function Name  : void Get_ID_String( unsigned char *c_data )

 Arguement      : unsigned char *c_data 

 Description    : This function transmits a Back Space character and 
                  reads the ADuC702xI ID string. The ID string is returned
                  in *c_data.

*********************************************************************/

void Get_ID_String( unsigned char *c_data )
{
  int i; 
  /* Send Backspace */
   
  I2C1MTX  =    0x08;       // Send BS

  I2C1ADR  =    0x04;       // Set Address Write Command

  while( ( I2C1MSTA & 0x40 ) == 0x40 )
  {}                        // What until Master is finished command

  delay( 10 );         // Delay to allow ADuC702xI to enter Download Mode
    
  I2C1CNT = 7;              
  I2C1ADR = 0x05;           // Transmit read Address

  for ( i = 0 ; i <  24 ;i++)
  {
    // Wait until Master recieve data
    while((I2C1FSTA & 0xC0) == 0x0)
    {}
    *c_data = I2C1MRX;          // Read Data
    c_data++;
    if ( i == 6 )
    {
      I2C1CNT = 6;
    }
    if ( i == 13 )
    {
      I2C1CNT = 5;
    }
    if ( i == 20 )
    {
      I2C1CNT = 7;
    }      
  }   
}
/*********************************************************************

 Author         : ADI - Apps            www.analog.com/MicroConverter

 Date           : Feb. 2007

 Function Name  : void Reset_ADuC(void)

 Arguement      : 

 Description    : This function resets ADuC702xI and holds BM Low
                  
                  ADuC702x    ->    ADuC702xI
                  P4.6        ->    BM 
                  P4.7        ->    Reset 

*********************************************************************/

void Reset_ADuC(void)
{
    GP4CLR = 0xFFC00000;
    delay( 1 );
    GP4SET = 0xFF800000;   
    delay( 10 );
    GP4SET = 0xFFC00000;
}

/*********************************************************************

 Author         : ADI - Apps            www.analog.com/MicroConverter

 Date           : Feb. 2007

 Function Name  : unsigned long ADI_Command_Packet( unsigned char Command, 
                  unsigned long laddress, unsigned char cNum_Bytes, 
                  unsigned char *cdata )

 Arguement      : unsigned char Command 
                  unsigned long laddress
                  unsigned char cNum_Bytes 
                  unsigned char *cdata

 Description    : This functions performs the following depending on Command
                  
                  Returns 0 for ACK
                  Returns 1 for NACK

                  Command = E
                  Erase cNum_Bytes of pages, starting at laddress.
                  If cNum_Bytes = laddress = 0x00, a Mass Erase is Performed

                  Command  = W
                  Writes cNum_Bytes of cdata, starting at laddress.
                  Note cNum_Bytes maximuim of 250

                  Command = V
                  Verify cNum_Bytes of cdata, starting at laddress.
                  Note cNum_Bytes maximuim of 250

                  Command = P
                  Write Protect cNum_Bytes of pages, starting at laddress.
                  If laddress = 0x08F800, The ADuC702xI is read protected

                  Command = R
                  Execute User Code
                  If laddress = 0x00, a jump to user code is execute
                  If laddress = 0x01, a software reset is performed


*********************************************************************/


unsigned long ADI_Command_Packet( unsigned char Command, unsigned long laddress, unsigned char cNum_Bytes, unsigned char *cdata )
{
  unsigned char Checksum = 0x00,ctemp;
  int i;
  //  Transmit Start ID
  
  I2C1MTX  =    0x07;       
  I2C1MTX  =    0x0E;       

  I2C1ADR  =    0x04;       // Set Address Write Command

    // Transmit Data Bytes
  
    while( I2C1MSTA & 0x1 )   // Wait until Master TX FIFO is empy
    {}
    I2C1MTX = 5+cNum_Bytes;             // # of Data Bytes
    Checksum -= 5+cNum_Bytes;
  
    // Transmit Command
    
    while( I2C1MSTA & 0x1 )   // Wait until Master TX FIFO is empy
    {}
    I2C1MTX = Command;             // Command 
    Checksum -= Command;  
   
    // Transmit Address
  
    for ( i = 0 ;i < 4; i++ )
    {
      while( I2C1MSTA & 0x1 )   // Wait until Master TX FIFO is empy
      {}
      ctemp = (( laddress >> (24 - 8*i) ) & 0xFF);
      I2C1MTX = ctemp;             // Command  
      Checksum -= ctemp; 
    }

    for ( i = 0 ;i < cNum_Bytes; i++ )
    {
      while( I2C1MSTA & 0x1 )   // Wait until Master TX FIFO is empy
      {}
       if (Command == 'V' )
      {
        ctemp = ( cdata[i] << 3 ) & 0xF8;
        ctemp += ( cdata[i] >> 5 ) & 0x7;
      }
      else
      {
        ctemp = (unsigned long)cdata[i];
      }
      I2C1MTX = ctemp;             // Command 
      Checksum -= ctemp;  
    }
                 
  
     while( I2C1MSTA & 0x1 )   // Wait until Master TX FIFO is empy
      {}
      I2C1MTX = Checksum;             // Checksum   
 
    if ( Command == 'E')
    {
      if ( (cdata[0] == 0 ) &&  ( laddress == 0 ) )
      {
        delay(3500);              
      } else
      {
        delay(30 * cdata[0]);      
      }
    }
 
    delay(10);
    
    if ( ( Command == 'P' ) && ( cdata[0] == 0x1 ) )
    {
      delay(20);
    }
           
    
      I2C1CNT = 0;              // Read a Single 8 Bit Byte
      I2C1ADR = 0x05;           // Transmit read Address

      // Wait until Master recieve data
      while((I2C1FSTA & 0xC0) == 0x0)
      {}
      return(I2C1MRX-6);
  
}

/*********************************************************************

 Author         : ADI - Apps            www.analog.com/MicroConverter

 Date           : Feb. 2007

 Function Name  : void delay(int length)

 Arguement      : 

 Description    : This function generates a software delay of length milliseconds 
                  using Timer2

*********************************************************************/

void delay (int length)
{
	T2LD = length * 33;
        T2CON = 0x4c0;
        
        while ( !(IRQSIG & WAKEUP_TIMER_BIT ) )
        {}
        T2CON = 0;
        T2CLRI = 0x1;
}


⌨️ 快捷键说明

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