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

📄 lpc2xxisp.cpp

📁 一款不错的关于串口升级硬件的软件
💻 CPP
字号:
#include "stdafx.h"
#include "SCOMM.h"
#include "resource.h"
#include "FlashISPDlg.h"
#include "hexreader.h"
#include "math.h"
#include "time.h"
//#include "..\\FrameData.h"
//#include "..\\Option.h"

#define ENCODE_BYTE(b) (((b) == 0) ? 0x60 : ((b) + 0x20))
#define MAX_LINELEN 45
#define UU_LINE		20
#define SYSTEMCLK 8000
#define BUFF_SIZE 4096
#define DOWN_SIZE 1024

#define ID_DWN_EXIT					-1
#define ID_DWN_ACTIVERUN			2
#define ID_DWN_DOWNPROGRAM			8
#define ID_IAP_ACTIVE				9
#define ID_IAP_ERASE				10
#define ID_IAP_PROGRAM				11
#define ID_IAP_BAUD					12
#define MAX_RANDNUM				10


BOOL m_ExitThreadNo,m_bEraseAll;
extern UINT m_DownloadTimerId,m_iDownloadTimer;

int randEx(int MAX,int NUM)
{
	int k=0;
	int j=0;
	time_t t;
	int RAND[MAX_RANDNUM];
	//设置rand函数所用的启始种子值,以期每次产生的随机数序列均不相同。
	srand((unsigned) time(&t));
	for (k=1;k<=NUM;k++)//定制随机数数量。
	{
		RAND[k]=rand()%MAX;//定制随机数在0至最大值之间
		do
		{
			for (j=1;j<k;j++) if (RAND[j]==RAND[k]) //一次随机数序列中有相同随机数则再
	//产生一个,直至一次随机数序列中随机数全不相同。
			{
				RAND[k]=rand()%MAX;
				break;
			}
		}while(j<k);
		j += RAND[k];
	}
	j = j/MAX_RANDNUM;
	return j;
}

DWORD PacketCommand(BYTE *cmdstr,BYTE cmd,BYTE *str,DWORD len)
{
	BYTE chksum = 0;
	DWORD pos = 0;
	cmdstr[pos++] = 0x55;
	cmdstr[pos++] = 0xAA;
	cmdstr[pos++] = (BYTE)(len + 6)/0x100 &0xff;
	cmdstr[pos++] = (BYTE)(len + 6)&0xff;
	cmdstr[pos++] = (BYTE)~(len + 6)/0x100 &0xff;
	cmdstr[pos++] = (BYTE)~(len + 6)&0xff;
	cmdstr[pos++] = (BYTE)cmd;
	chksum ^= cmd;
	while(len --)
	{
		cmdstr[pos++] = *str;
		chksum ^= *(str++);
	}
	cmdstr[pos++] = chksum;
	return pos;
}

DWORD PacketData(BYTE *cmdstr,BYTE cmd,DWORD address,BYTE *str,DWORD len)
{
	BYTE chksum = 0;
	DWORD pos = 0;
	cmdstr[pos++] = 0x55;
	cmdstr[pos++] = 0xAA;
	cmdstr[pos++] = (BYTE)((len + 6 + 8)/0x100 &0xff);
	cmdstr[pos++] = (BYTE)((len + 6 + 8)&0xff);
	cmdstr[pos++] = (BYTE)(~(len + 6 + 8)/0x100 &0xff);
	cmdstr[pos++] = (BYTE)(~(len + 6 + 8)&0xff);
	cmdstr[pos++] = cmd;
	chksum ^= cmd;

	cmdstr[pos] = (BYTE)(address/0x1000000 & 0xff);
	chksum ^= cmdstr[pos++];

	cmdstr[pos] = (BYTE)(address/0x10000 & 0xff);
	chksum ^= cmdstr[pos++];

	cmdstr[pos] = (BYTE)(address/0x100 & 0xff);
	chksum ^= cmdstr[pos++];

	cmdstr[pos] = (BYTE)(address/0x1 & 0xff);
	chksum ^= cmdstr[pos++];

	cmdstr[pos] = (BYTE)(len/0x1000000 & 0xff);
	chksum ^= cmdstr[pos++];
	cmdstr[pos] = (BYTE)(len/0x10000 & 0xff);
	chksum ^= cmdstr[pos++];
	cmdstr[pos] = (BYTE)(len/0x100 & 0xff);
	chksum ^= cmdstr[pos++];
	cmdstr[pos] = (BYTE)(len/0x1 & 0xff);
	chksum ^= cmdstr[pos++];
	
	while(len --)
	{
		cmdstr[pos++] = *str;
		chksum ^= *(str++);
	}
	cmdstr[pos++] = chksum;
	return pos;
}


BYTE ReadOneFrame(CSerial *pComm,BYTE *buff,DWORD *length)
{
	DWORD acklen,size;
	BYTE ack[10],func_code,tPos=0;
	m_iDownloadTimer = 1000;
	do {
		do{
			pComm->ReadData((BYTE*)ack,1,&acklen);
			if(acklen) break;
			else
			{
				Sleep(1);
				if(m_iDownloadTimer) m_iDownloadTimer --;
			}
			if(m_iDownloadTimer == 0)	return 0;
		} while(1);
		m_iDownloadTimer = 50;
		switch(tPos)
		{
		case 0:
			if(ack[0]==0x55) tPos++;
			break;
		case 1:
			if((BYTE)ack[0]==0xAA) tPos++;
			break;
		case 2:
			size = ack[0]*0x100;
			tPos++;
			break;
		case 3:
			size += ack[0];
			tPos ++;
			break;
		case 4:
		case 5:
			tPos ++;
			break;
		case 6:
			func_code = ack[0];
			tPos ++;
			size -= 5;
			break;
		default:
			buff[tPos-7] = ack[0];
			tPos ++;
			size --;
			if(size == 0)
			{
				m_iDownloadTimer = 0;
				return func_code;
			}
		}
	}while(m_iDownloadTimer != 0);
	return 0;
}

// 发送命令,并校验返回命令是否正确
// cmd,	   发送命令
// cmdlen, 发送命令长度
// ack,	   接收响应
// acklen, 接收响应长度
// 返回结果:
// 0 -- 没有收到信息
// >0 -- 接收信息长度并校验正确, 
// <0 -- 接收信息长度并校验错误.
long SendIspCommand(CSerial *pComm,char *cmd,DWORD cmdlen,char *ack,DWORD acklen,int timeout,LPVOID pParam)
{
	CFlashISPDlg *pDlg = (CFlashISPDlg *)pParam;
	DWORD rcvlen=0,rec_len,error_cnt=25;
	long result;
	char rcvbuff[100]={0};
	pComm->ClearBuffer();
	pComm->SendData((BYTE*)cmd,cmdlen);
	m_DownloadTimerId = pDlg->SetTimer(24,timeout,NULL);
	m_iDownloadTimer = timeout;
	while((rcvlen < acklen)&&(m_iDownloadTimer))
	{
		pComm->ReadData((BYTE *)rcvbuff,acklen,&rec_len);
		rcvlen+=rec_len;
		if(rec_len == 0) Sleep(30);
	}
	pDlg->KillTimer(24);
	if(m_iDownloadTimer == 0) return 0;
	if(memcmp(rcvbuff,ack,acklen)==0) return rcvlen;
	result = rcvlen;
	return -result;
}

long IspReadData(CSerial *pComm,char *cmd,DWORD cmdlen,char *ack,DWORD acklen,int timeout,LPVOID pParam)
{
	CFlashISPDlg *pDlg = (CFlashISPDlg *)pParam;
	DWORD rcvlen=0,rec_len,error_cnt=25;
	pComm->ClearBuffer();
	pComm->SendData((BYTE*)cmd,cmdlen);
	m_DownloadTimerId = pDlg->SetTimer(24,timeout,NULL);
	m_iDownloadTimer = timeout;
	while((rcvlen < acklen)&&(m_iDownloadTimer))
	{
		pComm->ReadData((BYTE *)ack,acklen,&rec_len);
		rcvlen+=rec_len;
		if(rec_len == 0) Sleep(30);
	}
	pDlg->KillTimer(24);
	return rcvlen;
}

//int NxpIspCommand()
//{
//}

// 根据地址计算获得该地址属于第几扇区


char szMcuAck[]={"Synchronized\r\n"};
char szMcuAckOK[]={"OK\r\n"};
char szSynchronizeOK[]={"Synchronized\rOK\r\n"};
char szDeviceSignature[20];

void ExitIspFlash(int exitcode)
{
	if(m_ExitThreadNo == 0) m_ExitThreadNo = exitcode;
}

UINT ThreadNxpIspFlash(LPVOID pParam)
{
	CFlashISPDlg *pDlg = (CFlashISPDlg *)pParam;
	CWnd *pnd = pDlg->GetDlgItem(IDOK);
	CProgressCtrl *pDownProgress = (CProgressCtrl*)pDlg->GetDlgItem(IDC_UPDATEPROGRESS);
	BYTE errorcount;
	int iBackupStep,iDownProgress,iDownFileStep=0,iDownStep;
	char cmd[10240];
	char ack[100]="Synchronized\r\n";
	int		iSect=0;
//	DWORD	xLen;
	DWORD	size,acklen;//,rLen;
	CFile	file;
	DWORD	tPos=0;
	DWORD	rCnt=0;
	DWORD	iPos=0;
	DWORD	xCrc=0;
	int		oPos=0;
//	DWORD	ixx;
//	BYTE	*sBuf;
	UINT	iStartAddress,iCurrentAddress,iEndAddress;
	CString filename;
	BYTE	ProgramBuff[512*1024];
	m_ExitThreadNo = FALSE;
	iDownFileStep = 0;
				
	srand( (unsigned)time( NULL ) );
	switch(pDlg->m_iFunc)
	{
	case 0x01:
		iDownStep = ID_DWN_DOWNPROGRAM;
		iDownFileStep = 0;
		break;
	case 0x02:
//		iDownStep = ID_DWN_ERASE;
//		iDownFileStep = 0;
//		break;
	default:
		return 0;
	}
	do
	{
		switch(iDownStep)
		{
		case ID_IAP_ACTIVE:
			pDlg->m_ComPort.SetBaudRate(19200);
			pDlg->m_ComPort.ClearBuffer();
			Sleep(20);
			errorcount = 3;
			memset(ack,0,sizeof(ack));
			pDlg->m_ComPort.SendData((BYTE*)("\x55\xAA\x00\x00\x00\x00\xC0\x05\x68\x7f\x4f\x5D"),12);
			m_DownloadTimerId = pDlg->SetTimer(24,1000,NULL);
			m_iDownloadTimer = 1000;
			do{
				pDlg->m_ComPort.ReadData((BYTE *)ack,1,(DWORD*)&acklen);
			} while((acklen==0)&&(m_iDownloadTimer));
			pDlg->KillTimer(24);
			if((ack[0]=='?')&&(acklen!=0))
			{
				sprintf(cmd,"UPDATE!");
				pDlg->m_ComPort.ClearBuffer();
				memset(ack,0,sizeof(ack));
				Sleep(20);
				pDlg->m_ComPort.SendData((BYTE*)cmd,strlen(cmd));
				m_DownloadTimerId = pDlg->SetTimer(24,200,NULL);
				m_iDownloadTimer = 200;
				do{
					pDlg->m_ComPort.ReadData((BYTE *)ack,3,(DWORD*)&acklen);
				} while((acklen<2)&&(m_iDownloadTimer));
				//pDlg->KillTimer(24);
				if(strstr(ack,"OK!")!=NULL)
				{
					iDownStep = ID_IAP_BAUD;
					break;
				}
			}
			if(errorcount > 0)
			{
				errorcount --;
				break;
			}
			ExitIspFlash(iDownStep);
			break;
		case ID_IAP_BAUD:
			Sleep(200);
			pDlg->m_ComPort.ClearBuffer();
			memset(cmd,0,sizeof(cmd));
			size = PacketData((BYTE*)cmd,0x63,pDlg->m_iBaudRate,(BYTE*)ack,0);
			pDlg->m_ComPort.SendData((BYTE*)cmd,size);
			memset(cmd,0,sizeof(cmd));
			if(ReadOneFrame(&pDlg->m_ComPort,(BYTE*)cmd,(DWORD*)&size)==0x63)
			{
				if(cmd[0] == 0)
				{
					iDownStep = ID_IAP_ERASE;
					pDlg->m_ComPort.SetBaudRate(pDlg->m_iBaudRate);
					break;
				}
				else if(errorcount > 0)
				{
					errorcount --;
					iDownStep = ID_IAP_ACTIVE;
					break;
				}
				if(m_ExitThreadNo != 0) break;
			}
			ExitIspFlash(iDownStep);
			break;
		case ID_IAP_ERASE:
		//	pDlg->m_ComPort.SetBaudRate(9600);
			pDlg->m_ComPort.ClearBuffer();
			ack[0] = 0x00;
			ack[1] = 0x01;
			ack[2] = 0x00;
			ack[3] = 0x00;

			ack[4] = 0x00;
			ack[5] = 0x06;
			ack[6] = 0x80;
			ack[7] = 0x00;
			memset(cmd,0,sizeof(cmd));
			tPos = 0;
			size = PacketCommand((BYTE*)cmd,0x62,(BYTE*)ack,8);
			memset(ack,0,sizeof(ack));
			pDlg->m_ComPort.SendData((BYTE*)cmd,size);
			memset(cmd,0,sizeof(cmd));
			if(ReadOneFrame(&pDlg->m_ComPort,(BYTE*)cmd,(DWORD*)&size)==0x62)
			{
				if(cmd[0] == 0)
				{
					iDownStep = ID_IAP_PROGRAM;
					break;
				}
				if(m_ExitThreadNo != 0) break;
			}
			ExitIspFlash(iDownStep);
			break;
		case ID_IAP_PROGRAM:
			iStartAddress = 0x10000;
			iCurrentAddress = 0x10000;
			errorcount = 3;
			do {
				pDlg->m_ComPort.ClearBuffer();
				memset(cmd,0,sizeof(cmd));
				tPos = 0;
				size = PacketData((BYTE*)cmd,0x61,iCurrentAddress,(BYTE*)&ProgramBuff[iCurrentAddress],DOWN_SIZE);
				memset(ack,0,sizeof(ack));
				pDlg->m_ComPort.SendData((BYTE*)cmd,size);
				memset(cmd,0,sizeof(cmd));
				if(ReadOneFrame(&pDlg->m_ComPort,(BYTE*)cmd,(DWORD*)&size)==0x61)
				{
					if(cmd[0] == 0)
					{
						iCurrentAddress += DOWN_SIZE;
						pDownProgress->SetPos((iCurrentAddress-iStartAddress)*100/(iEndAddress-iStartAddress));
						errorcount = 10;
					}
					else
					{
						if(errorcount > 0) errorcount --;
						else
							break;
					}
				}
				if(m_ExitThreadNo != 0) break;
			}while(iCurrentAddress<iEndAddress);
			if(iCurrentAddress == iEndAddress)
			{
				iDownStep = iBackupStep;
			}
			else
			{
				ExitIspFlash(iDownStep);
			}
			break;
		case ID_DWN_DOWNPROGRAM:
			iBackupStep = ID_DWN_DOWNPROGRAM;
			switch(iDownFileStep)
			{
			case 0:		// open boxinfo file
				filename = pDlg->m_DownLoadFileName;
				memset(ProgramBuff,0,sizeof(ProgramBuff));
				if(ReadHexFile(ProgramBuff,filename,&iStartAddress,&iEndAddress)==FALSE)
				{
					AfxMessageBox("打开文件失败!");
					ExitIspFlash(iDownStep);
					break;
				}
				iCurrentAddress = iStartAddress;
				if((iEndAddress - iStartAddress) < DOWN_SIZE)
				{
					iEndAddress = iStartAddress + DOWN_SIZE;
				}
				else if((iEndAddress - iStartAddress)%DOWN_SIZE!=0)
				{
					iEndAddress += (DOWN_SIZE - ((iEndAddress - iStartAddress)%DOWN_SIZE));
				}
				m_bEraseAll = FALSE;
				iDownFileStep ++;
				iDownStep = ID_IAP_ACTIVE;
				//		iDownStep = ID_IAP_ERASE;
				errorcount = 3;
				iDownProgress = 0;
				break;
			case 1:		// erase flash room
				//				pDlg->m_ComPort.Close();
				pnd->SetWindowText("开始");
				iDownStep = ID_DWN_ACTIVERUN;
				iDownProgress = 0;
				//				pDlg->m_ComPort.Open();
				pDlg->m_ComPort.ClearBuffer();
				pDlg->m_ComPort.SetBaudRate(19200);
				pDlg->m_ComPort.ClearBuffer();
				Sleep(20);
				pDlg->m_ComPort.SendData((BYTE*)("\x55\xAA\x00\x00\x00\x00\xC0\x05\x68\x7f\x4f\x5D"),12);
				pDlg->m_ComPort.Close();
				break;
			}
			break;
		case ID_DWN_ACTIVERUN:
			pDlg->m_ComPort.SetBaudRate(19200);
			pDlg->m_ComPort.ClearBuffer();
			pDlg->m_ComPort.SendData((BYTE*)("\x55\xAA\x00\x00\x00\x00\xC0\x05\x68\x7f\x4f\x5D"),12);
			Sleep(500);
			iDownStep = ID_DWN_EXIT;
			break;
		}
		if(iDownStep == -1) break;
	}while(m_ExitThreadNo == 0);
	pDlg->m_ComPort.Close();
	switch(m_ExitThreadNo)
	{
	case ID_IAP_ACTIVE:
	case ID_IAP_BAUD:
	case ID_IAP_ERASE:
		AfxMessageBox("下载程序失败!");
		break;
	case ID_IAP_PROGRAM:
		if(errorcount == 0) AfxMessageBox("下载程序失败!");
		else AfxMessageBox("下载程序完成!");
		break;
	}
	pnd->SetWindowText("编程");
	pDlg->SendMessage(WM_MYUPDATEDATA,false);
	return 0;
}

⌨️ 快捷键说明

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