?? isp.c
字號:
/******************************************************************************
* Isp.c
*
* 更新256K的程序
* BUZZER 只是用于作指示用.
* 先下載指定的程序到SRAM,然后程序轉入SRAM空間運行(關閉中斷),擦除指定區域的程序,然后更新之.
* 注意:在升級前,需不停刷新看門狗,因看門狗中斷不可屏蔽及關閉!
* 升級后設置全清標志,并自動軟復位.
* 此程序需512K的SRAM支持.
*
* ============================>>>>>>>>>
* ============================>>>>>>>>>
* ISP使用了后(256K+8K)作為新程序臨時保存, 故此部分不應有系統變量,PLU及開臺除外 !!!
* 要下載的程序大小統一為512K(前256K空) !!!
* ============================>>>>>>>>>
* ============================>>>>>>>>>
*
* 2004.01.14
******************************************************************************/
#include "ecrsys.h"
#include "ftype.h"
#include "disp.h"
#include "string.h"
#include "data.h"
#define ISP_PORT PORT4
#define ROM_FE_TOP_ISP 0xf80000
#define ROW_SIZE 256 /* Must be 256 bytes for 28SF040 */
#define SST_ID 0xBF /* SST Manufacturer ID code */
#define SST_28SF040 0x04 /* SST 28SF040 device code */
#define AUTO_PG_ERASE1 0x20 //Auto Erase parameter 1
#define AUTO_PG_ERASE2 0xD0 //Auto Erase parameter 1
#define AUTO_PGRM 0x10 //Auto Program(byte - write) commond
#define RESET 0xFF //Reset command.
#define READ_ID 0x90 //Read the chip ID command
#define FLS040_BASE_ADDR 0xf80000
#define PGM_BASE_ADDR 0x40000 // 程序大小統一為512K,前256K空,后256K為程序區.
//#define ISP_PART_SIZE 0x40000 // Don't Modify it!
#define ISP_PART_SIZE 0x80000 // Don't Modify it!
#define SRAM_BASE_ADDR 0x180000 // 后256K,作為程序臨時保存區.
#define FLS_BASE_ADDR_EX 0xF80000 /*MX29F040 chip base address*/
long ispAddr;
//byte * const pSramLast512Bytes = (byte *)(0x100000 + 0x80000 - 512);
byte * const pSramLast512Bytes = (byte *)(DATA_FE_TOP + 0x80000 - 512);
// 指向SRAM最后512字節,升級后全清標志.
/******************************************************************
* 軟件升級,從PC獲取新的程序.
******************************************************************/
byte GetNewProgram(void)
{
byte sendData[50];
byte recvData[200];
byte i;
word j;
dword tmpAddr, flsAddr;
byte chkSum;
byte *ptr;
byte temp;
dword lastAddr;
byte port = ISP_PORT;
long num;
lastAddr = ISP_PART_SIZE;
if (port == ISP_PORT)
{
// only for debug
Uart_SetBaudRate(ISP_PORT, BRG_576);
}
// for ( j = 0; j < 5; j ++ ) /*Initial for can receive and transmit data*/
// ser_port[j].device = PT_PC_COMM;
ser_port[ISP_PORT].device = PT_PC_COMM;
ta3s = 0; // 關閉這些定時器,是為了提高串口通信速度.
tb2s = 0;
ta4s = 0;
CloseBuzzer();
bellcnt = 0;
// ta0s = 0;
Clr_Dsp_Data();
disp_Char_Str("HAND-----", 0);
for (i=0; i<3; i++)
{
ClrRsBuf(port);
sendData[0] = 0x1b;
sendData[1] = 0x10;
sendData[2] = 0xfe;
sendData[3] = 0x10;
sendData[4] = 0x07;
sendData[5] = 0x00;
sendData[6] = 0x1b + 0x10 + 0xfe + 0x10 + 0x07 + 0x00;
Wr_Str_Uart(port, sendData, 7);
if (ReadStringUART(port, recvData, 5) == OK)
{
if ((recvData[0] + recvData[1] + recvData[2] + recvData[3] == recvData[4]) &&
(memcmp(recvData, "OK", 2) == 0))
{
break;
}
}
for (j=0; j<0xffff; j++);
for (j=0; j<0xffff; j++);
}
if (i >= 3)
{
sendData[0] = 0x1b;
sendData[1] = 0x10;
sendData[2] = 0xfe;
sendData[3] = 0x13;
sendData[4] = 0x07;
sendData[5] = 0x00;
sendData[6] = 0x1b + 0x10 + 0xfe + 0x13 + 0x07 + 0x00;
Wr_Str_Uart(port, sendData, 7);
ta3s = 1;
tb2s = 1;
ta4s = 1;
// ta0s = 0;
return 0xff;
}
Clr_Dsp_Data();
disp_Char_Str("DOUN-----",0);
for (tmpAddr=0; tmpAddr < lastAddr; tmpAddr+=0x80)
{
// flsAddr = tmpAddr + PGM_BASE_ADDR; // 要下載的程序大小統一為512K(前256K空) !!!
flsAddr = tmpAddr;
for (i=0; i<3; i++)
{
ClrRsBuf(port);
sendData[0] = 0x1b;
sendData[1] = 0x10;
sendData[2] = 0xfe;
sendData[3] = 0x14;
sendData[4] = 13;
sendData[5] = 0;
sendData[6] = (byte)flsAddr;
sendData[7] = (byte)(flsAddr >> 8);
sendData[8] = (byte)(flsAddr >> 16);
sendData[9] = (byte)(flsAddr >> 24);
sendData[10] = 0x80;
sendData[11] = 0x00;
sendData[12] = 0;
for (j=0; j<12; j++)
{
sendData[12] += sendData[j];
}
Wr_Str_Uart(port, sendData, 13);
if (ReadStringUART(port, recvData, 8+0x80) == OK)
{
chkSum = 0;
for (j=0; j<0x80+8; j++)
{
chkSum += recvData[j];
}
if ((ReadByteUART(port, &temp) == 0) &&
(chkSum == temp))
{
if ((memcmp(recvData, "OK", 2) == 0)
&& (memcmp(&recvData[4], &sendData[6], 4) == 0)
&& ((recvData[2] + recvData[3] * 0x100) == 0x89))
{
break;
}
else
{
//disp_Char_Str("DATA ERR",0);
}
}
else
{
//disp_Char_Str("CS ERR",0);
}
}
else
{
//disp_Char_Str("RECE ERR",0);
}
for (j=0; j<0xffff; j++);
for (j=0; j<0xffff; j++);
}
if (i >= 3)
{
sendData[0] = 0x1b;
sendData[1] = 0x10;
sendData[2] = 0xfe;
sendData[3] = 0x13;
sendData[4] = 0x07;
sendData[5] = 0x00;
sendData[6] = 0x1b + 0x10 + 0xfe + 0x13 + 0x07 + 0x00;
Wr_Str_Uart(port, sendData, 7);
ta3s = 1;
tb2s = 1;
ta4s = 1;
return 0xff;
}
ptr = (byte *)(SRAM_BASE_ADDR + tmpAddr);
memcpy(ptr, &recvData[8], 0x80);/*Store the received data */
}
sendData[0] = 0x1b;
sendData[1] = 0x10;
sendData[2] = 0xfe;
sendData[3] = 0x12;
sendData[4] = 0x07;
sendData[5] = 0x00;
sendData[6] = 0x1b + 0x10 + 0xfe + 0x12 + 0x07 + 0x00;
Wr_Str_Uart(port, sendData, 7);
ta3s = 1;
tb2s = 1;
ta4s = 1;
return OK;
}
#define ERROR() \
while (1)\
{\
OpenBuzzer();\
for (dlyCnt=0; dlyCnt<1000; dlyCnt++);\
CloseBuzzer();\
for (dlyCnt=0; dlyCnt<1000; dlyCnt++);\
}
const byte eraseFls[7] = {0xaa, 0x55, 0x80, 0xaa, 0x55, 0x10};
const byte *ptrFls[7] =
{
(byte *)(FLS_BASE_ADDR_EX + 0x555),
(byte *)(FLS_BASE_ADDR_EX + 0x2aa),
(byte *)(FLS_BASE_ADDR_EX + 0x555),
(byte *)(FLS_BASE_ADDR_EX + 0x555),
(byte *)(FLS_BASE_ADDR_EX + 0x2aa),
(byte *)(FLS_BASE_ADDR_EX + 0x555),
};
#define ReduceBusSpeed() (wcr = 0xd5)
/* Write to MX29F040*/
void ISP_WriteFls(void)
{
byte i;
word j;
byte *ptr;
byte *ptrSram;
dword addr = 0;
dword timeOut = 0;
byte curData;
byte loop;
dword index;
word k;
dword dlyCnt;
byte romData = 0;
word cnt;
byte result = NG;
dword idx;
byte retry;
byte error;
#define Fls_Reset() (*((byte *)FLS040_BASE_ADDR) = 0xF0)
ReduceBusSpeed();
while (1)
{
// Erase FLASH
Fls_Reset();
for (retry=0; retry<3; retry++)
{
*(BYTE*)(FLS_BASE_ADDR_EX + 0x555) = 0xaa;
*(BYTE*)(FLS_BASE_ADDR_EX + 0x2aa) = 0x55;
*(byte*)(FLS_BASE_ADDR_EX + 0x555) = 0x80;
*(byte*)(FLS_BASE_ADDR_EX + 0x555) = 0xaa;
*(byte*)(FLS_BASE_ADDR_EX + 0x2aa) = 0x55;
*(byte*)(FLS_BASE_ADDR_EX + 0x555) = 0x10;
for (cnt=0; cnt<200; cnt++);
ptr = (BYTE*)FLS_BASE_ADDR_EX;
while (1) // set a loop to check the flash's WSM till ready or system time out
{
romData = *ptr;
if (romData == 0xff) // if yes, write data== read out data, program is successful
{
result = OK;
break; // exit program operation polling loop
}
else if ((romData & 0x20) == 0x20 ) // if Q5==1, then program operation is time out
{
result = NG; // set the program operation is failed
break; // break to exit the program operation
}
for (dlyCnt=0; dlyCnt<1000; dlyCnt++);
timeOut++; // the delay time is adjustable and deponed on the system clock
if (timeOut > 2000) // The number for Timeout must be set bigger than Max. of the spec.
{ // Basically, this time out loop to prevent system hang up is no necessary,
result = NG; // since the flash already provides the Q5 timeout bit for that.
break;
}
}
if (result == OK)
break;
Fls_Reset(); // write RESET command to clear fail status
}
if (result == NG)
{
ERROR();
}
//--------- write data to Flash
ptrSram = (byte *)SRAM_BASE_ADDR;
for (index=0; index < ISP_PART_SIZE; index++, ptrSram++)
{
byte result = NG;
addr = ROM_FE_TOP_ISP + index;
for (i=0; i<3; i++)
{
timeOut = 0;
ptr = (byte *)FLS040_BASE_ADDR;
*(ptr + 0x555) = 0xaa;
*(ptr + 0x2aa) = 0x55;
*(ptr + 0x555) = 0xa0;
*(byte *)addr = *ptrSram;
for (j=0; j<20; j++);
while (1) // set a loop to check the flash's WSM till ready or system time out
{
romData = *(byte *)addr;
if (romData == *ptrSram) // if yes, write data== read out data, program is successful
{
result = OK;
break; // exit program operation polling loop
}
else if ((romData & 0x20) == 0x20) // if Q5==1, then program operation is time out
{
result = NG; // set the program operation is failed
break; // break to exit the program operation
}
timeOut++; // the delay time is adjustable and deponed on the system clock
if (timeOut > 0x7ff) // The number for Timeout must be set bigger than Max. of the spec.
{ // Basically, this time out loop to prevent system hang up is no necessary,
result = NG; // since the flash already provides the Q5 timeout bit for that.
break;
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -